mirror of
https://sourceware.org/git/binutils-gdb.git
synced 2024-11-24 02:24:46 +08:00
Optimize _bfd_elf_allocate_ifunc_dyn_relocs.
2011-01-06 H.J. Lu <hongjiu.lu@intel.com> * elf-ifunc.c (_bfd_elf_allocate_ifunc_dyn_relocs): Optimized.
This commit is contained in:
parent
fb03cb59c1
commit
7be867377d
@ -1,3 +1,7 @@
|
||||
2011-01-06 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
* elf-ifunc.c (_bfd_elf_allocate_ifunc_dyn_relocs): Optimized.
|
||||
|
||||
2011-01-06 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
PR ld/12366
|
||||
|
@ -194,25 +194,20 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
|
||||
where it is marked with regular reference, but not non-GOT
|
||||
reference. It may happen if we didn't see STT_GNU_IFUNC
|
||||
symbol at the time when checking relocations. */
|
||||
bfd_size_type count = 0;
|
||||
|
||||
if (info->shared
|
||||
&& !h->non_got_ref
|
||||
&& h->ref_regular)
|
||||
{
|
||||
for (p = *head; p != NULL; p = p->next)
|
||||
count += p->count;
|
||||
if (count != 0)
|
||||
h->non_got_ref = 1;
|
||||
}
|
||||
for (p = *head; p != NULL; p = p->next)
|
||||
if (p->count)
|
||||
{
|
||||
h->non_got_ref = 1;
|
||||
goto keep;
|
||||
}
|
||||
|
||||
if (count == 0)
|
||||
{
|
||||
h->got = htab->init_got_offset;
|
||||
h->plt = htab->init_plt_offset;
|
||||
*head = NULL;
|
||||
return TRUE;
|
||||
}
|
||||
h->got = htab->init_got_offset;
|
||||
h->plt = htab->init_plt_offset;
|
||||
*head = NULL;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Return and discard space for dynamic relocations against it if
|
||||
@ -228,6 +223,7 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
keep:
|
||||
bed = get_elf_backend_data (info->output_bfd);
|
||||
if (bed->rela_plts_and_copies_p)
|
||||
sizeof_reloc = bed->s->sizeof_rela;
|
||||
@ -277,10 +273,20 @@ _bfd_elf_allocate_ifunc_dyn_relocs (struct bfd_link_info *info,
|
||||
*head = NULL;
|
||||
|
||||
/* Finally, allocate space. */
|
||||
for (p = *head; p != NULL; p = p->next)
|
||||
htab->irelifunc->size += p->count * sizeof_reloc;
|
||||
p = *head;
|
||||
if (p != NULL)
|
||||
{
|
||||
bfd_size_type count = 0;
|
||||
do
|
||||
{
|
||||
count += p->count;
|
||||
p = p->next;
|
||||
}
|
||||
while (p != NULL);
|
||||
htab->irelifunc->size += count * sizeof_reloc;
|
||||
}
|
||||
|
||||
/* For STT_GNU_IFUNC symbol, .got.plt has the real function addres
|
||||
/* For STT_GNU_IFUNC symbol, .got.plt has the real function address
|
||||
and .got has the PLT entry adddress. We will load the GOT entry
|
||||
with the PLT entry in finish_dynamic_symbol if it is used. For
|
||||
branch, it uses .got.plt. For symbol value,
|
||||
|
Loading…
Reference in New Issue
Block a user