diff options
author | H.J. Lu <hjl.tools@gmail.com> | 2017-05-10 09:28:00 -0700 |
---|---|---|
committer | H.J. Lu <hjl.tools@gmail.com> | 2017-05-10 09:28:28 -0700 |
commit | aab82f4c201a2612c0fb6d5b66d8e4ce2f036f1c (patch) | |
tree | 62d80226330cf3d900e8e3511dc1f72bf738e22f /bfd | |
parent | f78c0b915888ab388f9bdac826d7ac18dc944c28 (diff) | |
download | gdb-aab82f4c201a2612c0fb6d5b66d8e4ce2f036f1c.zip gdb-aab82f4c201a2612c0fb6d5b66d8e4ce2f036f1c.tar.gz gdb-aab82f4c201a2612c0fb6d5b66d8e4ce2f036f1c.tar.bz2 |
x86-64: Use .plt.bnd for IFUNC function address
When -z bndplt is used, we must use the .plt.bnd entry for IFUNC function
address.
bfd/
PR ld/21481
* elf64-x86-64.c (elf_x86_64_finish_dynamic_symbol): Use .plt.bnd
for IFUNC function address.
ld/
PR ld/21481
* testsuite/ld-x86-64/pr21481a.c: New file.
* testsuite/ld-x86-64/pr21481b.S: Likewise.
* testsuite/ld-x86-64/x86-64.exp: Run PR ld/21481 tests.
Diffstat (limited to 'bfd')
-rw-r--r-- | bfd/ChangeLog | 6 | ||||
-rw-r--r-- | bfd/elf64-x86-64.c | 14 |
2 files changed, 18 insertions, 2 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog index c12ff16..b307ecb 100644 --- a/bfd/ChangeLog +++ b/bfd/ChangeLog @@ -1,3 +1,9 @@ +2017-05-10 H.J. Lu <hongjiu.lu@intel.com> + + PR ld/21481 + * elf64-x86-64.c (elf_x86_64_finish_dynamic_symbol): Use .plt.bnd + for IFUNC function address. + 2017-05-10 Claudiu Zissulescu <claziss@synopsys.com> * elf32-arc.c (FEATURE_LIST_NAME): Define. diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 1fbba1b..fb9336d 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -5974,6 +5974,7 @@ elf_x86_64_finish_dynamic_symbol (bfd *output_bfd, else { asection *plt; + bfd_vma plt_offset; if (!h->pointer_equality_needed) abort (); @@ -5981,10 +5982,19 @@ elf_x86_64_finish_dynamic_symbol (bfd *output_bfd, /* For non-shared object, we can't use .got.plt, which contains the real function addres if we need pointer equality. We load the GOT entry with the PLT entry. */ - plt = htab->elf.splt ? htab->elf.splt : htab->elf.iplt; + if (htab->plt_bnd != NULL) + { + plt = htab->plt_bnd; + plt_offset = eh->plt_bnd.offset; + } + else + { + plt = htab->elf.splt ? htab->elf.splt : htab->elf.iplt; + plt_offset = h->plt.offset; + } bfd_put_64 (output_bfd, (plt->output_section->vma + plt->output_offset - + h->plt.offset), + + plt_offset), htab->elf.sgot->contents + h->got.offset); return TRUE; } |