From patchwork Mon Sep 12 14:50:50 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Wilco Dijkstra X-Patchwork-Id: 668819 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 3sXrNV6JVRz9sC4 for ; Tue, 13 Sep 2016 00:51:22 +1000 (AEST) Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.b=rxHtuMQm; dkim-atps=neutral DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :to:cc:subject:date:message-id:references:in-reply-to :mime-version:content-type:content-transfer-encoding; q=dns; s= default; b=eI0KzCMY1I/WkAQ1tZCDJqhZELb3rvQjdBBJ5izOxPp/UU3UYqLLB 2DhkATWVvBJJAlt5GgSJonfBbySaborRGESFmE3xGFDOHYptkyNpA4mxTLNsUeRc nhQLOiXymyidPDG7F565+kco7u/+pzryZBndEY5TK3ZY0F+6WrvtVw= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :to:cc:subject:date:message-id:references:in-reply-to :mime-version:content-type:content-transfer-encoding; s=default; bh=SrZickCySDN1N2Y9vj5GgY991a0=; b=rxHtuMQmdh8niWlbbcu8xXXOeO06 Zz01uyU6FGBU1wmDNnLnNu0vr4ktPZIlzQ2+mX/IPqF84jiHHcRq4wfkPDxSxYDy CB0h1lw4edpu43W5u/p8JlEbgHtShKp7LEH9KS8F7a7QXInSzAa1/o5igDIGy6Pc QxepwF5SRLcMR2U= Received: (qmail 78727 invoked by alias); 12 Sep 2016 14:51:07 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 78717 invoked by uid 89); 12 Sep 2016 14:51:06 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=1.5 required=5.0 tests=AWL, BAYES_40, KAM_LOTSOFHASH, KAM_STOCKGEN, SPF_PASS autolearn=no version=3.3.2 spammy=cap, dgfinal, dg-final, tree_to_shwi X-HELO: eu-smtp-delivery-143.mimecast.com Received: from eu-smtp-delivery-143.mimecast.com (HELO eu-smtp-delivery-143.mimecast.com) (207.82.80.143) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Mon, 12 Sep 2016 14:50:56 +0000 Received: from EUR01-VE1-obe.outbound.protection.outlook.com (mail-ve1eur01lp0245.outbound.protection.outlook.com [213.199.154.245]) (Using TLS) by eu-smtp-1.mimecast.com with ESMTP id uk-mta-100-KOu7UlsqMj-5w0GA56Jngw-1; Mon, 12 Sep 2016 15:50:52 +0100 Received: from AM5PR0802MB2610.eurprd08.prod.outlook.com (10.175.46.18) by AM5PR0802MB2386.eurprd08.prod.outlook.com (10.175.43.148) with Microsoft SMTP Server (version=TLS1_0, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA_P384) id 15.1.619.10; Mon, 12 Sep 2016 14:50:50 +0000 Received: from AM5PR0802MB2610.eurprd08.prod.outlook.com ([10.175.46.18]) by AM5PR0802MB2610.eurprd08.prod.outlook.com ([10.175.46.18]) with mapi id 15.01.0619.011; Mon, 12 Sep 2016 14:50:50 +0000 From: Wilco Dijkstra To: Richard Earnshaw , GCC Patches CC: nd Subject: Re: [PATCH v2][AArch64] Fix symbol offset limit Date: Mon, 12 Sep 2016 14:50:50 +0000 Message-ID: References: , <896d038e-f19f-d95e-2213-f3360ba71b28@arm.com>, In-Reply-To: x-ms-office365-filtering-correlation-id: bdef2571-f630-4c3f-ad51-08d3db1c304a x-microsoft-exchange-diagnostics: 1; AM5PR0802MB2386; 20:14fwI4C45diUQZxwx7TTgWIhvtzjPsZPZzijOGELl8t9/3IYIdBqYqlhCrcsOWPXzeS1KDnGgny5qTGjqLcCzchpFitXlGnvcH8ehvP+GfGN+elhxAe+fVWKs0q7Q9LZP1SQcgOb1uGPwCd3m7+i7BbJqH1MJrpEGep/titUJww= x-microsoft-antispam: UriScan:;BCL:0;PCL:0;RULEID:;SRVR:AM5PR0802MB2386; nodisclaimer: True x-microsoft-antispam-prvs: x-exchange-antispam-report-test: UriScan:(180628864354917); x-exchange-antispam-report-cfa-test: BCL:0; PCL:0; RULEID:(6040176)(601004)(2401047)(5005006)(8121501046)(3002001)(10201501046)(6055026); SRVR:AM5PR0802MB2386; BCL:0; PCL:0; RULEID:; SRVR:AM5PR0802MB2386; x-forefront-prvs: 006339698F x-forefront-antispam-report: SFV:NSPM; SFS:(10009020)(6009001)(7916002)(54534003)(377424004)(24454002)(19580395003)(3846002)(450100001)(76576001)(102836003)(19580405001)(6116002)(7696004)(2900100001)(122556002)(10400500002)(586003)(3280700002)(189998001)(87936001)(66066001)(87386001)(8936002)(11100500001)(9686002)(2906002)(4326007)(3660700001)(54356999)(50986999)(106116001)(8676002)(81166006)(5002640100001)(2950100001)(76176999)(92566002)(5001770100001)(4001520100001)(77096005)(86362001)(7736002)(5660300001)(33656002)(7846002)(305945005)(74316002)(5001760100003); DIR:OUT; SFP:1101; SCL:1; SRVR:AM5PR0802MB2386; H:AM5PR0802MB2610.eurprd08.prod.outlook.com; FPR:; SPF:None; LANG:en; spamdiagnosticoutput: 1:99 spamdiagnosticmetadata: NSPM MIME-Version: 1.0 X-OriginatorOrg: arm.com X-MS-Exchange-CrossTenant-originalarrivaltime: 12 Sep 2016 14:50:50.4038 (UTC) X-MS-Exchange-CrossTenant-fromentityheader: Hosted X-MS-Exchange-CrossTenant-id: f34e5979-57d9-4aaa-ad4d-b122a662184d X-MS-Exchange-Transport-CrossTenantHeadersStamped: AM5PR0802MB2386 X-MC-Unique: KOu7UlsqMj-5w0GA56Jngw-1 Wilco wrote:  > The original example is from GCC itself, the fixed_regs array is small but due to > optimization we can end up with &fixed_regs + 0xffffffff. We could also check the bounds of each symbol if they exist, like the patch below. In aarch64_classify_symbol symbols are allowed full-range offsets on relocations. This means the offset can use all of the +/-4GB offset, leaving no offset available for the symbol itself. This results in relocation overflow and link-time errors for simple expressions like &global_char + 0xffffff00. To avoid this, limit the offset to +/-1GB so that the symbol needs to be within a 3GB offset from its references. For the tiny code model use a 64KB offset, allowing most of the 1MB range for code/data between the symbol and its references. For symbols with a defined size, limit the offset to be within the size of the symbol. ChangeLog: 2016-09-12 Wilco Dijkstra gcc/ * config/aarch64/aarch64.c (aarch64_classify_symbol): Apply reasonable limit to symbol offsets. testsuite/ * gcc.target/aarch64/symbol-range.c (foo): Set new limit. * gcc.target/aarch64/symbol-range-tiny.c (foo): Likewise. diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c index 385bd560fb12cd5d404e6ddb2f01edf1fe72d729..275a828ac9e6e9b8187380c1b602ffb1b2bcfb21 100644 --- a/gcc/config/aarch64/aarch64.c +++ b/gcc/config/aarch64/aarch64.c @@ -9351,6 +9351,8 @@ aarch64_classify_symbol (rtx x, rtx offset) if (aarch64_tls_symbol_p (x)) return aarch64_classify_tls_symbol (x); + const_tree decl = SYMBOL_REF_DECL (x); + switch (aarch64_cmodel) { case AARCH64_CMODEL_TINY: @@ -9359,25 +9361,45 @@ aarch64_classify_symbol (rtx x, rtx offset) we have no way of knowing the address of symbol at compile time so we can't accurately say if the distance between the PC and symbol + offset is outside the addressible range of +/-1M in the - TINY code model. So we rely on images not being greater than - 1M and cap the offset at 1M and anything beyond 1M will have to - be loaded using an alternative mechanism. Furthermore if the - symbol is a weak reference to something that isn't known to - resolve to a symbol in this module, then force to memory. */ + TINY code model. So we limit the maximum offset to +/-64KB and + assume the offset to the symbol is not larger than +/-(1M - 64KB). + Furthermore force to memory if the symbol is a weak reference to + something that doesn't resolve to a symbol in this module. */ if ((SYMBOL_REF_WEAK (x) && !aarch64_symbol_binds_local_p (x)) - || INTVAL (offset) < -1048575 || INTVAL (offset) > 1048575) + || !IN_RANGE (INTVAL (offset), -0x10000, 0x10000)) return SYMBOL_FORCE_TO_MEM; + + /* Limit offset to within the size of a declaration if available. */ + if (decl && DECL_P (decl)) + { + const_tree decl_size = DECL_SIZE (decl); + + if (decl_size + && !IN_RANGE (INTVAL (offset), 0, tree_to_shwi (decl_size))) + return SYMBOL_FORCE_TO_MEM; + } + return SYMBOL_TINY_ABSOLUTE; case AARCH64_CMODEL_SMALL: /* Same reasoning as the tiny code model, but the offset cap here is - 4G. */ + 1G, allowing +/-3G for the offset to the symbol. */ if ((SYMBOL_REF_WEAK (x) && !aarch64_symbol_binds_local_p (x)) - || !IN_RANGE (INTVAL (offset), HOST_WIDE_INT_C (-4294967263), - HOST_WIDE_INT_C (4294967264))) + || !IN_RANGE (INTVAL (offset), -0x40000000, 0x40000000)) return SYMBOL_FORCE_TO_MEM; + + /* Limit offset to within the size of a declaration if available. */ + if (decl && DECL_P (decl)) + { + const_tree decl_size = DECL_SIZE (decl); + + if (decl_size + && !IN_RANGE (INTVAL (offset), 0, tree_to_shwi (decl_size))) + return SYMBOL_FORCE_TO_MEM; + } + return SYMBOL_SMALL_ABSOLUTE; case AARCH64_CMODEL_TINY_PIC: diff --git a/gcc/testsuite/gcc.target/aarch64/symbol-range-tiny.c b/gcc/testsuite/gcc.target/aarch64/symbol-range-tiny.c index d7e46b059e41f2672b3a1da5506fa8944e752e01..d399a3637ed834ddc4bb429594c4ec229b5c2ea8 100644 --- a/gcc/testsuite/gcc.target/aarch64/symbol-range-tiny.c +++ b/gcc/testsuite/gcc.target/aarch64/symbol-range-tiny.c @@ -1,12 +1,12 @@ -/* { dg-do compile } */ +/* { dg-do link } */ /* { dg-options "-O3 -save-temps -mcmodel=tiny" } */ -int fixed_regs[0x00200000]; +char fixed_regs[0x00200000]; int -foo() +main() { - return fixed_regs[0x00080000]; + return fixed_regs[0x000ff000]; } /* { dg-final { scan-assembler-not "adr\tx\[0-9\]+, fixed_regs\\\+" } } */ diff --git a/gcc/testsuite/gcc.target/aarch64/symbol-range.c b/gcc/testsuite/gcc.target/aarch64/symbol-range.c index 6574cf4310430b847e77ea56bf8f20ef312d53e4..4b4ec8dab9321026d1fae96d336565a7883c8203 100644 --- a/gcc/testsuite/gcc.target/aarch64/symbol-range.c +++ b/gcc/testsuite/gcc.target/aarch64/symbol-range.c @@ -1,12 +1,12 @@ -/* { dg-do compile } */ +/* { dg-do link } */ /* { dg-options "-O3 -save-temps -mcmodel=small" } */ -int fixed_regs[0x200000000ULL]; +char fixed_regs[0x200000000ULL]; int -foo() +main() { - return fixed_regs[0x100000000ULL]; + return fixed_regs[0xfffff000ULL]; } /* { dg-final { scan-assembler-not "adrp\tx\[0-9\]+, fixed_regs\\\+" } } */