diff options
author | Richard Sandiford <rdsandiford@googlemail.com> | 2009-03-14 09:35:06 +0000 |
---|---|---|
committer | Richard Sandiford <rdsandiford@googlemail.com> | 2009-03-14 09:35:06 +0000 |
commit | 7d504122ef2032b3e0d6973a4f4f138481c4b5c2 (patch) | |
tree | dfa07a68fffdd8cf41538e97576ee2a34f8b7c31 /bfd/xcofflink.c | |
parent | 8602d4fea60dda606ad5e5e01e27f8f841120e15 (diff) | |
download | gdb-7d504122ef2032b3e0d6973a4f4f138481c4b5c2.zip gdb-7d504122ef2032b3e0d6973a4f4f138481c4b5c2.tar.gz gdb-7d504122ef2032b3e0d6973a4f4f138481c4b5c2.tar.bz2 |
bfd/
* xcofflink.c (xcoff_mark_symbol_by_name): New function.
(bfd_xcoff_size_dynamic_sections): Use it to mark the entry,
init and fini functions. Do garbage collection for objects
without an entry point too.
ld/testsuite/
* ld-powerpc/aix-gc-1.s, ld-powerpc/aix-gc-1.ex,
ld-powerpc/aix-gc-1-32.dd, ld-powerpc/aix-gc-1-64.dd,
ld-powerpc/aix-weak-1-gcdso.dnd, ld-powerpc/aix-weak-1-gcdso.hd,
ld-powerpc/aix-weak-1-gcdso.nd: New tests.
* ld-powerpc/aix52.exp: Run them.
Diffstat (limited to 'bfd/xcofflink.c')
-rw-r--r-- | bfd/xcofflink.c | 49 |
1 files changed, 33 insertions, 16 deletions
diff --git a/bfd/xcofflink.c b/bfd/xcofflink.c index d87940c..3ca9b72 100644 --- a/bfd/xcofflink.c +++ b/bfd/xcofflink.c @@ -2482,6 +2482,30 @@ xcoff_mark_symbol (struct bfd_link_info *info, struct xcoff_link_hash_entry *h) return TRUE; } +/* Look for a symbol called NAME. If the symbol is defined, mark it. + If the symbol exists, set FLAGS. */ + +static bfd_boolean +xcoff_mark_symbol_by_name (struct bfd_link_info *info, + const char *name, unsigned int flags) +{ + struct xcoff_link_hash_entry *h; + + h = xcoff_link_hash_lookup (xcoff_hash_table (info), name, + FALSE, FALSE, TRUE); + if (h != NULL) + { + h->flags |= flags; + if (h->root.type == bfd_link_hash_defined + || h->root.type == bfd_link_hash_defweak) + { + if (!xcoff_mark (info, h->root.u.def.section)) + return FALSE; + } + } + return TRUE; +} + /* The mark phase of garbage collection. For a given section, mark it, and all the sections which define symbols to which it refers. Because this function needs to look at the relocs, we also count @@ -3177,7 +3201,6 @@ bfd_xcoff_size_dynamic_sections (bfd *output_bfd, asection **special_sections, bfd_boolean rtld) { - struct xcoff_link_hash_entry *hentry; asection *lsec; struct xcoff_loader_info ldinfo; int i; @@ -3216,15 +3239,6 @@ bfd_xcoff_size_dynamic_sections (bfd *output_bfd, xcoff_hash_table (info)->textro = textro; xcoff_hash_table (info)->rtld = rtld; - hentry = NULL; - if (entry != NULL) - { - hentry = xcoff_link_hash_lookup (xcoff_hash_table (info), entry, - FALSE, FALSE, TRUE); - if (hentry != NULL) - hentry->flags |= XCOFF_ENTRY; - } - /* __rtinit */ if (info->init_function || info->fini_function || rtld) { @@ -3277,11 +3291,7 @@ bfd_xcoff_size_dynamic_sections (bfd *output_bfd, } /* Garbage collect unused sections. */ - if (info->relocatable - || ! gc - || hentry == NULL - || (hentry->root.type != bfd_link_hash_defined - && hentry->root.type != bfd_link_hash_defweak)) + if (info->relocatable || !gc) { gc = FALSE; xcoff_hash_table (info)->gc = FALSE; @@ -3309,7 +3319,14 @@ bfd_xcoff_size_dynamic_sections (bfd *output_bfd, } else { - if (! xcoff_mark (info, hentry->root.u.def.section)) + if (entry != NULL + && !xcoff_mark_symbol_by_name (info, entry, XCOFF_ENTRY)) + goto error_return; + if (info->init_function != NULL + && !xcoff_mark_symbol_by_name (info, info->init_function, 0)) + goto error_return; + if (info->fini_function != NULL + && !xcoff_mark_symbol_by_name (info, info->fini_function, 0)) goto error_return; xcoff_sweep (info); xcoff_hash_table (info)->gc = TRUE; |