I haven't figured out a small test case, but here's a real world problem: Get the Firefox/spidermonkey source from https://hg.mozilla.org/mozilla-central Create a build directory and run the following from under it: /path/to/mozilla-central/js/src/configure --enable-project=js --enable-fuzzing --enable-address-sanitizer --enable-linker=bfd CC=clang (note this also requires llvm-config, rustc, and cargo) Then run make -j<some-appropriate-number> The build fails with: BinSource.cpp:(.text.sancov.module_ctor[sancov.module_ctor]+0x4): undefined reference to `__start___sancov_cntrs' BinSource.cpp:(.text.sancov.module_ctor[sancov.module_ctor]+0xb): undefined reference to `__stop___sancov_cntrs' BinSource.cpp:(.text.sancov.module_ctor[sancov.module_ctor]+0x17): undefined reference to `__start___sancov_pcs' BinSource.cpp:(.text.sancov.module_ctor[sancov.module_ctor]+0x1e): undefined reference to `__stop___sancov_pcs' I bisected this to the following commit: commit 7dba9362c172f1073487536eb137feb2da30b0ff Author: Alan Modra <amodra@gmail.com> Date: Fri Jun 16 19:41:41 2017 +0930 Rewrite __start and __stop symbol handling This arranges for __start and __stop symbols to be defined before garbage collection, for all target formats. That should allow the COFF and PE --gc-sections to keep a singleton orphan input section, a feature lost by 2017-06-13 commit cbd0eecf26. The fancier ELF treatment of keeping all input sections associated with a __start or __stop symbol, from 2015-10-23 commit 1cce69b9dc, is retained. .startof. and .sizeof. symbols are deliberately not defined before garbage collection, so these won't affect garbage collection of sections. The patch also ensures __start, __stop, .startof. and .sizeof. symbols are defined before target size_dynamic_sections is called, albeit with a preliminary value, so that target code doesn't need to cope with a symbol changing from undefined at size_dynamic_sections to defined at relocate_section. Also, a number of problems with the testcases have been fixed.
It seems to be due to most __sancov_cntrs sections having the SHT_GROUP flag. This makes _bfd_elf_section_already_linked set the section's output_section to bfd_abs_section_ptr, which then fulfils the condition in undef_start_stop (bfs_abs_section_ptr->owner != link_info.output_bfd), which then marks the __start/__stop symbols as undefined.
(In reply to Mike Hommey from comment #1) > It seems to be due to most __sancov_cntrs sections having the SHT_GROUP flag. > This makes _bfd_elf_section_already_linked set the section's output_section > to bfd_abs_section_ptr, which then fulfils the condition in undef_start_stop > (bfs_abs_section_ptr->owner != link_info.output_bfd), which then marks the > __start/__stop symbols as undefined. From gABI: SHT_GROUP This section defines a section group. A section group is a set of sections that are related and that must be treated specially by the linker (see below for further details). Sections of type SHT_GROUP may appear only in relocatable objects (objects with the ELF header e_type member set to ET_REL). The section header table entry for a group section must appear in the section header table before the entries for any of the sections that are members of the group. How were __sancov_cntrs sections generated?
They are generate by clang from the combination of -fsanitize=address and -fsanitize=fuzzer-no-link. But using that with some dummy source file doesn't trigger the problem, so some subtle thing is happening. Also, correction: they have the SHF_GROUP flag. Only .group sections have the SHT_GROUP _type_.
It's worth noting that gold doesn't trip on the same object files (that is, chanfing the linker command line to include -fuse-ld=gold makes it work)
[hjl@gnu-cfl-1 pr23591]$ cat foo.S .section __sancov_cntrs,"aG",%progbits,foo1,comdat .long 0 .section .text,"axG",%progbits,foo1,comdat .globl foo1 .type foo1, @function foo1: .long 0 .section __sancov_cntrs,"aG",%progbits,foo2,comdat .long 1 .section .text,"axG",%progbits,foo2,comdat .globl foo2 .type foo2, @function foo2: .long 1 [hjl@gnu-cfl-1 pr23591]$ cat foo-auto.S .section .text,"axG",%progbits,foo1,comdat .globl foo1 .type foo1, @function foo1: .byte 0 [hjl@gnu-cfl-1 pr23591]$ cat x.c extern int __start___sancov_cntrs; int bar (void) { int* ap = &__start___sancov_cntrs; return ap[0]; } [hjl@gnu-cfl-1 pr23591]$ cat y.S .hidden __start___sancov_cntrs [hjl@gnu-cfl-1 pr23591]$ make gcc -B../ -fPIC -O2 -g -c -o x.o x.c gcc -B../ -fPIC -O2 -g -c -o y.o y.S gcc -B../ -fPIC -O2 -g -c -o foo-auto.o foo-auto.S gcc -B../ -fPIC -O2 -g -c -o foo.o foo.S ./ld -shared -o x.so x.o y.o foo-auto.o foo.o ./ld: x.o: in function `bar': /export/home/hjl/bugs/binutils/pr23591/x.c:7: undefined reference to `__start___sancov_cntrs' make: *** [Makefile:12: x.so] Error 1 [hjl@gnu-cfl-1 pr23591]$ make LD=ld.gold ld.gold -shared -o x.so x.o y.o foo-auto.o foo.o [hjl@gnu-cfl-1 pr23591]$
Created attachment 11219 [details] A patch Please try this.
It worked.
Comment on attachment 11219 [details] A patch The final patch is posted at https://sourceware.org/ml/binutils/2018-08/msg00482.html
The master branch has been updated by H.J. Lu <hjl@sourceware.org>: https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=4d1c6335455aeeda9de8a5eb58998f919ea35a1e commit 4d1c6335455aeeda9de8a5eb58998f919ea35a1e Author: H.J. Lu <hjl.tools@gmail.com> Date: Fri Aug 31 09:25:31 2018 -0700 ld: Lookup section in output with the same name When there are more than one input sections with the same section name, SECNAME, linker picks the first one to define __start_SECNAME and __stop_SECNAME symbols. When the first input section is removed by comdat group, we need to check if there is still an output section with section name SECNAME. PR ld/23591 * ldlang.c (undef_start_stop): Lookup section in output with the same name. * testsuite/ld-elf/pr23591.d: New file. * testsuite/ld-elf/pr23591a.s: Likewise. * testsuite/ld-elf/pr23591b.s: Likewise. * testsuite/ld-elf/pr23591c.s: Likewise.
Fixed for 2.32.
The master branch has been updated by Alan Modra <amodra@sourceware.org>: https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=0d9a433be406220413671495a9b0fab577a48b5e commit 0d9a433be406220413671495a9b0fab577a48b5e Author: Alan Modra <amodra@gmail.com> Date: Mon Sep 3 10:49:57 2018 +0930 Re: ld: Lookup section in output with the same name Fixes pr23591 test failures on hppa64-hpux and score-elf, and xfails frv-linux and lm32-linux. PR ld/23591 * testsuite/ld-elf/pr23591a.s, * testsuite/ld-elf/pr23591b.s, * testsuite/ld-elf/pr23591c.s: Don't start directives in first column. * testsuite/ld-elf/pr23591.d: xfail frv-linux and lm32-linux. Allow __start___sancov_cntrs as a local symbol.