This is the mail archive of the
binutils@sources.redhat.com
mailing list for the binutils project.
Re: PATCH: Fix ia64 linker crash when reporting non-pic code error
On Tue, Apr 26, 2005 at 04:40:39PM -0700, James E Wilson wrote:
> On Tue, 2005-04-26 at 15:38, H. J. Lu wrote:
> > * elfxx-ia64.c (elfNN_ia64_relocate_section): Get the local
> > symbol name when reporting non-pic code error.
>
> I see 3 places that use h->root.root.string to report an error for a
> dynamic symbol. You only fixed one of them. I think they should all be
> fixed.
>
> I see 2 existing places that use bfd_elf_string_from_elf_section. You
> are adding a third. If you fix the other 2 cases you missed, then we
> have 5 copies of this code total. I think this should be extracted out
> into a macro or inline function, so that we only have one copy of this
> code.
>
> It isn't clear why the code you added is trivially different than the
> existing two cases. They should all be the same. Looking at
> bfd_elf_string_from_elf_section, I see that it can return NULL, which
> looks like it can only happen if there was an error elsewhere, so the
> existing code for this seems more correct than your version.
>
> Alternatively, looking at elf32-ppc.c, I see that it doesn't use
> bfd_elf_string_from_elf_section for this at all. That is only used if
> it needs to make a bfd_get_section_by_name call. Instead, there is a
> variable sym_name, that gets set from a bfd_elf_sym_name call for local
> symbols, and from h->root.root.string for globals. I see that
> bfd_elf_sym_name calls bfd_elf_string_from_elf_section, so effectively
> this ends up the same result. This may be a better solution. This
> nicely avoids the need for 5 copies of this code, though it does mean
> that we are calling bfd_elf_sym_name many times, which may make the
> linker a little slower.
How about this patch? I modified bfd_elf_sym_name to accept a section
pointer.
H.J.
---
2005-04-27 H.J. Lu <hongjiu.lu@intel.com>
* elf-bfd.h (bfd_elf_sym_name): Also take "asection *".
* elf.c (bfd_elf_sym_name): Updated.
(group_signature): Likewise.
* elf32-ppc.c (ppc_elf_relocate_section): Likewise.
* elf64-ppc.c (ppc64_elf_edit_opd): Likewise.
(ppc64_elf_edit_toc): Likewise.
(ppc64_elf_relocate_section): Likewise.
* elfcode.h (elf_slurp_symbol_table): Likewise.
* elflink.c (elf_link_input_bfd): Likewise.
* elfxx-ia64.c (elfNN_ia64_relocate_section): Call
bfd_elf_sym_name to get local symbol name when reporting errors.
--- bfd/elf-bfd.h.name 2005-04-27 08:29:24.000000000 -0700
+++ bfd/elf-bfd.h 2005-04-27 08:59:50.000000000 -0700
@@ -1374,7 +1374,7 @@ extern Elf_Internal_Sym *bfd_elf_get_elf
(bfd *, Elf_Internal_Shdr *, size_t, size_t, Elf_Internal_Sym *, void *,
Elf_External_Sym_Shndx *);
extern const char *bfd_elf_sym_name
- (bfd *, Elf_Internal_Shdr *, Elf_Internal_Sym *);
+ (bfd *, Elf_Internal_Shdr *, Elf_Internal_Sym *, asection *);
extern bfd_boolean _bfd_elf_copy_private_bfd_data
(bfd *, bfd *);
--- bfd/elf.c.name 2005-04-27 08:29:24.000000000 -0700
+++ bfd/elf.c 2005-04-27 09:12:32.000000000 -0700
@@ -407,10 +407,13 @@ bfd_elf_get_elf_syms (bfd *ibfd,
const char *
bfd_elf_sym_name (bfd *abfd,
Elf_Internal_Shdr *symtab_hdr,
- Elf_Internal_Sym *isym)
+ Elf_Internal_Sym *isym,
+ asection *sym_sec)
{
+ const char *name;
unsigned int iname = isym->st_name;
unsigned int shindex = symtab_hdr->sh_link;
+
if (iname == 0 && ELF_ST_TYPE (isym->st_info) == STT_SECTION
/* Check for a bogus st_shndx to avoid crashing. */
&& isym->st_shndx < elf_numsections (abfd)
@@ -420,7 +423,13 @@ bfd_elf_sym_name (bfd *abfd,
shindex = elf_elfheader (abfd)->e_shstrndx;
}
- return bfd_elf_string_from_elf_section (abfd, shindex, iname);
+ name = bfd_elf_string_from_elf_section (abfd, shindex, iname);
+ if (name == NULL)
+ name = "(null)";
+ else if (sym_sec && *name == '\0')
+ name = bfd_section_name (abfd, sym_sec);
+
+ return name;
}
/* Elf_Internal_Shdr->contents is an array of these for SHT_GROUP
@@ -453,7 +462,7 @@ group_signature (bfd *abfd, Elf_Internal
&isym, esym, &eshndx) == NULL)
return NULL;
- return bfd_elf_sym_name (abfd, hdr, &isym);
+ return bfd_elf_sym_name (abfd, hdr, &isym, NULL);
}
/* Set next_in_group list pointer, and group name for NEWSECT. */
--- bfd/elf32-ppc.c.name 2005-04-19 08:54:09.000000000 -0700
+++ bfd/elf32-ppc.c 2005-04-27 09:01:10.000000000 -0700
@@ -4769,7 +4769,7 @@ ppc_elf_relocate_section (bfd *output_bf
{
sym = local_syms + r_symndx;
sec = local_sections[r_symndx];
- sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym);
+ sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym, sec);
relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
}
@@ -5802,8 +5802,6 @@ ppc_elf_relocate_section (bfd *output_bf
if (r != bfd_reloc_ok)
{
- if (sym_name == NULL)
- sym_name = "(null)";
if (r == bfd_reloc_overflow)
{
if (warned)
--- bfd/elf64-ppc.c.name 2005-04-06 09:00:57.000000000 -0700
+++ bfd/elf64-ppc.c 2005-04-27 09:04:52.000000000 -0700
@@ -6186,7 +6186,8 @@ ppc64_elf_edit_opd (bfd *obfd, struct bf
if (h != NULL)
sym_name = h->root.root.string;
else
- sym_name = bfd_elf_sym_name (ibfd, symtab_hdr, sym);
+ sym_name = bfd_elf_sym_name (ibfd, symtab_hdr, sym,
+ sym_sec);
(*_bfd_error_handler)
(_("%B: undefined sym `%s' in .opd section"),
@@ -7221,7 +7222,8 @@ ppc64_elf_edit_toc (bfd *obfd ATTRIBUTE_
{
(*_bfd_error_handler)
(_("%s defined in removed toc entry"),
- bfd_elf_sym_name (ibfd, symtab_hdr, sym));
+ bfd_elf_sym_name (ibfd, symtab_hdr, sym,
+ NULL));
sym->st_value = 0;
sym->st_shndx = SHN_ABS;
}
@@ -9473,7 +9475,7 @@ ppc64_elf_relocate_section (bfd *output_
sym = local_syms + r_symndx;
sec = local_sections[r_symndx];
- sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym);
+ sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym, sec);
sym_type = ELF64_ST_TYPE (sym->st_info);
relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
opd_adjust = get_opd_info (sec);
--- bfd/elfcode.h.name 2005-04-27 08:29:24.000000000 -0700
+++ bfd/elfcode.h 2005-04-27 09:12:01.000000000 -0700
@@ -1069,7 +1069,7 @@ elf_slurp_symbol_table (bfd *abfd, asymb
memcpy (&sym->internal_elf_sym, isym, sizeof (Elf_Internal_Sym));
sym->symbol.the_bfd = abfd;
- sym->symbol.name = bfd_elf_sym_name (abfd, hdr, isym);
+ sym->symbol.name = bfd_elf_sym_name (abfd, hdr, isym, NULL);
sym->symbol.value = isym->st_value;
--- bfd/elflink.c.name 2005-04-27 08:29:24.000000000 -0700
+++ bfd/elflink.c 2005-04-27 09:10:38.000000000 -0700
@@ -7159,7 +7159,9 @@ elf_link_input_bfd (struct elf_final_lin
{
Elf_Internal_Sym *sym = isymbuf + r_symndx;
ps = &finfo->sections[r_symndx];
- sym_name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym);
+ sym_name = bfd_elf_sym_name (input_bfd,
+ symtab_hdr,
+ sym, *ps);
}
/* Complain if the definition comes from a
--- bfd/elfxx-ia64.c.name 2005-04-27 08:29:24.000000000 -0700
+++ bfd/elfxx-ia64.c 2005-04-27 09:09:06.000000000 -0700
@@ -4050,7 +4050,9 @@ elfNN_ia64_relocate_section (output_bfd,
(*_bfd_error_handler)
(_("%B: non-pic code with imm relocation against dynamic symbol `%s'"),
input_bfd,
- h->root.root.string);
+ h ? h->root.root.string
+ : bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
+ sym_sec));
ret_val = FALSE;
continue;
@@ -4114,7 +4116,10 @@ elfNN_ia64_relocate_section (output_bfd,
{
(*_bfd_error_handler)
(_("%B: @gprel relocation against dynamic symbol %s"),
- input_bfd, h->root.root.string);
+ input_bfd,
+ h ? h->root.root.string
+ : bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
+ sym_sec));
ret_val = FALSE;
continue;
}
@@ -4315,7 +4320,12 @@ elfNN_ia64_relocate_section (output_bfd,
msg = _("%B: speculation fixup to dynamic symbol %s");
else
msg = _("%B: @pcrel relocation against dynamic symbol %s");
- (*_bfd_error_handler) (msg, input_bfd, h->root.root.string);
+ (*_bfd_error_handler) (msg, input_bfd,
+ h ? h->root.root.string
+ : bfd_elf_sym_name (input_bfd,
+ symtab_hdr,
+ sym,
+ sym_sec));
ret_val = FALSE;
continue;
}
@@ -4541,15 +4551,8 @@ elfNN_ia64_relocate_section (output_bfd,
if (h)
name = h->root.root.string;
else
- {
- name = bfd_elf_string_from_elf_section (input_bfd,
- symtab_hdr->sh_link,
- sym->st_name);
- if (name == NULL)
- return FALSE;
- if (*name == '\0')
- name = bfd_section_name (input_bfd, sym_sec);
- }
+ name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
+ sym_sec);
switch (r_type)
{