diff options
author | H.J. Lu <hjl.tools@gmail.com> | 2005-05-04 13:19:02 +0000 |
---|---|---|
committer | H.J. Lu <hjl.tools@gmail.com> | 2005-05-04 13:19:02 +0000 |
commit | f652615e8c2bba008e66f8eaf11a42650b714086 (patch) | |
tree | b10e04752515f4bafd6ced0dba1df6c81c6c876c | |
parent | c5e2ceadb7216936dcc3d9dec73de31075460765 (diff) | |
download | gdb-f652615e8c2bba008e66f8eaf11a42650b714086.zip gdb-f652615e8c2bba008e66f8eaf11a42650b714086.tar.gz gdb-f652615e8c2bba008e66f8eaf11a42650b714086.tar.bz2 |
bfd/
2005-05-04 H.J. Lu <hongjiu.lu@intel.com>
* bfd-in.h (_bfd_elf_provide_section_bound_symbols): New.
* bfd-in2.h: Regenerated.
* elflink.c (bfd_elf_set_symbol): New.
(_bfd_elf_provide_symbol): Call it.
(_bfd_elf_provide_section_bound_symbols): New.
ld/
2005-05-04 H.J. Lu <hongjiu.lu@intel.com>
* emultempl/elf32.em (gld${EMULATION_NAME}_provide_bound_symbols):
Call _bfd_elf_provide_section_bound_symbols.
-rw-r--r-- | bfd/ChangeLog | 9 | ||||
-rw-r--r-- | bfd/bfd-in.h | 3 | ||||
-rw-r--r-- | bfd/bfd-in2.h | 3 | ||||
-rw-r--r-- | bfd/elflink.c | 74 | ||||
-rw-r--r-- | ld/ChangeLog | 5 | ||||
-rw-r--r-- | ld/emultempl/elf32.em | 31 |
6 files changed, 89 insertions, 36 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog index 2b010e8..a05a025 100644 --- a/bfd/ChangeLog +++ b/bfd/ChangeLog @@ -1,5 +1,14 @@ 2005-05-04 H.J. Lu <hongjiu.lu@intel.com> + * bfd-in.h (_bfd_elf_provide_section_bound_symbols): New. + * bfd-in2.h: Regenerated. + + * elflink.c (bfd_elf_set_symbol): New. + (_bfd_elf_provide_symbol): Call it. + (_bfd_elf_provide_section_bound_symbols): New. + +2005-05-04 H.J. Lu <hongjiu.lu@intel.com> + * elflink.c (_bfd_elf_merge_symbol): Only skip weak definitions at the end, if a strong definition has already been seen. diff --git a/bfd/bfd-in.h b/bfd/bfd-in.h index 2aa6bbb..101930f 100644 --- a/bfd/bfd-in.h +++ b/bfd/bfd-in.h @@ -700,6 +700,9 @@ extern struct bfd_section *_bfd_elf_tls_setup extern void _bfd_elf_provide_symbol (struct bfd_link_info *, const char *, bfd_vma); +extern void _bfd_elf_provide_section_bound_symbols + (struct bfd_link_info *, struct bfd_section *sec, const char *, const char *); + extern bfd_boolean bfd_m68k_elf32_create_embedded_relocs (bfd *, struct bfd_link_info *, struct bfd_section *, struct bfd_section *, char **); diff --git a/bfd/bfd-in2.h b/bfd/bfd-in2.h index 45060f8..45b09146 100644 --- a/bfd/bfd-in2.h +++ b/bfd/bfd-in2.h @@ -707,6 +707,9 @@ extern struct bfd_section *_bfd_elf_tls_setup extern void _bfd_elf_provide_symbol (struct bfd_link_info *, const char *, bfd_vma); +extern void _bfd_elf_provide_section_bound_symbols + (struct bfd_link_info *, struct bfd_section *sec, const char *, const char *); + extern bfd_boolean bfd_m68k_elf32_create_embedded_relocs (bfd *, struct bfd_link_info *, struct bfd_section *, struct bfd_section *, char **); diff --git a/bfd/elflink.c b/bfd/elflink.c index 370a9b7..9e76d06 100644 --- a/bfd/elflink.c +++ b/bfd/elflink.c @@ -9824,6 +9824,18 @@ _bfd_elf_section_already_linked (bfd *abfd, struct bfd_section * sec) bfd_section_already_linked_table_insert (already_linked_list, sec); } +static void +bfd_elf_set_symbol (struct elf_link_hash_entry *h, bfd_vma val) +{ + h->root.type = bfd_link_hash_defined; + h->root.u.def.section = bfd_abs_section_ptr; + h->root.u.def.value = val; + h->def_regular = 1; + h->type = STT_OBJECT; + h->other = STV_HIDDEN | (h->other & ~ ELF_ST_VISIBILITY (-1)); + h->forced_local = 1; +} + /* Set NAME to VAL if the symbol exists and is undefined. */ void @@ -9836,13 +9848,61 @@ _bfd_elf_provide_symbol (struct bfd_link_info *info, const char *name, FALSE); if (h != NULL && (h->root.type == bfd_link_hash_undefined || h->root.type == bfd_link_hash_undefweak)) + bfd_elf_set_symbol (h, val); +} + +/* Set START and END to boundaries of SEC if they exist and are + undefined. */ + +void +_bfd_elf_provide_section_bound_symbols (struct bfd_link_info *info, + asection *sec, + const char *start, + const char *end) +{ + struct elf_link_hash_entry *hs, *he; + bfd_vma start_val, end_val; + bfd_boolean do_start, do_end; + + /* Check if we need them or not first. */ + hs = elf_link_hash_lookup (elf_hash_table (info), start, FALSE, + FALSE, FALSE); + do_start = (hs != NULL + && (hs->root.type == bfd_link_hash_undefined + || hs->root.type == bfd_link_hash_undefweak)); + + he = elf_link_hash_lookup (elf_hash_table (info), end, FALSE, + FALSE, FALSE); + do_end = (he != NULL + && (he->root.type == bfd_link_hash_undefined + || he->root.type == bfd_link_hash_undefweak)); + + if (!do_start && !do_end) + return; + + if (sec != NULL) { - h->root.type = bfd_link_hash_defined; - h->root.u.def.section = bfd_abs_section_ptr; - h->root.u.def.value = val; - h->def_regular = 1; - h->type = STT_OBJECT; - h->other = STV_HIDDEN | (h->other & ~ ELF_ST_VISIBILITY (-1)); - h->forced_local = 1; + start_val = sec->vma; + end_val = start_val + sec->size; } + else + { + /* We have to choose those values very carefully. Some targets, + like alpha, may have relocation overflow with 0. "_edata" + should be defined in all cases. */ + struct elf_link_hash_entry *h + = elf_link_hash_lookup (elf_hash_table (info), "_edata", + FALSE, FALSE, FALSE); + if (h != NULL && h->root.type == bfd_link_hash_defined) + start_val = h->root.u.def.value; + else + start_val = 0; + end_val = start_val; + } + + if (do_start) + bfd_elf_set_symbol (hs, start_val); + + if (do_end) + bfd_elf_set_symbol (he, end_val); } diff --git a/ld/ChangeLog b/ld/ChangeLog index 2448124..4e8bae8 100644 --- a/ld/ChangeLog +++ b/ld/ChangeLog @@ -1,3 +1,8 @@ +2005-05-04 H.J. Lu <hongjiu.lu@intel.com> + + * emultempl/elf32.em (gld${EMULATION_NAME}_provide_bound_symbols): + Call _bfd_elf_provide_section_bound_symbols. + 2005-05-04 Alan Modra <amodra@bigpond.net.au> * ldemul.c: Include bfdlink.h. diff --git a/ld/emultempl/elf32.em b/ld/emultempl/elf32.em index 641cd63..fb6efb1 100644 --- a/ld/emultempl/elf32.em +++ b/ld/emultempl/elf32.em @@ -1453,35 +1453,8 @@ gld${EMULATION_NAME}_provide_bound_symbols (const char *sec, const char *start, const char *end) { - asection *s; - bfd_vma start_val, end_val; - - s = bfd_get_section_by_name (output_bfd, sec); - if (s != NULL) - { - start_val = s->vma; - end_val = start_val + s->size; - } - else - { - /* We have to choose those values very carefully. Some targets, - like alpha, may have relocation overflow with 0. We use the - first SEC_ALLOC section which isn't SEC_READONLY or the last - SEC_ALLOC section. */ - start_val = 0; - for (s = output_bfd->sections; s != NULL; s = s->next) - { - if ((s->flags & SEC_ALLOC) != 0) - { - start_val = s->vma; - if ((s->flags & SEC_READONLY) == 0) - break; - } - } - end_val = start_val; - } - _bfd_elf_provide_symbol (&link_info, start, start_val); - _bfd_elf_provide_symbol (&link_info, end, end_val); + asection *s = bfd_get_section_by_name (output_bfd, sec); + _bfd_elf_provide_section_bound_symbols (&link_info, s, start, end); } /* If not building a shared library, provide |