aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Henderson <rth@redhat.com>2002-03-02 01:24:50 +0000
committerRichard Henderson <rth@redhat.com>2002-03-02 01:24:50 +0000
commit30831527a496163c41800021c20596dc252d4cc7 (patch)
treefc37f98a0404fb1933faf6fcf36af7a63006c49d
parent841ac7901d408fa9ebc97db8a939800431d3b9e7 (diff)
downloadfsf-binutils-gdb-30831527a496163c41800021c20596dc252d4cc7.zip
fsf-binutils-gdb-30831527a496163c41800021c20596dc252d4cc7.tar.gz
fsf-binutils-gdb-30831527a496163c41800021c20596dc252d4cc7.tar.bz2
* elflink.h (size_dynamic_sections): If section named
".preinit_array" exists, create DT_PREINIT_ARRAY and DT_PREINIT_ARRAYSZ entries in dynamic table. Analogously for ".init_array" and ".fini_array". (elf_bfd_final_link): Handle DT_PREINIT_ARRAYSZ, DT_INIT_ARRAYSZ, DT_FINI_ARRAYSZ, DT_PREINIT_ARRAY, DT_INIT_ARRAY, and DT_FINI_ARRAY.
-rw-r--r--bfd/ChangeLog10
-rw-r--r--bfd/elflink.h66
2 files changed, 75 insertions, 1 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index a381bfc..09dea78 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,3 +1,13 @@
+2002-03-01 David Mosberger <davidm@hpl.hp.com>
+
+ * elflink.h (size_dynamic_sections): If section named
+ ".preinit_array" exists, create DT_PREINIT_ARRAY and
+ DT_PREINIT_ARRAYSZ entries in dynamic table. Analogously for
+ ".init_array" and ".fini_array".
+ (elf_bfd_final_link): Handle DT_PREINIT_ARRAYSZ, DT_INIT_ARRAYSZ,
+ DT_FINI_ARRAYSZ, DT_PREINIT_ARRAY, DT_INIT_ARRAY, and
+ DT_FINI_ARRAY.
+
2002-02-26 Andrew Macleod <amacleod@cygnus.com>
* elflink.h (elf_bfd_final_link): Don't crash on SHN_UNDEF local
diff --git a/bfd/elflink.h b/bfd/elflink.h
index 76dbb19..7fd8b53 100644
--- a/bfd/elflink.h
+++ b/bfd/elflink.h
@@ -3029,7 +3029,9 @@ NAME(bfd_elf,size_dynamic_sections) (output_bfd, soname, rpath,
struct bfd_elf_version_tree *verdefs;
{
bfd_size_type soname_indx;
- bfd *dynobj;
+ bfd *dynobj, *sub;
+ asection *o;
+ int need_preinit_array = 0, need_init_array = 0, need_fini_array = 0;
struct elf_backend_data *bed;
struct elf_assign_sym_version_info asvinfo;
@@ -3200,6 +3202,43 @@ NAME(bfd_elf,size_dynamic_sections) (output_bfd, soname, rpath,
return false;
}
+ for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
+ for (o = sub->sections; o != NULL; o = o->next)
+ {
+ /* yuck, more matching by name... */
+
+ if (strcmp (bfd_section_name (sub, o), ".preinit_array") == 0)
+ need_preinit_array = 1;
+ if (strcmp (bfd_section_name (sub, o), ".init_array") == 0)
+ need_init_array = 1;
+ if (strcmp (bfd_section_name (sub, o), ".fini_array") == 0)
+ need_fini_array = 1;
+ }
+ if (need_preinit_array)
+ {
+ if (!elf_add_dynamic_entry (info, (bfd_vma) DT_PREINIT_ARRAY,
+ (bfd_vma) 0)
+ || !elf_add_dynamic_entry (info, (bfd_vma) DT_PREINIT_ARRAYSZ,
+ (bfd_vma) 0))
+ return false;
+ }
+ if (need_init_array)
+ {
+ if (!elf_add_dynamic_entry (info, (bfd_vma) DT_INIT_ARRAY,
+ (bfd_vma) 0)
+ || !elf_add_dynamic_entry (info, (bfd_vma) DT_INIT_ARRAYSZ,
+ (bfd_vma) 0))
+ return false;
+ }
+ if (need_fini_array)
+ {
+ if (!elf_add_dynamic_entry (info, (bfd_vma) DT_FINI_ARRAY,
+ (bfd_vma) 0)
+ || !elf_add_dynamic_entry (info, (bfd_vma) DT_FINI_ARRAYSZ,
+ (bfd_vma) 0))
+ return false;
+ }
+
dynstr = bfd_get_section_by_name (dynobj, ".dynstr");
/* If .dynstr is excluded from the link, we don't want any of
these tags. Strictly, we should be checking each section
@@ -5550,6 +5589,31 @@ elf_bfd_final_link (abfd, info)
}
break;
+ case DT_PREINIT_ARRAYSZ:
+ name = ".preinit_array";
+ goto get_size;
+ case DT_INIT_ARRAYSZ:
+ name = ".init_array";
+ goto get_size;
+ case DT_FINI_ARRAYSZ:
+ name = ".fini_array";
+ get_size:
+ o = bfd_get_section_by_name (abfd, name);
+ BFD_ASSERT (o != NULL);
+ dyn.d_un.d_val = o->_raw_size;
+ elf_swap_dyn_out (dynobj, &dyn, dyncon);
+ break;
+
+ case DT_PREINIT_ARRAY:
+ name = ".preinit_array";
+ goto get_vma;
+ case DT_INIT_ARRAY:
+ name = ".init_array";
+ goto get_vma;
+ case DT_FINI_ARRAY:
+ name = ".fini_array";
+ goto get_vma;
+
case DT_HASH:
name = ".hash";
goto get_vma;