aboutsummaryrefslogtreecommitdiff
path: root/bfd/elf32-arm.c
diff options
context:
space:
mode:
authorPaul Brook <paul@codesourcery.com>2007-02-22 17:03:59 +0000
committerPaul Brook <paul@codesourcery.com>2007-02-22 17:03:59 +0000
commit6a5bb8757e503d29dd2b0cc656a8747bca71362e (patch)
tree739be2901b553d31859250350c69dc13a3454070 /bfd/elf32-arm.c
parent115d86cfaa1c3ecbf7ce54222a7622a2adb994f9 (diff)
downloadgdb-6a5bb8757e503d29dd2b0cc656a8747bca71362e.zip
gdb-6a5bb8757e503d29dd2b0cc656a8747bca71362e.tar.gz
gdb-6a5bb8757e503d29dd2b0cc656a8747bca71362e.tar.bz2
2007-02-22 Paul Brook <paul@codesourcery.com>
bfd/ * elflink.c (gc_mark_hook_fn): Remove. (_bfd_elf_gc_mark): Rename gc_mark_hook_fn to elf_gc_mark_hook_fn. (bfd_elf_gc_sections): Ditto. Call gc_mark_extra_sections. * elf-bfd.h (elf_gc_mark_hook_fn): Define. (elf_backend_data): Add gc_mark_extra_sections. * elfxx-target.h (elf_backend_gc_mark_extra_sections): Provide default definition. (elfNN_bed): Add elf_backend_gc_mark_extra_sections. * elf32-arm.c (elf32_arm_gc_mark_extra_sections): New function. (elf_backend_gc_mark_extra_sections): Define. ld/testsuite/ * ld-arm/arm-elf.exp (armelftests): Add gc-unwind.h. * ld-arm/gc-unwind.s: New file. * ld-arm/gc-unwind.d: New file.
Diffstat (limited to 'bfd/elf32-arm.c')
-rw-r--r--bfd/elf32-arm.c45
1 files changed, 45 insertions, 0 deletions
diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
index 87d617f..78aa2a0 100644
--- a/bfd/elf32-arm.c
+++ b/bfd/elf32-arm.c
@@ -8150,6 +8150,50 @@ elf32_arm_check_relocs (bfd *abfd, struct bfd_link_info *info,
return TRUE;
}
+/* Unwinding tables are not referenced directly. This pass marks them as
+ required if the corresponding code section is marked. */
+
+static bfd_boolean
+elf32_arm_gc_mark_extra_sections(struct bfd_link_info *info,
+ elf_gc_mark_hook_fn gc_mark_hook)
+{
+ bfd *sub;
+ Elf_Internal_Shdr **elf_shdrp;
+ bfd_boolean again;
+
+ /* Marking EH data may cause additional code sections to be marked,
+ requiring multiple passes. */
+ again = TRUE;
+ while (again)
+ {
+ again = FALSE;
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ {
+ asection *o;
+
+ if (bfd_get_flavour (sub) != bfd_target_elf_flavour)
+ continue;
+
+ elf_shdrp = elf_elfsections (sub);
+ for (o = sub->sections; o != NULL; o = o->next)
+ {
+ Elf_Internal_Shdr *hdr;
+ hdr = &elf_section_data (o)->this_hdr;
+ if (hdr->sh_type == SHT_ARM_EXIDX && hdr->sh_link
+ && !o->gc_mark
+ && elf_shdrp[hdr->sh_link]->bfd_section->gc_mark)
+ {
+ again = TRUE;
+ if (!_bfd_elf_gc_mark (info, o, gc_mark_hook))
+ return FALSE;
+ }
+ }
+ }
+ }
+
+ return TRUE;
+}
+
/* Treat mapping symbols as special target symbols. */
static bfd_boolean
@@ -10532,6 +10576,7 @@ const struct elf_size_info elf32_arm_size_info = {
#define elf_backend_get_symbol_type elf32_arm_get_symbol_type
#define elf_backend_gc_mark_hook elf32_arm_gc_mark_hook
+#define elf_backend_gc_mark_extra_sections elf32_arm_gc_mark_extra_sections
#define elf_backend_gc_sweep_hook elf32_arm_gc_sweep_hook
#define elf_backend_check_relocs elf32_arm_check_relocs
#define elf_backend_relocate_section elf32_arm_relocate_section