From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail-pf1-x42f.google.com (mail-pf1-x42f.google.com [IPv6:2607:f8b0:4864:20::42f]) by sourceware.org (Postfix) with ESMTPS id 587B83858D39 for ; Fri, 4 Mar 2022 14:18:12 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org 587B83858D39 Received: by mail-pf1-x42f.google.com with SMTP id j1so3764386pfj.5 for ; Fri, 04 Mar 2022 06:18:12 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:in-reply-to; bh=nWUb2tG+WPB9M3RgvpDCjnotA3ajIhhDgMtDFKkv3Ko=; b=gH02xFyJNTlvDF2/03TpljH7fL23CifilKXTwJRilLxmi56Gare4ROtfzjFsOG3jnj gWMSXIl6WJipcWY9m68Wq9QN/T1T8kZpy0bbtHUI0zuvfDPHBcsfD6Sh+sIBjqUkzJEt Lx3eFwSqfu5UvKytUixLSCCTC2m8SUAUKIY9+xl+Q4e0grs9UoNmYtrus/K9sVCRB8pW psewExDPjHlekMIIzk+8mxmb2kqjwM/90MG3Yepon30s3fh0YEFl2r0C+axFKUEz288K tztCCzzBD32Rb9oyx18MCFZpB4H6w9BctF1nOj4S7Zg7nbGeh6JL/xOS7/QqBJWfFagF N7ig== X-Gm-Message-State: AOAM533UFYlSSaz4OKa5QRLii7NrLWmkus2k2hBNegw+DmzpClta+xBo mmBSD6TZ5yd/6j+zLKBkdIXqMcCTngU= X-Google-Smtp-Source: ABdhPJz/sssGsUIITCW6W569PzGFHnFNLYBV4z7wJ0G5NmN0BXNbeea2e65af3gUIwV8yC7hJSgruA== X-Received: by 2002:a63:4412:0:b0:372:f29e:3108 with SMTP id r18-20020a634412000000b00372f29e3108mr34456282pga.354.1646403491060; Fri, 04 Mar 2022 06:18:11 -0800 (PST) Received: from gnu-tgl-3.localdomain ([172.58.35.88]) by smtp.gmail.com with ESMTPSA id t4-20020a056a0021c400b004f654ba3580sm6203986pfj.116.2022.03.04.06.18.10 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 04 Mar 2022 06:18:10 -0800 (PST) Received: by gnu-tgl-3.localdomain (Postfix, from userid 1000) id 006EFC03D4; Fri, 4 Mar 2022 06:18:08 -0800 (PST) Date: Fri, 4 Mar 2022 06:18:08 -0800 From: "H.J. Lu" To: Jan Beulich Cc: Binutils Subject: Re: [PATCH v2 1/3] x86-64/ELF: permit relaxed overflow checking for 32-bit PC-relative relocs Message-ID: References: <319f39e5-1f17-23ef-e3fa-2169876aa31c@suse.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <319f39e5-1f17-23ef-e3fa-2169876aa31c@suse.com> X-Spam-Status: No, score=-3022.8 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, FREEMAIL_FROM, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP, T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.4 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on server2.sourceware.org X-BeenThere: binutils@sourceware.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Binutils mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 04 Mar 2022 14:18:22 -0000 On Fri, Mar 04, 2022 at 02:34:58PM +0100, Jan Beulich wrote: > Right now it is impossible to encode certain valid 32-bit mode > constructs; see the respective new test case. Note that there are > further 32-bit PC-relative relocations, but I don't think they make a > lot of sense to use in mixed-bitness code, so they're not having > overrides put in place. > > Putting in place a new testcase, I'd like to note that the two existing > ones (pcrel16 and pcrel16abs) appear to be pretty pointless: They don't > expect any error despite supposedly checking for overflow, and in fact > there can't possibly be any error for the > - former since gas doesn't emit any relocation in the first place there, > - latter because the way the relocation gets expressed by gas doesn't > allow the linker to notice the overflow; it should be detected by gas > if at all, but see above (an error would be reported here for x86-64 > afaict, but this test doesn't get re-used there). > --- > TBD: I didn't put thoughts yet into also making this work when linking > ELF to PE. > > Note that I'm not sure at all whether this propagation of the struct > elf_linker_x86_params pointer is actually acceptable. But this is the > 5th or 6th try I made, with all others having been worse or not even > working out. Hence I'd need pretty detailed guidance on how else the > information could be made available. > --- > v2: Re-base and split. > > --- a/bfd/elf-linker-x86.h > +++ b/bfd/elf-linker-x86.h > @@ -28,6 +28,13 @@ enum elf_x86_prop_report > prop_report_shstk = 1 << 3 /* Report missing SHSTK property. */ > }; > > +/* Control of PC32 (on 64-bit) overflow check strictness. */ > +enum elf_x86_pcrel_relocs > +{ > + pcrel_relocs_default, > + pcrel_relocs_lax, > +}; > + > /* Used to pass x86-specific linker options from ld to bfd. */ > struct elf_linker_x86_params > { > @@ -64,6 +71,9 @@ struct elf_linker_x86_params > /* Report relative relocations. */ > unsigned int report_relative_reloc : 1; > > + /* Strictness of PC32 (on 64-bit) overflow checks. */ > + enum elf_x86_pcrel_relocs pcrel_relocs; > + > /* X86-64 ISA level needed. */ > unsigned int isa_level; > > --- a/bfd/elf64-x86-64.c > +++ b/bfd/elf64-x86-64.c > @@ -192,6 +192,15 @@ static reloc_howto_type x86_64_elf_howto > false) > }; > > +static reloc_howto_type x86_64_howto_pc32_lax = > + HOWTO(R_X86_64_PC32, 0, 2, 32, true, 0, complain_overflow_bitfield, > + bfd_elf_generic_reloc, "R_X86_64_PC32", false, 0, 0xffffffff, true); > + > +static reloc_howto_type x86_64_howto_pc32_bnd_lax = > + HOWTO(R_X86_64_PC32_BND, 0, 2, 32, true, 0, complain_overflow_bitfield, > + bfd_elf_generic_reloc, "R_X86_64_PC32_BND", false, 0, 0xffffffff, > + true); > + > /* Map BFD relocs to the x86_64 elf relocs. */ > struct elf_reloc_map > { > @@ -248,6 +257,30 @@ static const struct elf_reloc_map x86_64 > }; > > static reloc_howto_type * > +elf_x86_64_reloc_override (const bfd *abfd, reloc_howto_type *howto) > +{ > + const struct elf_linker_x86_params *params = elf_x86_tdata (abfd)->params; > + > + switch (howto->type) > + { > + default: > + break; > + > + case R_X86_64_PC32: > + if (params == NULL || params->pcrel_relocs != pcrel_relocs_lax) > + break; > + return &x86_64_howto_pc32_lax; > + > + case R_X86_64_PC32_BND: > + if (params == NULL || params->pcrel_relocs != pcrel_relocs_lax) > + break; > + return &x86_64_howto_pc32_bnd_lax; > + } > + > + return howto; > +} > + > +static reloc_howto_type * > elf_x86_64_rtype_to_howto (bfd *abfd, unsigned r_type) > { > unsigned i; > @@ -275,7 +308,7 @@ elf_x86_64_rtype_to_howto (bfd *abfd, un > else > i = r_type - (unsigned int) R_X86_64_vt_offset; > BFD_ASSERT (x86_64_elf_howto_table[i].type == r_type); > - return &x86_64_elf_howto_table[i]; > + return elf_x86_64_reloc_override (abfd, &x86_64_elf_howto_table[i]); > } > > /* Given a BFD reloc type, return a HOWTO structure. */ > @@ -313,7 +346,7 @@ elf_x86_64_reloc_name_lookup (bfd *abfd, > for (i = 0; i < ARRAY_SIZE (x86_64_elf_howto_table); i++) > if (x86_64_elf_howto_table[i].name != NULL > && strcasecmp (x86_64_elf_howto_table[i].name, r_name) == 0) > - return &x86_64_elf_howto_table[i]; > + return elf_x86_64_reloc_override (abfd, &x86_64_elf_howto_table[i]); > > return NULL; > } > @@ -1846,6 +1879,9 @@ elf_x86_64_scan_relocs (bfd *abfd, struc > > BFD_ASSERT (is_x86_elf (abfd, htab)); > > + /* Make command line controlled settings accessible from the object. */ > + elf_x86_tdata (abfd)->params = htab->params; > + > /* Get the section contents. */ > if (elf_section_data (sec)->this_hdr.contents != NULL) > contents = elf_section_data (sec)->this_hdr.contents; > --- a/bfd/elfxx-x86.h > +++ b/bfd/elfxx-x86.h > @@ -702,6 +702,9 @@ struct elf_x86_obj_tdata > /* R_*_RELATIVE relocation in GOT for this local symbol has been > processed. */ > char *relative_reloc_done; > + > + /* Container holding command line controlled linker settings. */ > + const struct elf_linker_x86_params *params; > }; > > enum elf_x86_plt_type > --- /dev/null > +++ b/gas/testsuite/gas/i386/code32.d > @@ -0,0 +1,3 @@ > +#name: x86-64 code32 > +#as: -mx86-used-note=no --generate-missing-build-notes=no > +#readelf: -n > --- /dev/null > +++ b/gas/testsuite/gas/i386/code32.s > @@ -0,0 +1,11 @@ > + .code32 > + .text > + .section .text.0, "ax", @progbits > + .type func0, @function > +func0: > + call func1 > + ret > + .section .text.1, "ax", @progbits > + .type func1, @function > +func1: > + jmp func0 > --- a/gas/testsuite/gas/i386/i386.exp > +++ b/gas/testsuite/gas/i386/i386.exp > @@ -1331,6 +1331,7 @@ if [gas_64_check] then { > run_dump_test "x86-64-property-8" > run_dump_test "x86-64-property-9" > run_dump_test "x86-64-property-14" > + run_dump_test "code32" > > if {[istarget "*-*-linux*"]} then { > run_dump_test "x86-64-align-branch-3" > --- a/ld/emulparams/elf32_x86_64.sh > +++ b/ld/emulparams/elf32_x86_64.sh > @@ -2,6 +2,7 @@ source_sh ${srcdir}/emulparams/plt_unwin > source_sh ${srcdir}/emulparams/extern_protected_data.sh > source_sh ${srcdir}/emulparams/dynamic_undefined_weak.sh > source_sh ${srcdir}/emulparams/reloc_overflow.sh > +source_sh ${srcdir}/emulparams/pcrel-relocs.sh > source_sh ${srcdir}/emulparams/call_nop.sh > source_sh ${srcdir}/emulparams/cet.sh > source_sh ${srcdir}/emulparams/x86-report-relative.sh > --- a/ld/emulparams/elf_x86_64.sh > +++ b/ld/emulparams/elf_x86_64.sh > @@ -2,6 +2,7 @@ source_sh ${srcdir}/emulparams/plt_unwin > source_sh ${srcdir}/emulparams/extern_protected_data.sh > source_sh ${srcdir}/emulparams/dynamic_undefined_weak.sh > source_sh ${srcdir}/emulparams/reloc_overflow.sh > +source_sh ${srcdir}/emulparams/pcrel-relocs.sh > source_sh ${srcdir}/emulparams/call_nop.sh > source_sh ${srcdir}/emulparams/cet.sh > source_sh ${srcdir}/emulparams/x86-report-relative.sh > --- /dev/null > +++ b/ld/emulparams/pcrel-relocs.sh > @@ -0,0 +1,11 @@ > +PARSE_AND_LIST_OPTIONS_STRICT_PCREL_RELOCS=' > + fprintf (file, _("\ > + -z lax-pcrel-relocs Lax PC-relative relocation overflow checks\n")); > +' > +PARSE_AND_LIST_ARGS_CASE_Z_STRICT_PCREL_RELOCS=' > + else if (strcmp (optarg, "lax-pcrel-relocs") == 0) > + params.pcrel_relocs = pcrel_relocs_lax; > +' > + > +PARSE_AND_LIST_OPTIONS="$PARSE_AND_LIST_OPTIONS $PARSE_AND_LIST_OPTIONS_STRICT_PCREL_RELOCS" > +PARSE_AND_LIST_ARGS_CASE_Z="$PARSE_AND_LIST_ARGS_CASE_Z $PARSE_AND_LIST_ARGS_CASE_Z_STRICT_PCREL_RELOCS" > --- a/ld/ld.texi > +++ b/ld/ld.texi > @@ -1372,6 +1372,12 @@ missing properties in input files. @opt > the linker issue an error for missing properties in input files. > Supported for Linux/x86_64. > > +@item lax-pcrel-relocs > +Relax relocation overflow checks for certain 32-bit PC-relative relocations > +which, when used by 32-bit code inside a 64-bit object, may require a > +larger range of values to be considered valid. > +Supported for x86-64 ELF targets. > + I think the check should be turned on automatically. Can you use a GNU property bit to tell linker that a larger range of values should be checked for R_X86_64_PC32 and issue an error for R_X86_64_PC32_BND? H.J.