Bug 13255 - Wrong `local symbol is referenced by DSO' warnings on Solaris
Summary: Wrong `local symbol is referenced by DSO' warnings on Solaris
Status: RESOLVED FIXED
Alias: None
Product: binutils
Classification: Unclassified
Component: ld (show other bugs)
Version: 2.22
: P1 critical
Target Milestone: ---
Assignee: Not yet assigned to anyone
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2011-10-04 14:30 UTC by Rainer Orth
Modified: 2022-07-29 01:15 UTC (History)
1 user (show)

See Also:
Host: i386-pc-solaris2.11
Target: i386-pc-solaris2.11
Build: i386-pc-solaris2.11
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Rainer Orth 2011-10-04 14:30:07 UTC
I've just tried gcc mainline with binutils 2.21.90 on Solaris 11/x86.  Apart from
PR ld/13254, I've got many gcc testsuite failures like the following:

FAIL: gcc.dg/special/gcsec-1.c (test for excess errors)
Excess errors:
/vol/gcc/bin/gld-2.21.90: .
WARNING: gcc.dg/special/gcsec-1.c compilation failed to produce executable

Running test manually yields

> /vol/gcc/obj/gcc-4.7.0-20110930/11-gcc-gas-gld22190/gcc/xgcc -B/vol/gcc/obj/gcc-4.7.0-20110930/11-gcc-gas-gld22190/gcc/ /vol/gcc/src/hg/trunk/solaris/gcc/testsuite/gcc.dg/special/gcsec-1.c -ffunction-sections -fdata-sections -Wl,--gc-sections -lm -o ./gcsec-1.exe
/vol/gcc/bin/gld-2.21.90: ./gcsec-1.exe: local symbol `__flt_rounds@@SYSVABI_1.3' in /lib/libc.so is referenced by DSO
/vol/gcc/bin/gld-2.21.90: final link failed: Bad value
collect2: error: ld returned 1 exit status

so it seems most of the error message is stripped by the gcc testsuite
framework.

> gld-2.21.90 --eh-frame-hdr -m elf_i386_sol2 -Y P,/usr/ccs/lib:/lib:/usr/lib -Qy -o ./gcsec-1.exe /usr/lib/crt1.o /usr/lib/crti.o /usr/lib/values-Xa.o /vol/gcc/obj/gcc-4.7.0-20110930/11-gcc-gas-gld22190/gcc/crtbegin.o -L/vol/gcc/obj/gcc-4.7.0-20110930/11-gcc-gas-gld22190/gcc gcsec-1.o --gc-sections -lm -lgcc -lgcc_eh -lc -lgcc -lgcc_eh /vol/gcc/obj/gcc-4.7.0-20110930/11-gcc-gas-gld22190/gcc/crtend.o /usr/lib/crtn.o
gld-2.21.90: ./gcsec-1.exe: local symbol `__flt_rounds@@SYSVABI_1.3' in /lib/libc.so is referenced by DSO
gld-2.21.90: final link failed: Bad value

The main problem is that the error is wrong: __flt_rounds *isn't* a local symbol:

ro@fuego 185 > nm /lib/libc.so|grep __flt_rounds
[8262]  |   1496252|         4|OBJT |GLOB |0    |29     |__flt_rounds
[1237]  |         0|         0|FILE |LOCL |0    |ABS    |__flt_rounds.c

It is referenced in libm.so:

/lib/libm.so: [2411]    |         0|         0|OBJT |GLOB |0    |UNDEF  |__flt_rounds
/lib/libc.so: [8262]    |   1496252|         4|OBJT |GLOB |0    |29     |__flt_rounds
/lib/libc.so: [1237]    |         0|         0|FILE |LOCL |0    |ABS    |__flt_rounds.c

Apart from that, even if it were correct, the error message is pretty useless:
which DSO does it reference?

I fear this is a showstopper bug: it renders gld complete useless on Solaris.
I've only tried Solaris 11 so far, but expect that there's no difference on
older releases.

  Rainer
Comment 1 Rainer Orth 2011-10-10 15:36:42 UTC
I've digged a bit deeper and found the culprit patch:

In 2.21.1, h->forced_local is 0 in the test in elflink.c (elf_link_output_extsym):

  /* We should also warn if a forced local symbol is referenced from
     shared libraries.  */

In 2.21.90, it is set to 1 by _bfd_elf_link_hash_hide_symbol with this callstack, called due to --gc-sections:

(gdb) where
#0  _bfd_elf_link_hash_hide_symbol (info=0x821b7e0, h=0x84231c4, force_local=1) at /vol/gnu/src/binutils/binutils-2.21.90/bfd/elflink.c:6783
#1  0x080ffce4 in elf_gc_sweep_symbol (h=0x84231c4, data=0x8047688) at /vol/gnu/src/binutils/binutils-2.21.90/bfd/elflink.c:11704
#2  0x080b54d0 in bfd_link_hash_traverse (htab=0x822a7e0, func=0x80ffc26 <elf_gc_sweep_symbol>, info=0x8047688) at /vol/gnu/src/binutils/binutils-2.21.90/bfd/linker.c:628
#3  0x080fff0c in elf_gc_sweep (abfd=0x821e860, info=0x821b7e0) at /vol/gnu/src/binutils/binutils-2.21.90/bfd/elflink.c:11789
#4  0x08100672 in bfd_elf_gc_sections (abfd=0x821e860, info=0x821b7e0) at /vol/gnu/src/binutils/binutils-2.21.90/bfd/elflink.c:12033
#5  0x0807c4f1 in lang_gc_sections () at /vol/gnu/src/binutils/binutils-2.21.90/ld/ldlang.c:6346
#6  0x0807ca59 in lang_process () at /vol/gnu/src/binutils/binutils-2.21.90/ld/ldlang.c:6653
#7  0x08080156 in main (argc=24, argv=0x804780c) at /vol/gnu/src/binutils/binutils-2.21.90/ld/ldmain.c:465

This is ultimately caused by H.J.'s patch

	PR ld/13177
	* elflink.c (elf_gc_sweep_symbol): Also hide symbols without PLT
	nor GOT references.

For the symbol in question, we have

  h->root.type = bfd_link_hash_defined

  h->plt.refcount = -1
  h->got.refcount = 0

If I either remove the --gc-sections or revert the patch, the test links just
fine.

  Rainer
Comment 2 H.J. Lu 2011-10-10 15:55:01 UTC
Please try the current binutils 2.22 branch.
Comment 3 Rainer Orth 2011-10-14 11:46:00 UTC
> --- Comment #2 from H.J. Lu <hjl.tools at gmail dot com> 2011-10-10 15:55:01 UTC ---
> Please try the current binutils 2.22 branch.

Sorry for the delay: I've now re-bootstrapped gcc mainline as of
20111007 with gas/gld 2.21.90.20111007 and Alan's patch for PR ld/13254.

Works just fine, with only two testsuite regressions compared to 2.21.1:

FAIL: g++.dg/init/cleanup3.C scan-assembler-not _tcf
FAIL: g++.old-deja/g++.other/init5.C execution test

With gld 2.21.1, the cxa_atexit effective-target test fails, thus the
first test above is UNSUPPORTED and the second XFAIL.   With 2.21.90,
the cxa_atexit test suddenly passes, although Solaris 11 doesn't have
__cxa_atexit.

	Rainer
Comment 4 Alan Modra 2022-07-29 01:15:47 UTC
.