From 7320c6c93c36873df9c62e9843d95dc5fbd29caa8bb8244445cf2479e1dc8826 Mon Sep 17 00:00:00 2001 From: Michael Matz Date: Thu, 24 Jan 2019 14:15:08 +0000 Subject: [PATCH] - Add s390-relro.diff to improve relro support on s390 [fate#326356] OBS-URL: https://build.opensuse.org/package/show/devel:gcc/binutils?expand=0&rev=291 --- binutils.changes | 6 + binutils.spec | 4 +- cross-aarch64-binutils.spec | 2 +- cross-arm-binutils.spec | 2 +- cross-avr-binutils.spec | 2 +- cross-epiphany-binutils.spec | 2 +- cross-hppa-binutils.spec | 2 +- cross-hppa64-binutils.spec | 2 +- cross-i386-binutils.spec | 2 +- cross-ia64-binutils.spec | 2 +- cross-m68k-binutils.spec | 2 +- cross-mips-binutils.spec | 2 +- cross-ppc-binutils.spec | 2 +- cross-ppc64-binutils.spec | 2 +- cross-ppc64le-binutils.spec | 2 +- cross-riscv64-binutils.spec | 2 +- cross-rx-binutils.spec | 2 +- cross-s390-binutils.spec | 2 +- cross-s390x-binutils.spec | 2 +- cross-sparc-binutils.spec | 2 +- cross-sparc64-binutils.spec | 2 +- cross-spu-binutils.spec | 2 +- cross-x86_64-binutils.spec | 2 +- s390-relro.diff | 1079 ++++++++++++++++++++++++++++++++++ 24 files changed, 1109 insertions(+), 22 deletions(-) create mode 100644 s390-relro.diff diff --git a/binutils.changes b/binutils.changes index 3f6e057..dbc114c 100644 --- a/binutils.changes +++ b/binutils.changes @@ -1,3 +1,9 @@ +------------------------------------------------------------------- +Thu Jan 24 14:10:56 UTC 2019 - matz@suse.com + +- Add s390-relro.diff to improve relro support on s390 + [fate#326356] + ------------------------------------------------------------------- Thu Dec 6 13:53:51 UTC 2018 - matz@suse.com diff --git a/binutils.spec b/binutils.spec index e8759ff..9c3c374 100644 --- a/binutils.spec +++ b/binutils.spec @@ -1,7 +1,7 @@ # # spec file for package binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -97,6 +97,7 @@ Patch37: binutils-revert-plt32-in-branches.diff Patch38: fix-pr23919-1.diff Patch39: fix-pr23919-2.diff Patch40: fix-pr23919-3.diff +Patch41: s390-relro.diff Patch90: cross-avr-nesc-as.patch Patch92: cross-avr-omit_section_dynsym.patch Patch93: cross-avr-size.patch @@ -173,6 +174,7 @@ echo "make check will return with %{make_check_handling} in case of testsuite fa %patch38 -p1 %patch39 -p1 %patch40 -p1 +%patch41 -p1 %if "%{TARGET}" == "avr" cp gas/config/tc-avr.h gas/config/tc-avr-nesc.h %patch90 diff --git a/cross-aarch64-binutils.spec b/cross-aarch64-binutils.spec index b90e0bd..8cb2b4f 100644 --- a/cross-aarch64-binutils.spec +++ b/cross-aarch64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-aarch64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-arm-binutils.spec b/cross-arm-binutils.spec index 8bcb96f..ee230c2 100644 --- a/cross-arm-binutils.spec +++ b/cross-arm-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-arm-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-avr-binutils.spec b/cross-avr-binutils.spec index 0c15a97..bb14cf5 100644 --- a/cross-avr-binutils.spec +++ b/cross-avr-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-avr-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-epiphany-binutils.spec b/cross-epiphany-binutils.spec index 351545e..311835a 100644 --- a/cross-epiphany-binutils.spec +++ b/cross-epiphany-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-epiphany-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-hppa-binutils.spec b/cross-hppa-binutils.spec index 999bdc2..0a1b4b3 100644 --- a/cross-hppa-binutils.spec +++ b/cross-hppa-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-hppa-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-hppa64-binutils.spec b/cross-hppa64-binutils.spec index d7d6907..aeabf5a 100644 --- a/cross-hppa64-binutils.spec +++ b/cross-hppa64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-hppa64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-i386-binutils.spec b/cross-i386-binutils.spec index 9754eda..2d99a41 100644 --- a/cross-i386-binutils.spec +++ b/cross-i386-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-i386-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-ia64-binutils.spec b/cross-ia64-binutils.spec index 8c5c15a..2447a81 100644 --- a/cross-ia64-binutils.spec +++ b/cross-ia64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-ia64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-m68k-binutils.spec b/cross-m68k-binutils.spec index 477e739..c5cc7b0 100644 --- a/cross-m68k-binutils.spec +++ b/cross-m68k-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-m68k-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-mips-binutils.spec b/cross-mips-binutils.spec index f4f7a40..fd78d75 100644 --- a/cross-mips-binutils.spec +++ b/cross-mips-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-mips-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-ppc-binutils.spec b/cross-ppc-binutils.spec index 36b8c71..df4ce63 100644 --- a/cross-ppc-binutils.spec +++ b/cross-ppc-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-ppc-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-ppc64-binutils.spec b/cross-ppc64-binutils.spec index 402d106..45a7e82 100644 --- a/cross-ppc64-binutils.spec +++ b/cross-ppc64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-ppc64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-ppc64le-binutils.spec b/cross-ppc64le-binutils.spec index cde0844..7ec686c 100644 --- a/cross-ppc64le-binutils.spec +++ b/cross-ppc64le-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-ppc64le-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-riscv64-binutils.spec b/cross-riscv64-binutils.spec index 5242010..8d9ed13 100644 --- a/cross-riscv64-binutils.spec +++ b/cross-riscv64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-riscv64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-rx-binutils.spec b/cross-rx-binutils.spec index 20af2c3..66423e0 100644 --- a/cross-rx-binutils.spec +++ b/cross-rx-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-rx-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-s390-binutils.spec b/cross-s390-binutils.spec index 0811afc..ebed162 100644 --- a/cross-s390-binutils.spec +++ b/cross-s390-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-s390-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-s390x-binutils.spec b/cross-s390x-binutils.spec index ac7cd2d..d1652b9 100644 --- a/cross-s390x-binutils.spec +++ b/cross-s390x-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-s390x-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-sparc-binutils.spec b/cross-sparc-binutils.spec index eeee08a..4c27d7e 100644 --- a/cross-sparc-binutils.spec +++ b/cross-sparc-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-sparc-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-sparc64-binutils.spec b/cross-sparc64-binutils.spec index ba0d307..4897ed8 100644 --- a/cross-sparc64-binutils.spec +++ b/cross-sparc64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-sparc64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-spu-binutils.spec b/cross-spu-binutils.spec index 545f815..79c2d5e 100644 --- a/cross-spu-binutils.spec +++ b/cross-spu-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-spu-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/cross-x86_64-binutils.spec b/cross-x86_64-binutils.spec index 7604d3e..4b38b55 100644 --- a/cross-x86_64-binutils.spec +++ b/cross-x86_64-binutils.spec @@ -1,7 +1,7 @@ # # spec file for package cross-x86_64-binutils # -# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany. +# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed diff --git a/s390-relro.diff b/s390-relro.diff new file mode 100644 index 0000000..cf387ed --- /dev/null +++ b/s390-relro.diff @@ -0,0 +1,1079 @@ +Implement fate#326356 +This combines commits afca762f and a381372 +to implement RELRO properly on s390. Before that +the order of .got.plt vs. .got was such that the latter +couldn't be made read-only when lazy linking was enabled. + +commit afca762f598d453c563f244cd3777715b1a0cb72 +Author: Andreas Krebbel +Date: Thu Dec 21 13:12:03 2017 +0100 + + S/390: Improve partial relro support for 64 bit + + Currently on S/390 the .got.plt always comes first which prevents the + GNU_RELRO segment from being extended across the non-plt GOT entries. + + Just swapping both unfortunately is not that simple since our ABI + requires the _GLOBAL_OFFSET_TABLE_ symbol to point to the very + beginning of the entire GOT. Of the 3 magic GOT entries the first is + accessed via got pointer while second and third are being accessed via + DT_PLTGOT. In order to keep them together we make DT_PLTGOT to point + to the .got instead of .got.plt. However, this violates an assumption + in the dynamic linker prelink undo code about the GOTPLT entries + starting at DT_PLTGOT + 3. We got rid of this requirement with a + Glibc patch already in version 2.24: + https://sourceware.org/ml/libc-alpha/2016-06/msg01302.html + + So the S/390 relro GOT layout will look like this with this patch: + + +----------------------------------+ + |got[0]: DYNAMIC | <--- _GLOBAL_OFFSET_TABLE_ == DT_PLTGOT .got + |got[1]: link_map parm | + |got[2]: &_dl_runtime_resolve | + +----------------------------------+ + | | non-plt GOT entries + | | + | | + +----------------------------------+ + | | <--- .gotplt, PLT GOT entries + | | + | | + | | + +----------------------------------+ + + The patch detects the current layout in size_dynamic_section in order + to deal also with linker scripts not generated by this ld version. + With partial relro enabled we pick a linker script where .got and + .got.plt are swapped which then triggers the rest of the logic. + + ld/ChangeLog: + + 2018-07-18 Andreas Krebbel + + * emulparams/elf64_s390.sh: Define GENERATE_RELRO_SCRIPT and + SEPARATE_GOTPLT. + * testsuite/ld-s390/gotreloc_64-relro-1.dd: New test. + * testsuite/ld-s390/gotreloc_64-norelro-1.dd: Renamed from ... + * testsuite/ld-s390/gotreloc_64-1.dd: ... this. + * testsuite/ld-s390/s390.exp: Split the GOT testcase into two. + + bfd/ChangeLog: + + 2018-07-18 Andreas Krebbel + + * elf-s390-common.c (s390_gotplt_after_got_p): New function. + (s390_got_pointer): New function. + (s390_got_offset): New function. + (s390_gotplt_offset): New function. + * elf64-s390.c (allocate_dynrelocs): Adjust comment. + (elf_s390_size_dynamic_sections): Move space for magic GOT entries + from .got.plt to .got if necessary and pick the right location for + _GLOBAL_OFFSET_TABLE_. + (elf_s390_relocate_section): Use the wrapper functions from + elf-s390-common.c to deal with both possible layouts (either .got + or .got.plt first). + (elf_s390_finish_dynamic_sections): Likewise. + (elf_s390_finish_dynamic_symbol): Make the location of the GOT + magic entries conditional. + +commit a38137289e91fd548fc27fb6566a439233b94d65 +Author: Andreas Krebbel +Date: Mon Jun 11 13:23:00 2018 +0200 + + ld: Enable using separate linker script for -z relro + + With this patch dedicated linker scripts can be generated for partial + relro triggered by defining GENERATE_RELRO_SCRIPT in the target + specific scripts. + + This is necessary for e.g. S/390 where usually the .got.plt comes + first and prevents the relro segment from being extended across the + non-plt GOT entries. + + The patch started with the work from Marcin taken from the mwk user + branches. However, the patch needed substantial changes due to the + 'separate code' feature which got committed in the meantime. + + ld/ChangeLog: + + 2018-07-18 Andreas Krebbel + Marcin Koƛcielnicki + + * emultempl/elf32.em: Add code to pick dedicated linker scripts + for partial relro. + * genscripts.sh: Generate dedicated linker scripts for partial relro. + +Index: binutils-2.31/bfd/elf-s390-common.c +=================================================================== +--- binutils-2.31.orig/bfd/elf-s390-common.c 2018-06-24 20:38:56.000000000 +0200 ++++ binutils-2.31/bfd/elf-s390-common.c 2019-01-24 15:07:25.000000000 +0100 +@@ -30,6 +30,87 @@ s390_is_ifunc_symbol_p (struct elf_link_ + return h->type == STT_GNU_IFUNC || eh->ifunc_resolver_address != 0; + } + ++/* Return true if .got.plt is supposed to be emitted after .got. */ ++ ++static inline bfd_boolean ++s390_gotplt_after_got_p (struct bfd_link_info *info) ++{ ++ struct elf_s390_link_hash_table *htab = elf_s390_hash_table (info); ++ ++ if (!htab->elf.sgot || !htab->elf.sgotplt) ++ return TRUE; ++ ++ if (htab->elf.sgot->output_section == htab->elf.sgotplt->output_section) ++ { ++ if (htab->elf.sgot->output_offset < htab->elf.sgotplt->output_offset) ++ return TRUE; ++ } ++ else ++ { ++ if (htab->elf.sgot->output_section->vma ++ <= htab->elf.sgotplt->output_section->vma) ++ return TRUE; ++ } ++ return FALSE; ++} ++ ++/* Return the value of the _GLOBAL_OFFSET_TABLE_ symbol. */ ++ ++static inline bfd_vma ++s390_got_pointer (struct bfd_link_info *info) ++{ ++ struct elf_s390_link_hash_table *htab = elf_s390_hash_table (info); ++ bfd_vma got_pointer; ++ ++ BFD_ASSERT (htab && htab->elf.hgot); ++ ++ got_pointer = (htab->elf.hgot->root.u.def.section->output_section->vma ++ + htab->elf.hgot->root.u.def.section->output_offset); ++ /* Our ABI requires the GOT pointer to point at the very beginning ++ of the global offset table. */ ++ BFD_ASSERT (got_pointer ++ <= (htab->elf.sgot->output_section->vma ++ + htab->elf.sgot->output_offset)); ++ BFD_ASSERT (got_pointer ++ <= (htab->elf.sgotplt->output_section->vma ++ + htab->elf.sgotplt->output_offset)); ++ ++ return got_pointer; ++} ++ ++ ++/* Return the offset of the .got versus _GLOBAL_OFFSET_TABLE_. */ ++ ++static inline bfd_vma ++s390_got_offset (struct bfd_link_info *info) ++{ ++ struct elf_s390_link_hash_table *htab = elf_s390_hash_table (info); ++ ++ /* The absolute address of the .got in the target image. */ ++ bfd_vma got_address = (htab->elf.sgot->output_section->vma ++ + htab->elf.sgot->output_offset); ++ ++ /* GOT offset must not be negative. */ ++ BFD_ASSERT (s390_got_pointer (info) <= got_address); ++ return got_address - s390_got_pointer (info); ++} ++ ++/* Return the offset of the .got.plt versus _GLOBAL_OFFSET_TABLE_. */ ++ ++static inline bfd_vma ++s390_gotplt_offset (struct bfd_link_info *info) ++{ ++ struct elf_s390_link_hash_table *htab = elf_s390_hash_table (info); ++ ++ /* The absolute address of the .got.plt in the target image. */ ++ bfd_vma gotplt_address = (htab->elf.sgotplt->output_section->vma ++ + htab->elf.sgotplt->output_offset); ++ ++ /* GOT offset must not be negative. */ ++ BFD_ASSERT (s390_got_pointer (info) <= gotplt_address); ++ return gotplt_address - s390_got_pointer (info); ++} ++ + /* Create sections needed by STT_GNU_IFUNC symbol. */ + + static bfd_boolean +Index: binutils-2.31/bfd/elf64-s390.c +=================================================================== +--- binutils-2.31.orig/bfd/elf64-s390.c 2018-07-10 09:12:05.000000000 +0200 ++++ binutils-2.31/bfd/elf64-s390.c 2019-01-24 15:07:25.000000000 +0100 +@@ -481,7 +481,7 @@ elf_s390_is_local_label_name (bfd *abfd, + + #define RELA_ENTRY_SIZE sizeof (Elf64_External_Rela) + +-/* The first three entries in a procedure linkage table are reserved, ++/* The first three entries in a global offset table are reserved, + and the initial contents are unimportant (we zero them out). + Subsequent entries look like this. See the SVR4 ABI 386 + supplement to see how this works. */ +@@ -511,8 +511,8 @@ elf_s390_is_local_label_name (bfd *abfd, + LG 1,0(1) # 6 bytes Load address from GOT in r1 + BCR 15,1 # 2 bytes Jump to address + RET1: BASR 1,0 # 2 bytes Return from GOT 1st time +- LGF 1,12(1) # 6 bytes Load offset in symbl table in r1 +- BRCL 15,-x # 6 bytes Jump to start of PLT ++ LGF 1,12(1) # 6 bytes Load rela.plt offset into r1 ++ BRCL 15,-x # 6 bytes Jump to first PLT entry + .long ? # 4 bytes offset into .rela.plt + + Total = 32 bytes per PLT entry +@@ -1605,8 +1605,7 @@ allocate_dynrelocs (struct elf_link_hash + /* Make room for this entry. */ + s->size += PLT_ENTRY_SIZE; + +- /* We also need to make an entry in the .got.plt section, which +- will be placed in the .got section by the linker script. */ ++ /* We also need to make an entry in the .got.plt section. */ + htab->elf.sgotplt->size += GOT_ENTRY_SIZE; + + /* We also need to make an entry in the .rela.plt section. */ +@@ -1831,6 +1830,20 @@ elf_s390_size_dynamic_sections (bfd *out + } + } + ++ if (htab->elf.sgot && s390_gotplt_after_got_p (info)) ++ { ++ /* _bfd_elf_create_got_section adds the got header size always ++ to .got.plt but we need it in .got if this section comes ++ first. */ ++ htab->elf.sgot->size += 3 * GOT_ENTRY_SIZE; ++ htab->elf.sgotplt->size -= 3 * GOT_ENTRY_SIZE; ++ ++ /* Make the _GLOBAL_OFFSET_TABLE_ symbol point to the .got ++ instead of .got.plt. */ ++ htab->elf.hgot->root.u.def.section = htab->elf.sgot; ++ htab->elf.hgot->root.u.def.value = 0; ++ } ++ + /* Set up .got offsets for local syms, and space for local dynamic + relocs. */ + for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next) +@@ -2131,7 +2144,6 @@ elf_s390_relocate_section (bfd *output_b + bfd_boolean unresolved_reloc; + bfd_reloc_status_type r; + int tls_type; +- asection *base_got = htab->elf.sgot; + bfd_boolean resolved_to_zero; + + r_type = ELF64_R_TYPE (rel->r_info); +@@ -2172,7 +2184,7 @@ elf_s390_relocate_section (bfd *output_b + case R_390_PLTOFF16: + case R_390_PLTOFF32: + case R_390_PLTOFF64: +- relocation -= htab->elf.sgot->output_section->vma; ++ relocation -= s390_got_pointer (info); + break; + case R_390_GOTPLT12: + case R_390_GOTPLT16: +@@ -2192,10 +2204,10 @@ elf_s390_relocate_section (bfd *output_b + htab->elf.sgot->contents + + local_got_offsets[r_symndx]); + relocation = (local_got_offsets[r_symndx] + +- htab->elf.sgot->output_offset); ++ s390_got_offset (info)); + + if (r_type == R_390_GOTENT || r_type == R_390_GOTPLTENT) +- relocation += htab->elf.sgot->output_section->vma; ++ relocation += s390_got_pointer (info); + break; + } + default: +@@ -2254,25 +2266,23 @@ elf_s390_relocate_section (bfd *output_b + + if (s390_is_ifunc_symbol_p (h)) + { ++ /* Entry indices of .iplt and .igot.plt match ++ 1:1. No magic PLT first entry here. */ + plt_index = h->plt.offset / PLT_ENTRY_SIZE; +- relocation = (plt_index * GOT_ENTRY_SIZE + +- htab->elf.igotplt->output_offset); +- if (r_type == R_390_GOTPLTENT) +- relocation += htab->elf.igotplt->output_section->vma; ++ relocation = (plt_index * GOT_ENTRY_SIZE ++ + s390_gotplt_offset (info) ++ + htab->elf.igotplt->output_offset); + } + else + { +- /* Calc. index no. +- Current offset - size first entry / entry size. */ +- plt_index = (h->plt.offset - PLT_FIRST_ENTRY_SIZE) / +- PLT_ENTRY_SIZE; +- +- /* Offset in GOT is PLT index plus GOT headers(3) +- times 8, addr & GOT addr. */ +- relocation = (plt_index + 3) * GOT_ENTRY_SIZE; +- if (r_type == R_390_GOTPLTENT) +- relocation += htab->elf.sgot->output_section->vma; ++ plt_index = ((h->plt.offset - PLT_FIRST_ENTRY_SIZE) ++ / PLT_ENTRY_SIZE); ++ ++ relocation = (plt_index * GOT_ENTRY_SIZE ++ + s390_gotplt_offset (info)); + } ++ if (r_type == R_390_GOTPLTENT) ++ relocation += s390_got_pointer (info); + unresolved_reloc = FALSE; + break; + } +@@ -2286,7 +2296,7 @@ elf_s390_relocate_section (bfd *output_b + case R_390_GOTENT: + /* Relocation is to the entry for this symbol in the global + offset table. */ +- if (base_got == NULL) ++ if (htab->elf.sgot == NULL) + abort (); + + if (h != NULL) +@@ -2303,8 +2313,19 @@ elf_s390_relocate_section (bfd *output_b + { + /* No explicit GOT usage so redirect to the + got.iplt slot. */ +- base_got = htab->elf.igotplt; +- off = h->plt.offset / PLT_ENTRY_SIZE * GOT_ENTRY_SIZE; ++ relocation = (s390_gotplt_offset (info) ++ + htab->elf.igotplt->output_offset ++ + (h->plt.offset / PLT_ENTRY_SIZE ++ * GOT_ENTRY_SIZE)); ++ ++ /* For @GOTENT the relocation is against the offset between ++ the instruction and the symbols entry in the GOT and not ++ between the start of the GOT and the symbols entry. We ++ add the vma of the GOT to get the correct value. */ ++ if (r_type == R_390_GOTENT || r_type == R_390_GOTPLTENT) ++ relocation += s390_got_pointer (info); ++ ++ break; + } + else + { +@@ -2337,7 +2358,7 @@ elf_s390_relocate_section (bfd *output_b + else + { + bfd_put_64 (output_bfd, relocation, +- base_got->contents + off); ++ htab->elf.sgot->contents + off); + h->got.offset |= 1; + } + +@@ -2419,7 +2440,7 @@ elf_s390_relocate_section (bfd *output_b + if (off >= (bfd_vma) -2) + abort (); + +- relocation = base_got->output_offset + off; ++ relocation = s390_got_offset (info) + off; + + /* For @GOTENT the relocation is against the offset between + the instruction and the symbols entry in the GOT and not +@@ -2427,7 +2448,7 @@ elf_s390_relocate_section (bfd *output_b + add the vma of the GOT to get the correct value. */ + if ( r_type == R_390_GOTENT + || r_type == R_390_GOTPLTENT) +- relocation += base_got->output_section->vma; ++ relocation += s390_got_pointer (info); + + break; + +@@ -2445,22 +2466,17 @@ elf_s390_relocate_section (bfd *output_b + relocation = (htab->elf.iplt->output_section->vma + + htab->elf.iplt->output_offset + + h->plt.offset +- - htab->elf.sgot->output_section->vma); ++ - s390_got_pointer (info)); + goto do_relocation; + } + +- /* Note that sgot->output_offset is not involved in this +- calculation. We always want the start of .got. If we +- defined _GLOBAL_OFFSET_TABLE in a different way, as is +- permitted by the ABI, we might have to change this +- calculation. */ +- relocation -= htab->elf.sgot->output_section->vma; ++ relocation -= s390_got_pointer (info); + break; + + case R_390_GOTPC: + case R_390_GOTPCDBL: + /* Use global offset table as symbol value. */ +- relocation = htab->elf.sgot->output_section->vma; ++ relocation = s390_got_pointer (info); + unresolved_reloc = FALSE; + break; + +@@ -2509,7 +2525,7 @@ elf_s390_relocate_section (bfd *output_b + || h->plt.offset == (bfd_vma) -1 + || (htab->elf.splt == NULL && !s390_is_ifunc_symbol_p (h))) + { +- relocation -= htab->elf.sgot->output_section->vma; ++ relocation -= s390_got_pointer (info); + break; + } + +@@ -2517,12 +2533,12 @@ elf_s390_relocate_section (bfd *output_b + relocation = (htab->elf.iplt->output_section->vma + + htab->elf.iplt->output_offset + + h->plt.offset +- - htab->elf.sgot->output_section->vma); ++ - s390_got_pointer (info)); + else + relocation = (htab->elf.splt->output_section->vma + + htab->elf.splt->output_offset + + h->plt.offset +- - htab->elf.sgot->output_section->vma); ++ - s390_got_pointer (info)); + unresolved_reloc = FALSE; + break; + +@@ -3296,7 +3312,7 @@ elf_s390_finish_dynamic_symbol (bfd *out + if (h->plt.offset != (bfd_vma) -1) + { + bfd_vma plt_index; +- bfd_vma got_offset; ++ bfd_vma gotplt_offset; + Elf_Internal_Rela rela; + bfd_byte *loc; + +@@ -3325,18 +3341,25 @@ elf_s390_finish_dynamic_symbol (bfd *out + Current offset - size first entry / entry size. */ + plt_index = (h->plt.offset - PLT_FIRST_ENTRY_SIZE) / PLT_ENTRY_SIZE; + +- /* Offset in GOT is PLT index plus GOT headers(3) times 8, +- addr & GOT addr. */ +- got_offset = (plt_index + 3) * GOT_ENTRY_SIZE; ++ /* The slots in the .got.plt correspond to the PLT slots in ++ the same order. */ ++ gotplt_offset = plt_index * GOT_ENTRY_SIZE; ++ ++ /* If .got.plt comes first it needs to contain the 3 header ++ entries. */ ++ if (!s390_gotplt_after_got_p (info)) ++ gotplt_offset += 3 * GOT_ENTRY_SIZE; + + /* Fill in the blueprint of a PLT. */ + memcpy (htab->elf.splt->contents + h->plt.offset, elf_s390x_plt_entry, + PLT_ENTRY_SIZE); + +- /* Fixup the relative address to the GOT entry */ ++ /* The first instruction in the PLT entry is a LARL loading ++ the address of the GOT slot. We write the 4 byte ++ immediate operand of the LARL instruction here. */ + bfd_put_32 (output_bfd, + (htab->elf.sgotplt->output_section->vma + +- htab->elf.sgotplt->output_offset + got_offset ++ htab->elf.sgotplt->output_offset + gotplt_offset + - (htab->elf.splt->output_section->vma + + htab->elf.splt->output_offset + + h->plt.offset))/2, +@@ -3356,12 +3379,12 @@ elf_s390_finish_dynamic_symbol (bfd *out + + htab->elf.splt->output_offset + + h->plt.offset + + 14), +- htab->elf.sgotplt->contents + got_offset); ++ htab->elf.sgotplt->contents + gotplt_offset); + + /* Fill in the entry in the .rela.plt section. */ + rela.r_offset = (htab->elf.sgotplt->output_section->vma + + htab->elf.sgotplt->output_offset +- + got_offset); ++ + gotplt_offset); + rela.r_info = ELF64_R_INFO (h->dynindx, R_390_JMP_SLOT); + rela.r_addend = 0; + loc = htab->elf.srelplt->contents + plt_index * +@@ -3568,8 +3591,8 @@ elf_s390_finish_dynamic_sections (bfd *o + continue; + + case DT_PLTGOT: +- s = htab->elf.sgotplt; +- dyn.d_un.d_ptr = s->output_section->vma + s->output_offset; ++ /* DT_PLTGOT matches _GLOBAL_OFFSET_TABLE_ */ ++ dyn.d_un.d_ptr = s390_got_pointer (info); + break; + + case DT_JMPREL: +@@ -3606,10 +3629,11 @@ elf_s390_finish_dynamic_sections (bfd *o + /* fill in blueprint for plt 0 entry */ + memcpy (htab->elf.splt->contents, elf_s390x_first_plt_entry, + PLT_FIRST_ENTRY_SIZE); +- /* Fixup relative address to start of GOT */ ++ /* The second instruction in the first PLT entry is a LARL ++ loading the GOT pointer. Fill in the LARL immediate ++ address. */ + bfd_put_32 (output_bfd, +- (htab->elf.sgotplt->output_section->vma +- + htab->elf.sgotplt->output_offset ++ (s390_got_pointer (info) + - htab->elf.splt->output_section->vma + - htab->elf.splt->output_offset - 6)/2, + htab->elf.splt->contents + 8); +@@ -3619,21 +3643,22 @@ elf_s390_finish_dynamic_sections (bfd *o + = PLT_ENTRY_SIZE; + } + +- if (htab->elf.sgotplt) ++ if (htab->elf.hgot && htab->elf.hgot->root.u.def.section) + { + /* Fill in the first three entries in the global offset table. */ +- if (htab->elf.sgotplt->size > 0) ++ if (htab->elf.hgot->root.u.def.section->size > 0) + { + bfd_put_64 (output_bfd, + (sdyn == NULL ? (bfd_vma) 0 + : sdyn->output_section->vma + sdyn->output_offset), +- htab->elf.sgotplt->contents); ++ htab->elf.hgot->root.u.def.section->contents); + /* One entry for shared object struct ptr. */ +- bfd_put_64 (output_bfd, (bfd_vma) 0, htab->elf.sgotplt->contents + 8); ++ bfd_put_64 (output_bfd, (bfd_vma) 0, ++ htab->elf.hgot->root.u.def.section->contents + 8); + /* One entry for _dl_runtime_resolve. */ +- bfd_put_64 (output_bfd, (bfd_vma) 0, htab->elf.sgotplt->contents + 16); ++ bfd_put_64 (output_bfd, (bfd_vma) 0, ++ htab->elf.hgot->root.u.def.section->contents + 16); + } +- + elf_section_data (htab->elf.sgot->output_section) + ->this_hdr.sh_entsize = 8; + } +Index: binutils-2.31/ld/emulparams/elf64_s390.sh +=================================================================== +--- binutils-2.31.orig/ld/emulparams/elf64_s390.sh 2018-06-24 20:38:57.000000000 +0200 ++++ binutils-2.31/ld/emulparams/elf64_s390.sh 2019-01-24 15:07:25.000000000 +0100 +@@ -11,9 +11,12 @@ NOP=0x07070707 + TEMPLATE_NAME=elf32 + GENERATE_SHLIB_SCRIPT=yes + GENERATE_PIE_SCRIPT=yes ++GENERATE_RELRO_SCRIPT=yes + NO_SMALL_DATA=yes + EXTRA_EM_FILE=s390 + IREL_IN_PLT= ++SEPARATE_GOTPLT=0 ++test -z "$RELRO" && unset SEPARATE_GOTPLT + + # Treat a host that matches the target with the possible exception of "x" + # in the name as if it were native. +Index: binutils-2.31/ld/testsuite/ld-s390/gotreloc_64-1.dd +=================================================================== +--- binutils-2.31.orig/ld/testsuite/ld-s390/gotreloc_64-1.dd 2018-06-24 20:38:58.000000000 +0200 ++++ /dev/null 1970-01-01 00:00:00.000000000 +0000 +@@ -1,12 +0,0 @@ +-tmpdir/gotreloc_64-1: file format elf64-s390 +- +-Disassembly of section .text: +- +-.* : +-.*: c0 10 00 00 00 0e [ ]*larl %r1,.* +-.*: c0 10 00 00 00 0b [ ]*larl %r1,.* +-.*: c4 1d 00 00 08 86 [ ]*lrl %r1,.* <_GLOBAL_OFFSET_TABLE_\+0x18> +-.*: 58 10 c0 18 [ ]*l %r1,24\(%r12\) +-.*: e3 10 c0 18 00 58 [ ]*ly %r1,24\(%r12\) +-.* : +-.*: 00 00 01 23 .long 0x00000123 +Index: binutils-2.31/ld/testsuite/ld-s390/gotreloc_64-norelro-1.dd +=================================================================== +--- /dev/null 1970-01-01 00:00:00.000000000 +0000 ++++ binutils-2.31/ld/testsuite/ld-s390/gotreloc_64-norelro-1.dd 2019-01-24 15:07:25.000000000 +0100 +@@ -0,0 +1,12 @@ ++tmpdir/gotreloc_64-1: file format elf64-s390 ++ ++Disassembly of section .text: ++ ++.* : ++.*: c0 10 00 00 00 0e [ ]*larl %r1,.* ++.*: c0 10 00 00 00 0b [ ]*larl %r1,.* ++.*: c4 1d 00 00 08 86 [ ]*lrl %r1,.* <_GLOBAL_OFFSET_TABLE_\+0x18> ++.*: 58 10 c0 18 [ ]*l %r1,24\(%r12\) ++.*: e3 10 c0 18 00 58 [ ]*ly %r1,24\(%r12\) ++.* : ++.*: 00 00 01 23 .long 0x00000123 +Index: binutils-2.31/ld/testsuite/ld-s390/gotreloc_64-relro-1.dd +=================================================================== +--- /dev/null 1970-01-01 00:00:00.000000000 +0000 ++++ binutils-2.31/ld/testsuite/ld-s390/gotreloc_64-relro-1.dd 2019-01-24 15:07:25.000000000 +0100 +@@ -0,0 +1,12 @@ ++tmpdir/gotreloc_64-1: file format elf64-s390 ++ ++Disassembly of section .text: ++ ++.* : ++.*: c0 10 00 00 00 0e [ ]*larl %r1,.* ++.*: c0 10 00 00 00 0b [ ]*larl %r1,.* ++.*: c4 1d 00 00 0f 1a [ ]*lrl %r1,.* <_GLOBAL_OFFSET_TABLE_\+0x18> ++.*: 58 10 c0 18 [ ]*l %r1,24\(%r12\) ++.*: e3 10 c0 18 00 58 [ ]*ly %r1,24\(%r12\) ++.* : ++.*: 00 00 01 23 .long 0x00000123 +Index: binutils-2.31/ld/testsuite/ld-s390/s390.exp +=================================================================== +--- binutils-2.31.orig/ld/testsuite/ld-s390/s390.exp 2018-06-24 20:38:58.000000000 +0200 ++++ binutils-2.31/ld/testsuite/ld-s390/s390.exp 2019-01-24 15:07:25.000000000 +0100 +@@ -70,10 +70,15 @@ set s390xtests { + {{readelf -WSsrl tlsbin_64.rd} {objdump -dzrj.text tlsbin_64.dd} + {objdump -sj.got tlsbin_64.sd} {objdump -sj.tdata tlsbin_64.td}} + "tlsbin_64"} +- {"GOT: symbol address load from got to larl" +- "-shared -melf64_s390 --hash-style=sysv --version-script=gotreloc-1.ver" "" ++ {"GOT: norelro symbol address load from got to larl" ++ "-shared -melf64_s390 -z norelro --hash-style=sysv --version-script=gotreloc-1.ver" "" + "-m64" {gotreloc-1.s} +- {{objdump -dzrj.text gotreloc_64-1.dd}} ++ {{objdump -dzrj.text gotreloc_64-norelro-1.dd}} ++ "gotreloc_64-1"} ++ {"GOT: relro symbol address load from got to larl" ++ "-shared -melf64_s390 -z relro --hash-style=sysv --version-script=gotreloc-1.ver" "" ++ "-m64" {gotreloc-1.s} ++ {{objdump -dzrj.text gotreloc_64-relro-1.dd}} + "gotreloc_64-1"} + {"PLT: offset test" + "-shared -m elf64_s390 -dT pltoffset-1.ld" "" +Index: binutils-2.31/ld/emultempl/elf32.em +=================================================================== +--- binutils-2.31.orig/ld/emultempl/elf32.em 2019-01-24 15:07:25.000000000 +0100 ++++ binutils-2.31/ld/emultempl/elf32.em 2019-01-24 15:07:25.000000000 +0100 +@@ -2461,17 +2461,41 @@ echo ' && link_info.combrelo + echo ' && link_info.relro' >> e${EMULATION_NAME}.c + echo ' && (link_info.flags & DF_BIND_NOW)) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xdw >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xdceo >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c + echo ' && link_info.combreloc) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xdce >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xdco >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.combreloc) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xdc >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xdeo >> e${EMULATION_NAME}.c ++fi + fi + echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.separate_code) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xde >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_pie (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xdo >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_pie (&link_info)) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xd >> e${EMULATION_NAME}.c + fi +@@ -2487,17 +2511,41 @@ echo ' && link_info.combrelo + echo ' && link_info.relro' >> e${EMULATION_NAME}.c + echo ' && (link_info.flags & DF_BIND_NOW)) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xsw >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xsceo >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.combreloc' >> e${EMULATION_NAME}.c + echo ' && link_info.separate_code) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xsce >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xsco >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.combreloc) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xsc >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xseo >> e${EMULATION_NAME}.c ++fi + fi + echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c + echo ' && link_info.separate_code) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xse >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (bfd_link_dll (&link_info)' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xso >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (bfd_link_dll (&link_info)) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xs >> e${EMULATION_NAME}.c + fi +@@ -2510,14 +2558,34 @@ echo ' ; else if (link_info.combreloc' + echo ' && link_info.relro' >> e${EMULATION_NAME}.c + echo ' && (link_info.flags & DF_BIND_NOW)) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xw >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xceo >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (link_info.combreloc' >> e${EMULATION_NAME}.c + echo ' && link_info.separate_code) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xce >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (link_info.combreloc' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xco >> e${EMULATION_NAME}.c ++fi + echo ' ; else if (link_info.combreloc) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xc >> e${EMULATION_NAME}.c + fi +-echo ' ; else if (link_info.separate_code) return' >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (link_info.separate_code' >> e${EMULATION_NAME}.c ++echo ' && link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xeo >> e${EMULATION_NAME}.c ++fi ++echo ' ; else if (link_info.separate_code) return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.xe >> e${EMULATION_NAME}.c ++if test -n "$GENERATE_RELRO_SCRIPT" ; then ++echo ' ; else if (link_info.relro) return' >> e${EMULATION_NAME}.c ++sed $sc ldscripts/${EMULATION_NAME}.xo >> e${EMULATION_NAME}.c ++fi + echo ' ; else return' >> e${EMULATION_NAME}.c + sed $sc ldscripts/${EMULATION_NAME}.x >> e${EMULATION_NAME}.c + echo '; }' >> e${EMULATION_NAME}.c +@@ -2556,6 +2624,21 @@ fragment < ldscripts/${EMULATION_NAME}.xe + ++if test -n "$GENERATE_RELRO_SCRIPT"; then ++ LD_FLAG= ++ RELRO=" " ++ ( echo "/* Script for -z relo: generate normal executables with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xo ++ LD_FLAG=textonly ++ ( echo "/* Script for -z separate-code -z relo: generate normal executables with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xeo ++ unset RELRO ++fi + LD_FLAG=n + DATA_ALIGNMENT=${DATA_ALIGNMENT_n} + ( echo "/* Script for -n: mix text and data on same page */" +@@ -353,6 +398,25 @@ if test -n "$GENERATE_COMBRELOC_SCRIPT"; + rm -f ${COMBRELOC} + COMBRELOC= + unset RELRO_NOW ++ if test -n "$GENERATE_RELRO_SCRIPT"; then ++ LD_FLAG=c ++ RELRO=" " ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xco.tmp ++ ( echo "/* Script for -z combreloc -z relro: combine and sort reloc sections */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xco ++ rm -f ${COMBRELOC} ++ LD_FLAG=ctextonly ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xceo.tmp ++ ( echo "/* Script for -z combreloc -z separate-code -z relro: combine and sort reloc sections */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xceo ++ rm -f ${COMBRELOC} ++ COMBRELOC= ++ unset RELRO ++ fi + fi + + if test -n "$GENERATE_SHLIB_SCRIPT"; then +@@ -370,6 +434,23 @@ if test -n "$GENERATE_SHLIB_SCRIPT"; the + . ${CUSTOMIZER_SCRIPT} + . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc + ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xse ++ ++ if test -n "$GENERATE_RELRO_SCRIPT"; then ++ RELRO=" " ++ LD_FLAG=shared ++ ( ++ echo "/* Script for ld --shared -z relro: link shared library */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xso ++ LD_FLAG=sharedtextonly ++ ( ++ echo "/* Script for ld --shared -z relro -z separate-code: link shared library with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xseo ++ unset RELRO ++ fi + if test -n "$GENERATE_COMBRELOC_SCRIPT"; then + DATA_ALIGNMENT=${DATA_ALIGNMENT_sc-${DATA_ALIGNMENT}} + LD_FLAG=cshared +@@ -401,8 +482,27 @@ if test -n "$GENERATE_SHLIB_SCRIPT"; the + . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc + ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xswe + rm -f ${COMBRELOC} +- COMBRELOC= + unset RELRO_NOW ++ ++ if test -n "$GENERATE_RELRO_SCRIPT"; then ++ LD_FLAG=wshared ++ RELRO=" " ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xsco.tmp ++ ( echo "/* Script for --shared -z combreloc -z relro: shared library, combine & sort relocs with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xsco ++ rm -f ${COMBRELOC} ++ LD_FLAG=wsharedtextonly ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xsceo.tmp ++ ( echo "/* Script for --shared -z combreloc -z relro -z separate-code: shared library, combine & sort relocs with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xsceo ++ rm -f ${COMBRELOC} ++ unset RELRO ++ fi ++ COMBRELOC= + fi + unset CREATE_SHLIB + fi +@@ -422,6 +522,22 @@ if test -n "$GENERATE_PIE_SCRIPT"; then + . ${CUSTOMIZER_SCRIPT} + . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc + ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xde ++ if test -n "$GENERATE_RELRO_SCRIPT"; then ++ RELRO=" " ++ LD_FLAG=pie ++ ( ++ echo "/* Script for ld -pie -z relro: link position independent executable */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdo ++ LD_FLAG=pietextonly ++ ( ++ echo "/* Script for ld -pie -z relro -z separate-code: link position independent executable with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdeo ++ unset RELRO ++ fi + if test -n "$GENERATE_COMBRELOC_SCRIPT"; then + DATA_ALIGNMENT=${DATA_ALIGNMENT_sc-${DATA_ALIGNMENT}} + COMBRELOC=ldscripts/${EMULATION_NAME}.xdc.tmp +@@ -453,8 +569,28 @@ if test -n "$GENERATE_PIE_SCRIPT"; then + . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc + ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdwe + rm -f ${COMBRELOC} +- COMBRELOC= + unset RELRO_NOW ++ ++ if test -n "$GENERATE_RELRO_SCRIPT"; then ++ LD_FLAG=wpie ++ RELRO=" " ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xdco.tmp ++ ( echo "/* Script for -pie -z combreloc -z relro: position independent executable, combine & sort relocs with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdco ++ rm -f ${COMBRELOC} ++ LD_FLAG=wpietextonly ++ COMBRELOC=ldscripts/${EMULATION_NAME}.xdceo.tmp ++ ( echo "/* Script for -pie -z combreloc -z relro -z separate-code: position independent executable, combine & sort relocs with separate code segment */" ++ . ${CUSTOMIZER_SCRIPT} ++ . ${srcdir}/scripttempl/${SCRIPT_NAME}.sc ++ ) | sed -e '/^ *$/d;s/[ ]*$//' > ldscripts/${EMULATION_NAME}.xdceo ++ rm -f ${COMBRELOC} ++ ++ unset RELRO ++ fi ++ COMBRELOC= + fi + unset CREATE_PIE + fi