PR 4497
* elf-eh-frame.c (struct cie): Add "local_personality". Make "personality" a union. (cie_eq): Compare local_personality too. Adjust personality comparison. (_bfd_elf_discard_section_eh_frame): Check binding on personality reloc sym to allow for bad symtab. Use stashed local syms rather than reading personality local sym. Handle discarded sections.
This commit is contained in:
parent
4f4416b5f9
commit
f137a54e7a
|
@ -1,3 +1,14 @@
|
||||||
|
2007-05-12 Alan Modra <amodra@bigpond.net.au>
|
||||||
|
|
||||||
|
PR 4497
|
||||||
|
* elf-eh-frame.c (struct cie): Add "local_personality". Make
|
||||||
|
"personality" a union.
|
||||||
|
(cie_eq): Compare local_personality too. Adjust personality
|
||||||
|
comparison.
|
||||||
|
(_bfd_elf_discard_section_eh_frame): Check binding on personality
|
||||||
|
reloc sym to allow for bad symtab. Use stashed local syms rather
|
||||||
|
than reading personality local sym. Handle discarded sections.
|
||||||
|
|
||||||
2007-05-12 Alan Modra <amodra@bigpond.net.au>
|
2007-05-12 Alan Modra <amodra@bigpond.net.au>
|
||||||
|
|
||||||
* elf32-spu.c (elf_howto_table): Add howto for R_SPU_ADDR16X.
|
* elf32-spu.c (elf_howto_table): Add howto for R_SPU_ADDR16X.
|
||||||
|
|
|
@ -32,12 +32,16 @@ struct cie
|
||||||
unsigned int length;
|
unsigned int length;
|
||||||
unsigned int hash;
|
unsigned int hash;
|
||||||
unsigned char version;
|
unsigned char version;
|
||||||
|
unsigned char local_personality;
|
||||||
char augmentation[20];
|
char augmentation[20];
|
||||||
bfd_vma code_align;
|
bfd_vma code_align;
|
||||||
bfd_signed_vma data_align;
|
bfd_signed_vma data_align;
|
||||||
bfd_vma ra_column;
|
bfd_vma ra_column;
|
||||||
bfd_vma augmentation_size;
|
bfd_vma augmentation_size;
|
||||||
bfd_vma personality;
|
union {
|
||||||
|
struct elf_link_hash_entry *h;
|
||||||
|
bfd_vma val;
|
||||||
|
} personality;
|
||||||
asection *output_sec;
|
asection *output_sec;
|
||||||
struct eh_cie_fde *cie_inf;
|
struct eh_cie_fde *cie_inf;
|
||||||
unsigned char per_encoding;
|
unsigned char per_encoding;
|
||||||
|
@ -216,13 +220,15 @@ cie_eq (const void *e1, const void *e2)
|
||||||
if (c1->hash == c2->hash
|
if (c1->hash == c2->hash
|
||||||
&& c1->length == c2->length
|
&& c1->length == c2->length
|
||||||
&& c1->version == c2->version
|
&& c1->version == c2->version
|
||||||
|
&& c1->local_personality == c2->local_personality
|
||||||
&& strcmp (c1->augmentation, c2->augmentation) == 0
|
&& strcmp (c1->augmentation, c2->augmentation) == 0
|
||||||
&& strcmp (c1->augmentation, "eh") != 0
|
&& strcmp (c1->augmentation, "eh") != 0
|
||||||
&& c1->code_align == c2->code_align
|
&& c1->code_align == c2->code_align
|
||||||
&& c1->data_align == c2->data_align
|
&& c1->data_align == c2->data_align
|
||||||
&& c1->ra_column == c2->ra_column
|
&& c1->ra_column == c2->ra_column
|
||||||
&& c1->augmentation_size == c2->augmentation_size
|
&& c1->augmentation_size == c2->augmentation_size
|
||||||
&& c1->personality == c2->personality
|
&& memcmp (&c1->personality, &c2->personality,
|
||||||
|
sizeof (c1->personality)) == 0
|
||||||
&& c1->output_sec == c2->output_sec
|
&& c1->output_sec == c2->output_sec
|
||||||
&& c1->per_encoding == c2->per_encoding
|
&& c1->per_encoding == c2->per_encoding
|
||||||
&& c1->lsda_encoding == c2->lsda_encoding
|
&& c1->lsda_encoding == c2->lsda_encoding
|
||||||
|
@ -670,12 +676,10 @@ _bfd_elf_discard_section_eh_frame
|
||||||
REQUIRE (skip_bytes (&buf, end, length));
|
REQUIRE (skip_bytes (&buf, end, length));
|
||||||
}
|
}
|
||||||
ENSURE_NO_RELOCS (buf);
|
ENSURE_NO_RELOCS (buf);
|
||||||
/* Ensure we have a reloc here, against
|
/* Ensure we have a reloc here. */
|
||||||
a global symbol. */
|
|
||||||
if (GET_RELOC (buf) != NULL)
|
if (GET_RELOC (buf) != NULL)
|
||||||
{
|
{
|
||||||
unsigned long r_symndx;
|
unsigned long r_symndx;
|
||||||
asection *sym_sec = NULL;
|
|
||||||
|
|
||||||
#ifdef BFD64
|
#ifdef BFD64
|
||||||
if (ptr_size == 8)
|
if (ptr_size == 8)
|
||||||
|
@ -683,7 +687,9 @@ _bfd_elf_discard_section_eh_frame
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
r_symndx = ELF32_R_SYM (cookie->rel->r_info);
|
r_symndx = ELF32_R_SYM (cookie->rel->r_info);
|
||||||
if (r_symndx >= cookie->locsymcount)
|
if (r_symndx >= cookie->locsymcount
|
||||||
|
|| ELF_ST_BIND (cookie->locsyms[r_symndx]
|
||||||
|
.st_info) != STB_LOCAL)
|
||||||
{
|
{
|
||||||
struct elf_link_hash_entry *h;
|
struct elf_link_hash_entry *h;
|
||||||
|
|
||||||
|
@ -695,33 +701,29 @@ _bfd_elf_discard_section_eh_frame
|
||||||
h = (struct elf_link_hash_entry *)
|
h = (struct elf_link_hash_entry *)
|
||||||
h->root.u.i.link;
|
h->root.u.i.link;
|
||||||
|
|
||||||
if (h->root.type == bfd_link_hash_defined
|
cie->personality.h = h;
|
||||||
|| h->root.type == bfd_link_hash_defweak)
|
|
||||||
{
|
|
||||||
cie->personality = h->root.u.def.value;
|
|
||||||
sym_sec = h->root.u.def.section;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Elf_Internal_Shdr *symtab_hdr;
|
|
||||||
Elf_Internal_Sym *sym;
|
Elf_Internal_Sym *sym;
|
||||||
|
asection *sym_sec;
|
||||||
|
bfd_vma val;
|
||||||
|
|
||||||
symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
|
sym = &cookie->locsyms[r_symndx];
|
||||||
sym = bfd_elf_get_elf_syms (abfd, symtab_hdr,
|
sym_sec = (bfd_section_from_elf_index
|
||||||
1, r_symndx,
|
(abfd, sym->st_shndx));
|
||||||
NULL, NULL, NULL);
|
if (sym_sec->kept_section != NULL)
|
||||||
if (sym != NULL)
|
sym_sec = sym_sec->kept_section;
|
||||||
|
if (sym_sec != NULL
|
||||||
|
&& sym_sec->output_section != NULL)
|
||||||
{
|
{
|
||||||
cie->personality = sym->st_value;
|
val = (sym->st_value
|
||||||
sym_sec = (bfd_section_from_elf_index
|
+ sym_sec->output_offset
|
||||||
(abfd, sym->st_shndx));
|
+ sym_sec->output_section->vma);
|
||||||
free (sym);
|
cie->personality.val = val;
|
||||||
|
cie->local_personality = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (sym_sec != NULL)
|
|
||||||
cie->personality += (sym_sec->output_section->vma
|
|
||||||
+ sym_sec->output_offset);
|
|
||||||
|
|
||||||
/* Cope with MIPS-style composite relocations. */
|
/* Cope with MIPS-style composite relocations. */
|
||||||
do
|
do
|
||||||
|
@ -729,7 +731,7 @@ _bfd_elf_discard_section_eh_frame
|
||||||
while (GET_RELOC (buf) != NULL);
|
while (GET_RELOC (buf) != NULL);
|
||||||
}
|
}
|
||||||
REQUIRE (skip_bytes (&buf, end, per_width));
|
REQUIRE (skip_bytes (&buf, end, per_width));
|
||||||
REQUIRE (cie->personality);
|
REQUIRE (cie->local_personality || cie->personality.h);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
|
Loading…
Reference in New Issue