From: Alan Modra <amodra@bigpond.net.au>
To: binutils@sources.redhat.com
Subject: Fix an --as-needed linker problem
Date: Wed, 22 Dec 2004 03:55:00 -0000 [thread overview]
Message-ID: <20041222035542.GA18274@bubble.modra.org> (raw)
This is a fix for http://gcc.gnu.org/bugzilla/show_bug.cgi?id=17608
Quoting from the PR:
When linking we use:
-lgcc --as-needed -lgcc_s --no-as-needed -lc_p -lgcc --as-needed -lgcc_s
--no-as-needed.
During the first scan of libgcc_s.so, the linker finds no reason to mark
libgcc_s.so as needed, because no symbols in libgcc_s.so are referenced
at that point. After linking libc_p.a, the second scan of libgcc_s.so
does find referenced symbols. However, the linker sees that these
symbols have already been defined, thus the "new" definitions found in
the second scan of libgcc_s.so aren't used. (If a symbol is defined in
two shared libs, the one from the lib first encountered by the linker is
used. As far as the linker is concerned the first libgcc_s.so is a
different shared lib from the second libgcc_s.so). Thus the linker
decides that the second libgcc_s.so isn't needed, and so doesn't emit a
DT_NEEDED tag for libgcc_s.so.
With older glibc ld.so, this resulted in segfaults. Current ld.so
complains with
Inconsistency detected by ld.so: dl-version.c: 230: _dl_check_map_versions:
Assertion `needed != ((void *)0)' failed!
* elflink.c (_bfd_elf_merge_symbol): Treat old definitions from
as-needed dynamic libs as undefined.
(elf_link_add_object_symbols): Remove DYN_AS_NEEDED from as-needed
libs when finding they are needed.
Index: bfd/elflink.c
===================================================================
RCS file: /cvs/src/src/bfd/elflink.c,v
retrieving revision 1.121
diff -u -p -r1.121 elflink.c
--- bfd/elflink.c 10 Dec 2004 14:04:58 -0000 1.121
+++ bfd/elflink.c 22 Dec 2004 03:42:50 -0000
@@ -719,7 +719,7 @@ _bfd_elf_merge_symbol (bfd *abfd,
int bind;
bfd *oldbfd;
bfd_boolean newdyn, olddyn, olddef, newdef, newdyncommon, olddyncommon;
- bfd_boolean newweak, oldweak;
+ bfd_boolean newweak, oldweak, old_asneeded;
*skip = FALSE;
*override = FALSE;
@@ -849,6 +849,14 @@ _bfd_elf_merge_symbol (bfd *abfd,
else
olddef = TRUE;
+ /* If the old definition came from an as-needed dynamic library which
+ wasn't found to be needed, treat the sym as undefined. */
+ old_asneeded = FALSE;
+ if (newdyn
+ && olddyn
+ && (elf_dyn_lib_class (oldbfd) & DYN_AS_NEEDED) != 0)
+ old_asneeded = TRUE;
+
/* Check TLS symbol. */
if ((ELF_ST_TYPE (sym->st_info) == STT_TLS || h->type == STT_TLS)
&& ELF_ST_TYPE (sym->st_info) != h->type)
@@ -1051,6 +1059,7 @@ _bfd_elf_merge_symbol (bfd *abfd,
if (olddyn
&& olddef
+ && !old_asneeded
&& h->root.type == bfd_link_hash_defined
&& h->def_dynamic
&& (h->root.u.def.section->flags & SEC_ALLOC) != 0
@@ -1102,7 +1111,7 @@ _bfd_elf_merge_symbol (bfd *abfd,
if (newdyn
&& newdef
- && (olddef
+ && ((olddef && !old_asneeded)
|| (h->root.type == bfd_link_hash_common
&& (newweak
|| ELF_ST_TYPE (sym->st_info) == STT_FUNC))))
@@ -1152,7 +1161,7 @@ _bfd_elf_merge_symbol (bfd *abfd,
symbol is a function or is weak. */
flip = NULL;
- if (! newdyn
+ if ((!newdyn || old_asneeded)
&& (newdef
|| (bfd_is_com_section (sec)
&& (oldweak
@@ -3937,6 +3946,8 @@ elf_link_add_object_symbols (bfd *abfd,
goto error_free_vers;
}
+ elf_dyn_lib_class (abfd) &= ~DYN_AS_NEEDED;
+
add_needed = TRUE;
ret = elf_add_dt_needed_tag (info, soname, add_needed);
if (ret < 0)
--
Alan Modra
IBM OzLabs - Linux Technology Centre
reply other threads:[~2004-12-22 3:55 UTC|newest]
Thread overview: [no followups] expand[flat|nested] mbox.gz Atom feed
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20041222035542.GA18274@bubble.modra.org \
--to=amodra@bigpond.net.au \
--cc=binutils@sources.redhat.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).