summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bfd/ChangeLog29
-rw-r--r--bfd/elf-bfd.h7
-rw-r--r--bfd/elf32-sh64.c10
-rw-r--r--bfd/elf32-v850.c8
-rw-r--r--bfd/elf64-hppa.c10
-rw-r--r--bfd/elf64-mmix.c8
-rw-r--r--bfd/elf64-ppc.c122
-rw-r--r--bfd/elf64-sh64.c10
-rw-r--r--bfd/elf64-sparc.c9
-rw-r--r--bfd/elflink.h30
-rw-r--r--bfd/elfxx-mips.c4
-rw-r--r--bfd/elfxx-mips.h4
12 files changed, 190 insertions, 61 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index ec2958a566..75ed5cd90e 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,3 +1,32 @@
+2003-12-08 Alan Modra <amodra@bigpond.net.au>
+
+ * elf-bfd.h (struct elf_backend_data): Remove "bfd *" and add
+ "elflink_hash_entry *" param to elf_backend_link_output_symbol_hook.
+ Add "elflink_hash_entry *" param to elf_backend_output_arch_syms.
+ * elflink.h (elf_link_output_sym): Add "elflink_hash_entry *" param,
+ and pass to output_symbol_hook.
+ (elf_bfd_final_link): Adjust elf_link_output_sym calls.
+ (elf_link_output_extsym): Likewise.
+ (elf_link_input_bfd): Likewise.
+ * elf32-sh64.c (sh64_elf_link_output_symbol_hook): Adjust.
+ * elf32-v850.c (v850_elf_link_output_symbol_hook): Likewise.
+ * elf64-mmix.c (mmix_elf_link_output_symbol_hook): Likewise.
+ * elf64-sh64.c (sh64_elf64_link_output_symbol_hook): Likewise.
+ * elfxx-mips.c (_bfd_mips_elf_link_output_symbol_hook): Likewise.
+ * elfxx-mips.h (_bfd_mips_elf_link_output_symbol_hook): Likewise.
+ * elf64-sparc.c (sparc64_elf_output_arch_syms): Likewise.
+ * elf64-hppa.c (elf64_hppa_link_output_symbol_hook): Likewise.
+ Validate dynh->h against h.
+ * elf64-ppc.c (struct ppc_link_hash_entry): Add adjust_done bitfield.
+ (link_hash_newfunc): Init it.
+ (adjust_opd_syms): New function.
+ (ppc64_elf_edit_opd): Set adjust_done when global .opd sym adjusted.
+ Set opd.adjust for all .opd relocs. Call adjust_opd_syms.
+ (ppc64_elf_tls_optimize): Adjust possible .opd sym values here.
+ (ppc64_elf_relocate_section): Also adjust syms not a multiple of 24.
+ (ppc64_elf_output_symbol_hook): New function.
+ (elf_backend_link_output_symbol_hook): Define.
+
2003-12-07 Richard Sandiford <rsandifo@redhat.com>
* elf32-mips.c, elfn32-mips.c, elf64-mips.c: Convert prototypes.
diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h
index 0a2f6b2068..c457a399f3 100644
--- a/bfd/elf-bfd.h
+++ b/bfd/elf-bfd.h
@@ -626,8 +626,8 @@ struct elf_backend_data
/* If this field is not NULL, it is called by the elf_link_output_sym
phase of a link for each symbol which will appear in the object file. */
bfd_boolean (*elf_backend_link_output_symbol_hook)
- (bfd *, struct bfd_link_info *info, const char *, Elf_Internal_Sym *,
- asection *);
+ (struct bfd_link_info *info, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *);
/* The CREATE_DYNAMIC_SECTIONS function is called by the ELF backend
linker the first time it encounters a dynamic object in the link.
@@ -793,7 +793,8 @@ struct elf_backend_data
not handled in the hash table. */
bfd_boolean (*elf_backend_output_arch_syms)
(bfd *, struct bfd_link_info *, void *,
- bfd_boolean (*) (void *, const char *, Elf_Internal_Sym *, asection *));
+ bfd_boolean (*) (void *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *));
/* Copy any information related to dynamic linking from a pre-existing
symbol to a newly created symbol. Also called to copy flags and
diff --git a/bfd/elf32-sh64.c b/bfd/elf32-sh64.c
index 8760f60c51..eac444af46 100644
--- a/bfd/elf32-sh64.c
+++ b/bfd/elf32-sh64.c
@@ -59,8 +59,8 @@ static bfd_boolean sh64_elf_add_symbol_hook
(bfd *, struct bfd_link_info *, const Elf_Internal_Sym *, const char **,
flagword *, asection **, bfd_vma *);
static bfd_boolean sh64_elf_link_output_symbol_hook
- (bfd *, struct bfd_link_info *, const char *, Elf_Internal_Sym *,
- asection *);
+ (struct bfd_link_info *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *);
static bfd_boolean sh64_backend_section_from_shdr
(bfd *, Elf_Internal_Shdr *, const char *);
static void sh64_elf_final_write_processing
@@ -470,11 +470,11 @@ sh64_elf_add_symbol_hook (bfd *abfd, struct bfd_link_info *info,
DataLabel symbol. */
bfd_boolean
-sh64_elf_link_output_symbol_hook (bfd *abfd ATTRIBUTE_UNUSED,
- struct bfd_link_info *info,
+sh64_elf_link_output_symbol_hook (struct bfd_link_info *info,
const char *cname,
Elf_Internal_Sym *sym,
- asection *input_sec ATTRIBUTE_UNUSED)
+ asection *input_sec ATTRIBUTE_UNUSED,
+ struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
{
char *name = (char *) cname;
diff --git a/bfd/elf32-v850.c b/bfd/elf32-v850.c
index b964a7e29e..45bb4f6eb7 100644
--- a/bfd/elf32-v850.c
+++ b/bfd/elf32-v850.c
@@ -76,8 +76,8 @@ static bfd_boolean v850_elf_add_symbol_hook
PARAMS ((bfd *, struct bfd_link_info *, const Elf_Internal_Sym *,
const char **, flagword *, asection **, bfd_vma *));
static bfd_boolean v850_elf_link_output_symbol_hook
- PARAMS ((bfd *, struct bfd_link_info *, const char *,
- Elf_Internal_Sym *, asection *));
+ PARAMS ((struct bfd_link_info *, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *));
static bfd_boolean v850_elf_section_from_shdr
PARAMS ((bfd *, Elf_Internal_Shdr *, const char *));
static bfd_boolean v850_elf_gc_sweep_hook
@@ -2213,12 +2213,12 @@ v850_elf_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
}
static bfd_boolean
-v850_elf_link_output_symbol_hook (abfd, info, name, sym, input_sec)
- bfd *abfd ATTRIBUTE_UNUSED;
+v850_elf_link_output_symbol_hook (info, name, sym, input_sec, h)
struct bfd_link_info *info ATTRIBUTE_UNUSED;
const char *name ATTRIBUTE_UNUSED;
Elf_Internal_Sym *sym;
asection *input_sec;
+ struct elf_link_hash_entry *h ATTRIBUTE_UNUSED;
{
/* If we see a common symbol, which implies a relocatable link, then
if a symbol was in a special common section in an input file, mark
diff --git a/bfd/elf64-hppa.c b/bfd/elf64-hppa.c
index 2dd2a36186..36c27c4b6f 100644
--- a/bfd/elf64-hppa.c
+++ b/bfd/elf64-hppa.c
@@ -202,8 +202,8 @@ static bfd_boolean elf64_hppa_size_dynamic_sections
PARAMS ((bfd *, struct bfd_link_info *));
static bfd_boolean elf64_hppa_link_output_symbol_hook
- PARAMS ((bfd *abfd, struct bfd_link_info *, const char *,
- Elf_Internal_Sym *, asection *input_sec));
+ PARAMS ((struct bfd_link_info *, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *));
static bfd_boolean elf64_hppa_finish_dynamic_symbol
PARAMS ((bfd *, struct bfd_link_info *,
@@ -1893,12 +1893,12 @@ elf64_hppa_size_dynamic_sections (output_bfd, info)
table. Ick. */
static bfd_boolean
-elf64_hppa_link_output_symbol_hook (abfd, info, name, sym, input_sec)
- bfd *abfd ATTRIBUTE_UNUSED;
+elf64_hppa_link_output_symbol_hook (info, name, sym, input_sec, h)
struct bfd_link_info *info;
const char *name;
Elf_Internal_Sym *sym;
asection *input_sec ATTRIBUTE_UNUSED;
+ struct elf_link_hash_entry *h;
{
struct elf64_hppa_link_hash_table *hppa_info;
struct elf64_hppa_dyn_hash_entry *dyn_h;
@@ -1912,6 +1912,8 @@ elf64_hppa_link_output_symbol_hook (abfd, info, name, sym, input_sec)
hppa_info = elf64_hppa_hash_table (info);
dyn_h = elf64_hppa_dyn_hash_lookup (&hppa_info->dyn_hash_table,
name, FALSE, FALSE);
+ if (dyn_h->h != h)
+ return TRUE;
/* Function symbols for which we created .opd entries *may* have been
munged by finish_dynamic_symbol and have to be un-munged here.
diff --git a/bfd/elf64-mmix.c b/bfd/elf64-mmix.c
index a747fd34f4..ca627ef2c0 100644
--- a/bfd/elf64-mmix.c
+++ b/bfd/elf64-mmix.c
@@ -157,8 +157,8 @@ struct bpo_greg_section_info
};
static bfd_boolean mmix_elf_link_output_symbol_hook
- PARAMS ((bfd *, struct bfd_link_info *, const char *,
- Elf_Internal_Sym *, asection *));
+ PARAMS ((struct bfd_link_info *, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *));
static bfd_reloc_status_type mmix_elf_reloc
PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
@@ -2113,12 +2113,12 @@ _bfd_mmix_check_all_relocs (abfd, info)
number. */
static bfd_boolean
-mmix_elf_link_output_symbol_hook (abfd, info, name, sym, input_sec)
- bfd *abfd ATTRIBUTE_UNUSED;
+mmix_elf_link_output_symbol_hook (info, name, sym, input_sec, h)
struct bfd_link_info *info ATTRIBUTE_UNUSED;
const char *name ATTRIBUTE_UNUSED;
Elf_Internal_Sym *sym;
asection *input_sec;
+ struct elf_link_hash_entry *h ATTRIBUTE_UNUSED;
{
if (input_sec != NULL
&& input_sec->name != NULL
diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c
index 1282b3b524..3ed9042e6f 100644
--- a/bfd/elf64-ppc.c
+++ b/bfd/elf64-ppc.c
@@ -92,6 +92,7 @@ static bfd_reloc_status_type ppc64_elf_unhandled_reloc
#define elf_backend_finish_dynamic_symbol ppc64_elf_finish_dynamic_symbol
#define elf_backend_reloc_type_class ppc64_elf_reloc_type_class
#define elf_backend_finish_dynamic_sections ppc64_elf_finish_dynamic_sections
+#define elf_backend_link_output_symbol_hook ppc64_elf_output_symbol_hook
#define elf_backend_special_sections ppc64_elf_special_sections
/* The name of the dynamic interpreter. This is put in the .interp
@@ -2762,6 +2763,9 @@ struct ppc_link_hash_entry
unsigned int is_func_descriptor:1;
unsigned int is_entry:1;
+ /* Whether global opd sym has been adjusted or not. */
+ unsigned int adjust_done:1;
+
/* Contexts in which symbol is used in the GOT (or TOC).
TLS_GD .. TLS_EXPLICIT bits are or'd into the mask as the
corresponding relocs are encountered during check_relocs.
@@ -2971,6 +2975,7 @@ link_hash_newfunc (struct bfd_hash_entry *entry,
eh->is_func = 0;
eh->is_func_descriptor = 0;
eh->is_entry = 0;
+ eh->adjust_done = 0;
eh->tls_mask = 0;
}
@@ -4875,10 +4880,53 @@ get_tls_mask (char **tls_maskp, unsigned long *toc_symndx,
return 1;
}
+/* Adjust all global syms defined in opd sections. In gcc generated
+ code these will already have been done, but I suppose we have to
+ cater for all sorts of hand written assembly. */
+
+static bfd_boolean
+adjust_opd_syms (struct elf_link_hash_entry *h, void *inf ATTRIBUTE_UNUSED)
+{
+ struct ppc_link_hash_entry *eh;
+ asection *sym_sec;
+ long *opd_adjust;
+
+ if (h->root.type == bfd_link_hash_indirect)
+ return TRUE;
+
+ if (h->root.type == bfd_link_hash_warning)
+ h = (struct elf_link_hash_entry *) h->root.u.i.link;
+
+ if (h->root.type != bfd_link_hash_defined
+ && h->root.type != bfd_link_hash_defweak)
+ return TRUE;
+
+ eh = (struct ppc_link_hash_entry *) h;
+ if (eh->adjust_done)
+ return TRUE;
+
+ sym_sec = eh->elf.root.u.def.section;
+ if (sym_sec != NULL
+ && elf_section_data (sym_sec) != NULL
+ && (opd_adjust = ppc64_elf_section_data (sym_sec)->opd.adjust) != NULL)
+ {
+ eh->elf.root.u.def.value += opd_adjust[eh->elf.root.u.def.value / 24];
+ eh->adjust_done = 1;
+ }
+ return TRUE;
+}
+
+/* Remove unused Official Procedure Descriptor entries. Currently we
+ only remove those associated with functions in discarded link-once
+ sections, or weakly defined functions that have been overridden. It
+ would be possible to remove many more entries for statically linked
+ applications. */
+
bfd_boolean
ppc64_elf_edit_opd (bfd *obfd, struct bfd_link_info *info)
{
bfd *ibfd;
+ bfd_boolean some_edited = FALSE;
for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link_next)
{
@@ -5079,22 +5127,24 @@ ppc64_elf_edit_opd (bfd *obfd, struct bfd_link_info *info)
if (h != NULL)
{
- /* Redefine the function descriptor symbol
- to this location in the opd section.
- We've checked above that opd relocs are
- ordered. */
+ /* Redefine the function descriptor symbol to
+ this location in the opd section. It is
+ necessary to update the value here rather
+ than using an array of adjustments as we do
+ for local symbols, because various places
+ in the generic ELF code use the value
+ stored in u.def.value. */
fdh->elf.root.u.def.value = wptr - sec->contents;
+ fdh->adjust_done = 1;
}
- else
- {
- /* Local syms are a bit tricky. We could
- tweak them as they can be cached, but
- we'd need to look through the local syms
- for the function descriptor sym which we
- don't have at the moment. So keep an
- array of adjustments. */
- adjust[rel->r_offset / 24] = wptr - rptr;
- }
+
+ /* Local syms are a bit tricky. We could
+ tweak them as they can be cached, but
+ we'd need to look through the local syms
+ for the function descriptor sym which we
+ don't have at the moment. So keep an
+ array of adjustments. */
+ adjust[rel->r_offset / 24] = wptr - rptr;
if (wptr != rptr)
memcpy (wptr, rptr, 24);
@@ -5153,6 +5203,7 @@ ppc64_elf_edit_opd (bfd *obfd, struct bfd_link_info *info)
elf_section_data (sec)->rel_hdr.sh_size
= sec->reloc_count * elf_section_data (sec)->rel_hdr.sh_entsize;
BFD_ASSERT (elf_section_data (sec)->rel_hdr2 == NULL);
+ some_edited = TRUE;
}
else if (elf_section_data (sec)->relocs != relstart)
free (relstart);
@@ -5167,6 +5218,9 @@ ppc64_elf_edit_opd (bfd *obfd, struct bfd_link_info *info)
}
}
+ if (some_edited)
+ elf_link_hash_traverse (elf_hash_table (info), adjust_opd_syms, NULL);
+
return TRUE;
}
@@ -5262,7 +5316,17 @@ ppc64_elf_tls_optimize (bfd *obfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
value = h->root.u.def.value;
}
else
- value = sym->st_value;
+ {
+ value = sym->st_value;
+
+ if (elf_section_data (sym_sec) != NULL)
+ {
+ long *adjust;
+ adjust = ppc64_elf_section_data (sym_sec)->opd.adjust;
+ if (adjust != NULL)
+ value += adjust[value / 24];
+ }
+ }
ok_tprel = FALSE;
is_local = FALSE;
@@ -7402,7 +7466,7 @@ ppc64_elf_relocate_section (bfd *output_bfd,
long *opd_sym_adjust;
opd_sym_adjust = ppc64_elf_section_data (sec)->opd.adjust;
- if (opd_sym_adjust != NULL && sym->st_value % 24 == 0)
+ if (opd_sym_adjust != NULL)
relocation += opd_sym_adjust[sym->st_value / 24];
}
}
@@ -8673,6 +8737,32 @@ ppc64_elf_relocate_section (bfd *output_bfd,
return ret;
}
+/* Adjust the value of any local symbols in opd sections. */
+
+static bfd_boolean
+ppc64_elf_output_symbol_hook (struct bfd_link_info *info,
+ const char *name ATTRIBUTE_UNUSED,
+ Elf_Internal_Sym *elfsym,
+ asection *input_sec,
+ struct elf_link_hash_entry *h)
+{
+ long *adjust;
+ bfd_vma value;
+
+ if (h != NULL
+ || input_sec == NULL
+ || ppc64_elf_section_data (input_sec) == NULL
+ || (adjust = ppc64_elf_section_data (input_sec)->opd.adjust) == NULL)
+ return TRUE;
+
+ value = elfsym->st_value - input_sec->output_offset;
+ if (!info->relocatable)
+ value -= input_sec->output_section->vma;
+
+ elfsym->st_value += adjust[value / 24];
+ return TRUE;
+}
+
/* Finish up dynamic symbol handling. We set the contents of various
dynamic sections here. */
diff --git a/bfd/elf64-sh64.c b/bfd/elf64-sh64.c
index 338278e58d..15c29924d9 100644
--- a/bfd/elf64-sh64.c
+++ b/bfd/elf64-sh64.c
@@ -144,8 +144,8 @@ static bfd_boolean sh64_elf64_add_symbol_hook
(bfd *, struct bfd_link_info *, const Elf_Internal_Sym *, const char **,
flagword *, asection **, bfd_vma *);
static bfd_boolean sh64_elf64_link_output_symbol_hook
- (bfd *, struct bfd_link_info *, const char *, Elf_Internal_Sym *,
- asection *);
+ (struct bfd_link_info *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *);
static bfd_boolean sh64_elf64_fake_sections
(bfd *, Elf_Internal_Shdr *, asection *);
static void sh64_elf64_final_write_processing
@@ -2982,11 +2982,11 @@ sh64_elf64_add_symbol_hook (bfd *abfd, struct bfd_link_info *info,
DataLabel symbol. */
static bfd_boolean
-sh64_elf64_link_output_symbol_hook (bfd *abfd ATTRIBUTE_UNUSED,
- struct bfd_link_info *info,
+sh64_elf64_link_output_symbol_hook (struct bfd_link_info *info,
const char *cname,
Elf_Internal_Sym *sym,
- asection *input_sec ATTRIBUTE_UNUSED)
+ asection *input_sec ATTRIBUTE_UNUSED,
+ struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
{
char *name = (char *) cname;
diff --git a/bfd/elf64-sparc.c b/bfd/elf64-sparc.c
index 204b648ba8..4224310267 100644
--- a/bfd/elf64-sparc.c
+++ b/bfd/elf64-sparc.c
@@ -65,7 +65,8 @@ static bfd_boolean sparc64_elf_add_symbol_hook
const char **, flagword *, asection **, bfd_vma *));
static bfd_boolean sparc64_elf_output_arch_syms
PARAMS ((bfd *, struct bfd_link_info *, PTR,
- bfd_boolean (*) (PTR, const char *, Elf_Internal_Sym *, asection *)));
+ bfd_boolean (*) (PTR, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *)));
static void sparc64_elf_symbol_processing
PARAMS ((bfd *, asymbol *));
@@ -1511,7 +1512,8 @@ sparc64_elf_output_arch_syms (output_bfd, info, finfo, func)
struct bfd_link_info *info;
PTR finfo;
bfd_boolean (*func)
- PARAMS ((PTR, const char *, Elf_Internal_Sym *, asection *));
+ PARAMS ((PTR, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *));
{
int reg;
struct sparc64_elf_app_reg *app_regs =
@@ -1557,7 +1559,8 @@ sparc64_elf_output_arch_syms (output_bfd, info, finfo, func)
sym.st_shndx = app_regs [reg].shndx;
if (! (*func) (finfo, app_regs [reg].name, &sym,
sym.st_shndx == SHN_ABS
- ? bfd_abs_section_ptr : bfd_und_section_ptr))
+ ? bfd_abs_section_ptr : bfd_und_section_ptr,
+ NULL))
return FALSE;
}
diff --git a/bfd/elflink.h b/bfd/elflink.h
index b02f024bed..f558e1c51a 100644
--- a/bfd/elflink.h
+++ b/bfd/elflink.h
@@ -2833,7 +2833,8 @@ struct elf_final_link_info
};
static bfd_boolean elf_link_output_sym
- (struct elf_final_link_info *, const char *, Elf_Internal_Sym *, asection *);
+ (struct elf_final_link_info *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *);
static bfd_boolean elf_link_flush_output_syms
(struct elf_final_link_info *);
static bfd_boolean elf_link_output_extsym
@@ -3407,7 +3408,8 @@ elf_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
elfsym.st_info = 0;
elfsym.st_other = 0;
elfsym.st_shndx = SHN_UNDEF;
- if (! elf_link_output_sym (&finfo, NULL, &elfsym, bfd_und_section_ptr))
+ if (! elf_link_output_sym (&finfo, NULL, &elfsym, bfd_und_section_ptr,
+ NULL))
goto error_return;
}
@@ -3423,7 +3425,7 @@ elf_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
elfsym.st_other = 0;
elfsym.st_shndx = SHN_ABS;
if (! elf_link_output_sym (&finfo, bfd_get_filename (abfd),
- &elfsym, bfd_abs_section_ptr))
+ &elfsym, bfd_abs_section_ptr, NULL))
goto error_return;
#endif
@@ -3448,7 +3450,7 @@ elf_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
elfsym.st_value = 0;
else
elfsym.st_value = o->vma;
- if (! elf_link_output_sym (&finfo, NULL, &elfsym, o))
+ if (! elf_link_output_sym (&finfo, NULL, &elfsym, o, NULL))
goto error_return;
if (i == SHN_LORESERVE - 1)
i += SHN_HIRESERVE + 1 - SHN_LORESERVE;
@@ -3702,7 +3704,8 @@ elf_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
if (bed->elf_backend_output_arch_syms)
{
typedef bfd_boolean (*out_sym_func)
- (void *, const char *, Elf_Internal_Sym *, asection *);
+ (void *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *);
if (! ((*bed->elf_backend_output_arch_syms)
(abfd, info, &finfo, (out_sym_func) elf_link_output_sym)))
@@ -4086,20 +4089,20 @@ static bfd_boolean
elf_link_output_sym (struct elf_final_link_info *finfo,
const char *name,
Elf_Internal_Sym *elfsym,
- asection *input_sec)
+ asection *input_sec,
+ struct elf_link_hash_entry *h)
{
Elf_External_Sym *dest;
Elf_External_Sym_Shndx *destshndx;
bfd_boolean (*output_symbol_hook)
- (bfd *, struct bfd_link_info *info, const char *,
- Elf_Internal_Sym *, asection *);
+ (struct bfd_link_info *, const char *, Elf_Internal_Sym *, asection *,
+ struct elf_link_hash_entry *);
output_symbol_hook = get_elf_backend_data (finfo->output_bfd)->
elf_backend_link_output_symbol_hook;
if (output_symbol_hook != NULL)
{
- if (! ((*output_symbol_hook)
- (finfo->output_bfd, finfo->info, name, elfsym, input_sec)))
+ if (! (*output_symbol_hook) (finfo->info, name, elfsym, input_sec, h))
return FALSE;
}
@@ -4640,7 +4643,7 @@ elf_link_output_extsym (struct elf_link_hash_entry *h, void *data)
h->indx = bfd_get_symcount (finfo->output_bfd);
- if (! elf_link_output_sym (finfo, h->root.root.string, &sym, input_sec))
+ if (! elf_link_output_sym (finfo, h->root.root.string, &sym, input_sec, h))
{
eoinfo->failed = TRUE;
return FALSE;
@@ -4845,7 +4848,7 @@ elf_link_input_bfd (struct elf_final_link_info *finfo, bfd *input_bfd)
}
}
- if (! elf_link_output_sym (finfo, name, &osym, isec))
+ if (! elf_link_output_sym (finfo, name, &osym, isec, NULL))
return FALSE;
}
@@ -5207,7 +5210,8 @@ elf_link_input_bfd (struct elf_final_link_info *finfo, bfd *input_bfd)
finfo->indices[r_symndx]
= bfd_get_symcount (output_bfd);
- if (! elf_link_output_sym (finfo, name, &sym, sec))
+ if (! elf_link_output_sym (finfo, name, &sym, sec,
+ NULL))
return FALSE;
}
diff --git a/bfd/elfxx-mips.c b/bfd/elfxx-mips.c
index 37a3ee7ac0..09e826b725 100644
--- a/bfd/elfxx-mips.c
+++ b/bfd/elfxx-mips.c
@@ -4818,12 +4818,12 @@ _bfd_mips_elf_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
also where we undo the increment of the value for a mips16 symbol. */
bfd_boolean
-_bfd_mips_elf_link_output_symbol_hook (abfd, info, name, sym, input_sec)
- bfd *abfd ATTRIBUTE_UNUSED;
+_bfd_mips_elf_link_output_symbol_hook (info, name, sym, input_sec, h)
struct bfd_link_info *info ATTRIBUTE_UNUSED;
const char *name ATTRIBUTE_UNUSED;
Elf_Internal_Sym *sym;
asection *input_sec;
+ struct elf_link_hash_entry *h ATTRIBUTE_UNUSED;
{
/* If we see a common symbol, which implies a relocatable link, then
if a symbol was small common in an input file, mark it as small
diff --git a/bfd/elfxx-mips.h b/bfd/elfxx-mips.h
index 924ca535b0..72d9751a53 100644
--- a/bfd/elfxx-mips.h
+++ b/bfd/elfxx-mips.h
@@ -36,8 +36,8 @@ extern bfd_boolean _bfd_mips_elf_add_symbol_hook
PARAMS ((bfd *, struct bfd_link_info *, const Elf_Internal_Sym *,
const char **, flagword *, asection **, bfd_vma *));
extern bfd_boolean _bfd_mips_elf_link_output_symbol_hook
- PARAMS ((bfd *, struct bfd_link_info *, const char *, Elf_Internal_Sym *,
- asection *));
+ PARAMS ((struct bfd_link_info *, const char *, Elf_Internal_Sym *,
+ asection *, struct elf_link_hash_entry *));
extern bfd_boolean _bfd_mips_elf_create_dynamic_sections
PARAMS ((bfd *, struct bfd_link_info *));
extern bfd_boolean _bfd_mips_elf_check_relocs