This is the mail archive of the
binutils@sourceware.org
mailing list for the binutils project.
[committed] Fix problem with hidden symbols on hppa-linux
- From: John David Anglin <dave at hiauly1 dot hia dot nrc dot ca>
- To: binutils at sourceware dot org
- Date: Sun, 6 Nov 2011 15:45:40 -0500
- Subject: [committed] Fix problem with hidden symbols on hppa-linux
- Reply-to: John David Anglin <dave dot anglin at nrc-cnrc dot gc dot ca>
This change fixes PR ld/13387, an abort in elf32-hppa.c linking
libQtWebKit.so.4.8.0.
The scenario is roughly as follows:
1) elf32_hppa_hide_symbol is called with a plt.refcount of roughly 8.
The plabel flag is not set, so the plt.refcount is reset.
2) The plabel reloc is processed and plt.refcount is incremented.
3) elf32_hppa_hide_symbol is called again but this time the plabel
flag is set and it doesn't reset the plt.refcount.
4) However, garbage collection reduces the count to zero.
5) elf32_hppa_adjust_dynamic_symbol is called. Seeing the zero
plt.refcount, it decides that a PLT entry isn't needed.
6) Abort occurs processing the plabel reloc because no slot has
been allocated.
The main fix is to set the plt.refcount to 1 in elf32_hppa_adjust_dynamic_symbol
if its value is <= 0 for symbols referenced by a plabel.
With this change, I was able to change elf32_hppa_hide_symbol so that
it is now more similar to the default hide_symbol.
Tested on hppa-unknown-linux-gnu with no regressions. Committed to
trunk.
Dave
--
J. David Anglin dave.anglin@nrc-cnrc.gc.ca
National Research Council of Canada (613) 990-0752 (FAX: 952-6602)
2011-11-06 John David Anglin <dave.anglin@nrc-cnrc.gc.ca>
PR ld/13387
* elf32-hppa.c (elf32_hppa_hide_symbol): Make STT_GNU_IFUNC symbol
go through PLT. Reset plt field with init_plt_offset.
(elf32_hppa_adjust_dynamic_symbol): Ensure that a PLT slot is
allocated for symbols referenced by a plabel.
Index: elf32-hppa.c
===================================================================
RCS file: /cvs/src/src/bfd/elf32-hppa.c,v
retrieving revision 1.181
diff -u -3 -p -r1.181 elf32-hppa.c
--- elf32-hppa.c 26 Oct 2011 09:47:58 -0000 1.181
+++ elf32-hppa.c 6 Nov 2011 18:21:46 -0000
@@ -1789,10 +1789,12 @@ elf32_hppa_hide_symbol (struct bfd_link_
}
}
- if (! hppa_elf_hash_entry (eh)->plabel)
+ /* STT_GNU_IFUNC symbol must go through PLT. */
+ if (! hppa_elf_hash_entry (eh)->plabel
+ && eh->type != STT_GNU_IFUNC)
{
eh->needs_plt = 0;
- eh->plt = elf_hash_table (info)->init_plt_refcount;
+ eh->plt = elf_hash_table (info)->init_plt_offset;
}
}
@@ -1814,6 +1816,13 @@ elf32_hppa_adjust_dynamic_symbol (struct
if (eh->type == STT_FUNC
|| eh->needs_plt)
{
+ /* If the symbol is used by a plabel, we must allocate a PLT slot.
+ The refcounts are not reliable when it has been hidden since
+ hide_symbol can be called before the plabel flag is set. */
+ if (hppa_elf_hash_entry (eh)->plabel
+ && eh->plt.refcount <= 0)
+ eh->plt.refcount = 1;
+
if (eh->plt.refcount <= 0
|| (eh->def_regular
&& eh->root.type != bfd_link_hash_defweak