ld/testsuite/ld-loongarch-elf
* ld-loongarch-elf.exp: Test LoongArch32 and LoongArch64 testcases respectively.
* jmp_op.d: Fix bug in test LoongArch32.
* disas-jirl-32.d: New test case for LoongArch32.
* disas-jirl-32.s: New test case for LoongArch32.
* disas-jirl.d: Skip test case LoongArch32.
* macro_op_32.d: New test case for LoongArch32.
* macro_op_32.s: New test case for LoongArch32.
* macro_op.d: Skip test case LoongArch32.
The extended instructions implemented in powerpc_macros aren't used by
the disassembler. That means instructions like "sldi r3,r3,2" appear
in disassembly as "rldicr r3,r3,2,61", which is annoying since many
other extended instructions are shown.
Note that some of the instructions moved out of the macro table to the
opcode table won't appear in disassembly, because they are aliases
rather than a subset of the underlying raw instruction. If enabled,
rotrdi, extrdi, extldi, clrlsldi, and insrdi would replace all
occurrences of rotldi, rldicl, rldicr, rldic and rldimi. (Or many
occurrences in the case of clrlsldi if n <= b was added to the extract
functions.)
The patch also fixes a small bug in opcode sanity checking.
include/
* opcode/ppc.h (PPC_OPSHIFT_SH6): Define.
opcodes/
* ppc-opc.c (insert_erdn, extract_erdn, insert_eldn, extract_eldn),
(insert_crdn, extract_crdn, insert_rrdn, extract_rrdn),
(insert_sldn, extract_sldn, insert_srdn, extract_srdn),
(insert_erdb, extract_erdb, insert_csldn, extract_csldb),
(insert_irdb, extract_irdn): New functions.
(ELDn, ERDn, ERDn, RRDn, SRDn, ERDb, CSLDn, CSLDb, IRDn, IRDb):
Define and add associated powerpc_operands entries.
(powerpc_opcodes): Add "rotrdi", "srdi", "extrdi", "clrrdi",
"sldi", "extldi", "clrlsldi", "insrdi" and corresponding record
(ie. dot suffix) forms.
(powerpc_macros): Delete same from here.
gas/
* config/tc-ppc.c (insn_validate): Don't modify value passed
to operand->insert for PPC_OPERAND_PLUS1 when calculating mask.
Handle PPC_OPSHIFT_SH6.
* testsuite/gas/ppc/prefix-reloc.d: Update.
* testsuite/gas/ppc/simpshft.d: Update.
ld/
* testsuite/ld-powerpc/elfv2so.d: Update.
* testsuite/ld-powerpc/notoc.d: Update.
* testsuite/ld-powerpc/notoc3.d: Update.
* testsuite/ld-powerpc/tlsdesc2.d: Update.
* testsuite/ld-powerpc/tlsget.d: Update.
* testsuite/ld-powerpc/tlsget2.d: Update.
* testsuite/ld-powerpc/tlsopt5.d: Update.
* testsuite/ld-powerpc/tlsopt6.d: Update.
Don't change indirect symbol defined in IR to undefined if it is
referenced from shared object.
bfd/
PR ld/28879
* elflink.c (_bfd_elf_merge_symbol): Don't change indirect
symbol defined in IR to undefined if it is referenced from
shared object.
ld/
PR ld/28879
* testsuite/ld-plugin/lto.exp: Run PR ld/28879 tests.
* testsuite/ld-plugin/pr28879a.cc: New file.
* testsuite/ld-plugin/pr28879b.cc: Likewise.
The better to see any code that accesses expld.dataseg.
* ldexp.c (fold_segment_end): Remove seg parameter. Adjust calls.
(fold_segment_align, fold_segment_relro_end): Likewise.
* ldlang.c (lang_size_segment): Likewise.
(lang_size_relro_segment_1, lang_find_relro_sections_1): Likewise.
Now that ld properly aligns the end of the relro segment, the hack to
make relro work on powerpc can disappear.
bfd/
* bfd.c (bfd_emul_get_commonpagesize): Remove relro param.
Don't return bed->relropagesize.
* elf-bfd.h (struct elf_backend_data): Remove relropagesize.
* elfxx-target.h (ELF_RELROPAGESIZE): Remove.
* elf32-ppc.c (ELF_RELROPAGESIZE): Don't define.
* elf64-ppc.c: Likewise.
* bfd-in2.h: Regenerate.
ld/
* ldemul.c (after_parse_default): Adjust
bfd_emul_get_commonpagesize call.
x86 treats MAXPAGESIZE as a memory optimisation parameter, actual
hardware paging is always COMMPAGESIZE of 4k. Use COMMONPAGESIZE for
the end of the relro segment alignment.
The previous patch regresses pr18176, increasing the testcase file
size from 322208 to 2099872 bytes. Fixing this on x86 will require
introducing a gap after the end of the relro segment (of up to
relropagesize-1 bytes).
PR 28824
PR 18176
* ld.h (ld_config_type): Add relro_use_commonpagesize field.
* ldexp.c (fold_segment_align): Set relropagesize depending on
relro_use_commonpagesize.
* emultempl/elf-x86.em (elf_x86_create_output_section_statements):
Set relro_use_commonpagesize.
* testsuite/ld-x86-64/pr18176.d: xfail.
Background
==========
There are constraints on layout of binaries to meet demand paging and
memory protection requirements. Demand paged binaries must have file
offset mod pagesize equal to vma mod pagesize. Memory protection
(executable, read, write status) can only change at page boundaries.
The linker's MAXPAGESIZE variable gives the page size for these layout
constraints.
In a typical basic executable with two memory segments, text (RE) and
data (RW), the data segment must start on a different page to the
last text segment page. For example, with 64k pages and a small
executable of 48k text and 1k data, the text segment might start at
address 0x10000 and data at 0x20000 for a total of two 64k memory
pages. Demand paging would require the image on disk to be 64k+1k
in size. We can do better than that. If the data segment instead
starts at 0x2c000 (the end of the text segment plus one 64k page) then
there are still only two memory pages, but the disk image is now
smaller, 48k+1k in size. This is why the linker normally starts the
data segment at the end of the text segment plus one page. That
simple heuristic isn't ideal in all cases. Changing our simple
example to one with 64k-1 text size, following that heuristic would
result in data starting at 0x2ffff. Now we have two 64k memory data
pages for a data segment of 1k! If the data segment instead started
at 0x30000 we'd get a single data segment page at the cost of 1 byte
extra in the disk image, which is likely a good trade-off. So the
linker does adjust the simple heuristic. Just how much disk image
size increase is allowed is controlled by the linker's COMMONPAGESIZE
variable.
A PT_GNU_RELRO segment overlays the initial part of the data segment,
saying that those pages should be made read-only after relocation by
the dynamic loader. Page granularity for memory protection means that
the end of the relro segment must be at a page boundary.
The problem
===========
Unfortunately most targets currently only align the end of the relro
segment to COMMONPAGESIZE. That results in only partial relro
protection if an executable is running with MAXPAGESIZE pages, since
any part of the relro segment past the last MAXPAGESIZE boundary can't
be made read-only without also affecting sections past the end of the
relro segment. I believe this problem arose because x86 always runs
with 4k (COMMPAGESIZE) memory pages, and therefore using a larger
MAXPAGESIZE on x86 is for reasons other than the demand paging and
memory page protection boundary requirements.
The solution
============
Always end the relro segment on a MAXPAGESIZE boundary, except for
x86. Note that the relro segment, comprising of sections at the start
of the data segment, is sized according to how those sections are laid
out. That means the start of the relro segment is fixed relative to
its end. Which also means the start of the data segment must be at a
fixed address mod MAXPAGESIZE. So for relro the linker can't play
games with the start of the data segment to save disk space. At
least, not without introducing gaps between the relro sections. In
fact, because the linker was starting layout using its simple
heuristic of starting the data segment at the end of the text segment
plus one page, it was sometimes introducing page gaps for no reason.
See pr28743.
PR 28824
PR 28734
* ldexp.c (fold_segment_align): When relro, don't adjust up by
offset within page. Set relropagesize.
(fold_segment_relro_end): Align to relropagesize.
* ldexp.h (seg_align_type): Rename pagesize to commonpagesize.
Add relropagesize. Comment.
* ldlang.c (lang_size_segment): Adjust to suit field renaming.
(lang_size_relro_segment_1): Align relro_end using relropagesize.
I am checking this into master and will backport it to 2.38 branch.
H.J
----
On x86, GCC 12 supports -mno-direct-extern-access to enable canonical
reference to protected function and disable copy relocation. With
-mno-direct-extern-access, the canonical protected function symbols must
be accessed via canonical reference and the protected data symbols in
shared libraries are non-copyable. Under glibc 2.35, non-canonical
reference to the canonical protected function will get the run-time error:
./y: internal_f: ./libfoo.so: non-canonical reference to canonical protected function
and copy relocations against the non-copyable protected symbols will get
the run-time error:
./x: internal_i: ./libfoo.so: copy relocation against non-copyable protected symbol
Update x86 linker to disallow non-canonical reference to the canonical
protected function:
ld: plt.o: non-canonical reference to canonical protected function `internal_f' in libfoo.so
ld: failed to set dynamic section sizes: bad value
and copy relocation against the non-copyable protected symbol:
ld: main.o: copy relocation against non-copyable protected symbol `internal_i' in libfoo.so
at link-time.
bfd/
PR ld/28875
* elf-properties.c (_bfd_elf_parse_gnu_properties): Don't skip
shared libraries for GNU_PROPERTY_1_NEEDED_INDIRECT_EXTERN_ACCESS.
* elf32-i386.c (elf_i386_scan_relocs): Disallow non-canonical
reference to canonical protected function.
* elf64-x86-64.c (elf_x86_64_scan_relocs): Likewise.
* elfxx-x86.c (elf_x86_allocate_dynrelocs): Don't allow copy
relocation against non-copyable protected symbol.
ld/
PR ld/28875
* testsuite/ld-i386/i386.exp: Check non-canonical reference to
canonical protected function and check copy relocation against
non-copyable protected symbol.
* testsuite/ld-i386/pr21997-1.err: New file.
* testsuite/ld-i386/pr28875.err: Likewise.
* testsuite/ld-i386/pr28875a.c: Likewise.
* testsuite/ld-i386/pr28875b.c: Likewise.
* testsuite/ld-x86-64/pr21997-1a.err: Updated.
* testsuite/ld-x86-64/pr21997-1b.err: Likewise.
* testsuite/ld-x86-64/pr28875-data.err: New file.
* testsuite/ld-x86-64/pr28875-func.err: Likewise.
* testsuite/ld-x86-64/x86-64.exp: Check non-canonical reference
to canonical protected function and check copy relocation against
non-copyable protected symbol.
The extension version checking logic is really just too complicated to
encode into the linker, trying to do so causes more harm than good.
This removes the checks and the associated tests, leaving the logic to
keep the largest version of each extension linked into the target.
bfd/
* elfnn-riscv.c (riscv_version_mismatch): Rename to
riscv_update_subset_version, and stop reporting warnings on
version mismatches.
(riscv_merge_std_ext): Adjust calls to riscv_version_mismatch.
(riscv_merge_multi_letter_ext): Likewise.
ld/
* testsuite/ld-riscv-elf/attr-merge-arch-failed-01.d: Remove
* testsuite/ld-riscv-elf/attr-merge-arch-failed-01a.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-01b.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-02.d: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-02a.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-02b.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-02c.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-arch-failed-02d.s: Likewise
* testsuite/ld-riscv-elf/attr-merge-user-ext-01.d: New test.
* testsuite/ld-riscv-elf/attr-merge-user-ext-rv32i21_m2p0.s:
Likewise.
* testsuite/ld-riscv-elf/attr-merge-user-ext-rv32i21_m2p1.s:
Likewise.
* testsuite/ld-riscv-elf/ld-riscv-elf.exp: Remove obselete
attr-merge-arch-failed-{01,02}, replace with
attr-merge-user-ext-01.
Signed-off-by: Palmer Dabbelt <palmer@rivosinc.com>
GOT32 relocations are allowed since absolute value + addend is stored in
the GOT slot.
Tested on glibc 2.35 build with GCC 11.2 and -Os.
bfd/
PR ld/28870
* elfxx-x86.c (_bfd_elf_x86_valid_reloc_p): Also allow GOT32
relocations.
ld/
PR ld/28870
* testsuite/ld-i386/i386.exp: Run pr28870.
* testsuite/ld-i386/pr28870.d: New file.
* testsuite/ld-i386/pr28870.s: Likewise.
This testcase triggers a stub sizing error with the patches applied
for PR28743 (commit 2f83249c13 and c804c6f98d).
PR 28827
* testsuite/ld-powerpc/pr28827-1.s,
* testsuite/ld-powerpc/pr28827-1.d: New test.
* testsuite/ld-powerpc/powerpc.exp: Run it.
Remove emultempl/armcoff.em which has been unused after
commit 2ac93be706
Author: Alan Modra <amodra@gmail.com>
Date: Mon Apr 16 20:33:36 2018 +0930
Remove arm-aout and arm-coff support
This also removes arm-netbsd (not arm-netbsdelf!), arm-openbsd, and
arm-riscix. Those targets weren't on the obsolete list but they are
all aout, and it doesn't make all that much sense to remove arm-aout
without removing them too.
* emultempl/armcoff.em: Removed.
Supporting -static-pie on PowerPC64 requires the linker to properly
treat SHN_ABS symbols for cases like glibc's _nl_current_LC_CTYPE_used
absolute symbol. I've been slow to fix the linker on powerpc because
there is some chance that this will break some shared libraries or
PIEs.
bfd/
* elf64-ppc.c (ppc64_elf_check_relocs): Consolidate local sym
handling code. Don't count dyn relocs against non-dynamic
absolute symbols.
(dec_dynrel_count): Adjust to suit.
(ppc64_elf_edit_toc): Don't remove entries for absolute symbols
when pic.
(allocate_got): Don't allocate space for got relocs against
non-dynamic absolute syms.
(ppc64_elf_layout_multitoc): Likewise.
(got_and_plt_relr): Likewise.
(ppc64_elf_size_dynamic_sections): Likewise for local got.
(got_and_plt_relr_for_local_syms): Likewise.
(ppc64_elf_size_stubs): Don't allocate space for relr either.
(ppc64_elf_relocate_section): Don't write relocs against non-dynamic
absolute symbols. Don't optimise got and toc code sequences
loading absolute symbol entries.
ld/
* testsuite/ld-powerpc/abs-reloc.s,
* testsuite/ld-powerpc/abs-static.d,
* testsuite/ld-powerpc/abs-static.r,
* testsuite/ld-powerpc/abs-pie.d,
* testsuite/ld-powerpc/abs-pie.r,
* testsuite/ld-powerpc/abs-shared.d,
* testsuite/ld-powerpc/abs-shared.r,
* testsuite/ld-powerpc/abs-pie-relr.d,
* testsuite/ld-powerpc/abs-pie-relr.r,
* testsuite/ld-powerpc/abs-shared-relr.d,
* testsuite/ld-powerpc/abs-shared-relr.r: New tests.
* testsuite/ld-powerpc/powerpc.exp: Run them.
VER_FLG_WEAK doesn't indicate that all symbol references of the symbol
version have STB_WEAK. VER_FLG_WEAK indicates a weak symbol version
definition with no symbols associated with it. It is used to verify
the existence of a particular implementation without any symbol references
to the weak symbol version.
PR ld/24718
* testsuite/ld-elf/pr24718-1.d: New file.
* testsuite/ld-elf/pr24718-1.s: Likewise.
* testsuite/ld-elf/pr24718-1.t: Likewise.
In trying to find a testcase for PR28827, I managed to hit a linker
error in bfd_set_section_contents with a .branch_lt input section
being too large for the output .branch_lt.
bfd/
PR 28827
* elf64-ppc.c (ppc64_elf_size_stubs): Set section size to
maxsize past STUB_SHRINK_ITER before laying out. Remove now
unnecessary conditional setting of maxsize at start of loop.
ld/
* testsuite/ld-powerpc/pr28827-2.d,
* testsuite/ld-powerpc/pr28827-2.lnk,
* testsuite/ld-powerpc/pr28827-2.s: New test.
* testsuite/ld-powerpc/powerpc.exp: Run it.
This is just a tidy, making the __ehdr_start symbol flag tweaks all in
one place.
* ldelf.c (ldelf_before_allocation): Don't set rel_from_abs
for __ehdr_start.
* ldlang.c (lang_symbol_tweaks): Set it here instead.
Using a symbol other than .TOC. with @tocbase is an extension to the
ABI. It is never valid to use a symbol without a definition in the
binary, and symbols on these expressions cannot be overridden. Make
this explicit by using ".hidden" in the testcase.
* testsuite/ld-powerpc/symtocbase-1.s: Align data. Make function
entry symbol hidden.
* testsuite/ld-powerpc/symtocbase-2.s: Likewise.
* testsuite/ld-powerpc/symtocbase.d: Adjust expected output.
1. Compute the desired PT_GNU_RELRO segment base and find the maximum
section alignment of sections starting from the PT_GNU_RELRO segment.
2. Find the first preceding load section.
3. Don't add the 1-page gap between the first preceding load section and
the relro segment if the maximum page size >= the maximum section
alignment. Align the PT_GNU_RELRO segment first. Subtract the maximum
page size if therer is still a 1-page gap.
PR ld/28743
PR ld/28819
* ldlang.c (lang_size_relro_segment_1): Rewrite.
* testsuite/ld-x86-64/pr28743-1.d: New file.
* testsuite/ld-x86-64/pr28743-1.s: Likewise.
* testsuite/ld-x86-64/x86-64.exp: Run pr28743-1.
PowerPC64 takes a more traditional approach to DT_RELR than x86. Count
relative relocs in check_relocs, allocate space for them and output in
the usual places but not doing so when enable_dt_relr. DT_RELR is
sized in the existing ppc stub relaxation machinery, run via the
linker's ldemul_after_allocation hook. DT_RELR is output in the same
function that writes ppc stubs, run via ldemul_finish.
This support should be considered experimental.
bfd/
* elf64-ppc.c (struct ppc_local_dyn_relocs): Renamed from
ppc_dyn_relocs. Add rel_count field. Update uses.
(struct ppc_dyn_relocs): New. Replace all uses of elf_dyn_relocs.
(struct ppc_link_hash_table): Add relr_alloc, relr_count and
relr_addr.
(ppc64_elf_copy_indirect_symbol): Merge rel_count.
(ppc64_elf_check_relocs): Init rel_count for global and local syms.
(dec_dynrel_count): Change r_info param to reloc pointer. Update
all callers. Handle decrementing rel_count.
(allocate_got): Don't allocate space for relative relocs when
enable_dt_relr.
(allocate_dynrelocs): Likewise.
(ppc64_elf_size_dynamic_sections): Likewise. Handle srelrdyn.
(ppc_build_one_stub): Don't emit relative relocs on .branch_lt.
(compare_relr_address, append_relr_off): New functions.
(got_and_plt_relr_for_local_syms, got_and_plt_relr): Likewise.
(ppc64_elf_size_stubs): Size .relr.syn.
(ppc64_elf_build_stubs): Emit .relr.dyn.
(build_global_entry_stubs_and_plt): Don't output relative relocs
when enable_dt_relr.
(write_plt_relocs_for_local_syms): Likewise.
(ppc64_elf_relocate_section): Likewise.
binutils/
* testsuite/lib/binutils-common.exp (supports_dt_relr): Add
powerpc64.
ld/
* emulparams/elf64ppc.sh: Source dt-relr.sh.
* testsuite/ld-elf/dt-relr-2b.d: Adjust for powerpc.
* testsuite/ld-elf/dt-relr-2c.d: Likewise.
* testsuite/ld-elf/dt-relr-2d.d: Likewise.
* testsuite/ld-elf/dt-relr-2e.d: Likewise.
bfd/
* elf-bfd.h (UNDEFWEAK_NO_DYNAMIC_RELOC): Test linker_def.
ld/
* ldelf.c (ldelf_before_allocation): Don't force __ehdr_start
local and hidden here..
* ldlang.c (lang_symbol_tweaks): ..do so here instead and set
def_regular and linker_def for check_relocs. New function
extracted from lang_process.