diff options
Diffstat (limited to 'bfd/elfxx-ia64.c')
-rw-r--r-- | bfd/elfxx-ia64.c | 59 |
1 files changed, 31 insertions, 28 deletions
diff --git a/bfd/elfxx-ia64.c b/bfd/elfxx-ia64.c index 2996485..20d9083 100644 --- a/bfd/elfxx-ia64.c +++ b/bfd/elfxx-ia64.c @@ -1,5 +1,6 @@ /* IA-64 support for 64-bit ELF - Copyright 1998, 1999, 2000, 2001, 2002, 2003 Free Software Foundation, Inc. + Copyright 1998, 1999, 2000, 2001, 2002, 2003, 2004 + Free Software Foundation, Inc. Contributed by David Mosberger-Tang <davidm@hpl.hp.com> This file is part of BFD, the Binary File Descriptor library. @@ -92,6 +93,9 @@ struct elfNN_ia64_dyn_sym_info asection *srel; int type; int count; + + /* Is this reloc against readonly section? */ + bfd_boolean reltext; } *reloc_entries; /* TRUE when the section contents have been updated. */ @@ -182,13 +186,13 @@ static bfd_boolean is_unwind_section_name static bfd_boolean elfNN_ia64_section_from_shdr PARAMS ((bfd *, Elf_Internal_Shdr *, const char *)); static bfd_boolean elfNN_ia64_section_flags - PARAMS ((flagword *, Elf_Internal_Shdr *)); + PARAMS ((flagword *, const Elf_Internal_Shdr *)); static bfd_boolean elfNN_ia64_fake_sections PARAMS ((bfd *abfd, Elf_Internal_Shdr *hdr, asection *sec)); static void elfNN_ia64_final_write_processing PARAMS ((bfd *abfd, bfd_boolean linker)); static bfd_boolean elfNN_ia64_add_symbol_hook - PARAMS ((bfd *abfd, struct bfd_link_info *info, const Elf_Internal_Sym *sym, + PARAMS ((bfd *abfd, struct bfd_link_info *info, Elf_Internal_Sym *sym, const char **namep, flagword *flagsp, asection **secp, bfd_vma *valp)); static int elfNN_ia64_additional_program_headers @@ -243,9 +247,6 @@ static asection *get_pltoff static asection *get_reloc_section PARAMS ((bfd *abfd, struct elfNN_ia64_link_hash_table *ia64_info, asection *sec, bfd_boolean create)); -static bfd_boolean count_dyn_reloc - PARAMS ((bfd *abfd, struct elfNN_ia64_dyn_sym_info *dyn_i, - asection *srel, int type)); static bfd_boolean elfNN_ia64_check_relocs PARAMS ((bfd *abfd, struct bfd_link_info *info, asection *sec, const Elf_Internal_Rela *relocs)); @@ -1270,7 +1271,7 @@ elfNN_ia64_section_from_shdr (abfd, hdr, name) static bfd_boolean elfNN_ia64_section_flags (flags, hdr) flagword *flags; - Elf_Internal_Shdr *hdr; + const Elf_Internal_Shdr *hdr; { if (hdr->sh_flags & SHF_IA_64_SHORT) *flags |= SEC_SMALL_DATA; @@ -1429,7 +1430,7 @@ static bfd_boolean elfNN_ia64_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp) bfd *abfd; struct bfd_link_info *info; - const Elf_Internal_Sym *sym; + Elf_Internal_Sym *sym; const char **namep ATTRIBUTE_UNUSED; flagword *flagsp ATTRIBUTE_UNUSED; asection **secp; @@ -2175,18 +2176,12 @@ get_reloc_section (abfd, ia64_info, sec, create) return NULL; } - if (sec->flags & SEC_READONLY) - ia64_info->reltext = 1; - return srel; } static bfd_boolean -count_dyn_reloc (abfd, dyn_i, srel, type) - bfd *abfd; - struct elfNN_ia64_dyn_sym_info *dyn_i; - asection *srel; - int type; +count_dyn_reloc (bfd *abfd, struct elfNN_ia64_dyn_sym_info *dyn_i, + asection *srel, int type, bfd_boolean reltext) { struct elfNN_ia64_dyn_reloc_entry *rent; @@ -2207,6 +2202,7 @@ count_dyn_reloc (abfd, dyn_i, srel, type) rent->count = 0; dyn_i->reloc_entries = rent; } + rent->reltext = reltext; rent->count++; return TRUE; @@ -2463,7 +2459,7 @@ elfNN_ia64_check_relocs (abfd, info, sec, relocs) dynamic symbol table. */ if (!h && info->shared) { - if (! (_bfd_elfNN_link_record_local_dynamic_symbol + if (! (bfd_elf_link_record_local_dynamic_symbol (info, abfd, (long) r_symndx))) return FALSE; } @@ -2491,7 +2487,8 @@ elfNN_ia64_check_relocs (abfd, info, sec, relocs) if (!srel) return FALSE; } - if (!count_dyn_reloc (abfd, dyn_i, srel, dynrel_type)) + if (!count_dyn_reloc (abfd, dyn_i, srel, dynrel_type, + (sec->flags & SEC_READONLY) != 0)) return FALSE; } } @@ -2634,7 +2631,7 @@ allocate_fptr (dyn_i, data) BFD_ASSERT ((h->root.type == bfd_link_hash_defined) || (h->root.type == bfd_link_hash_defweak)); - if (!_bfd_elfNN_link_record_local_dynamic_symbol + if (!bfd_elf_link_record_local_dynamic_symbol (x->info, h->root.u.def.section->owner, global_sym_index (h))) return FALSE; @@ -2798,6 +2795,8 @@ allocate_dynrel_entries (dyn_i, data) default: abort (); } + if (rent->reltext) + ia64_info->reltext = 1; rent->srel->_raw_size += sizeof (ElfNN_External_Rela) * count; } @@ -2942,8 +2941,12 @@ elfNN_ia64_size_dynamic_sections (output_bfd, info) data.ofs = (data.ofs + 31) & (bfd_vma) -32; elfNN_ia64_dyn_sym_traverse (ia64_info, allocate_plt2_entries, &data); - if (data.ofs != 0) + if (data.ofs != 0 || ia64_info->root.dynamic_sections_created) { + /* FIXME: we always reserve the memory for dynamic linker even if + there are no PLT entries since dynamic linker may assume the + reserved memory always exists. */ + BFD_ASSERT (ia64_info->root.dynamic_sections_created); ia64_info->plt_sec->_raw_size = data.ofs; @@ -3084,7 +3087,7 @@ elfNN_ia64_size_dynamic_sections (output_bfd, info) /* The DT_DEBUG entry is filled in by the dynamic linker and used by the debugger. */ #define add_dynamic_entry(TAG, VAL) \ - bfd_elfNN_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL)) + _bfd_elf_add_dynamic_entry (info, TAG, VAL) if (!add_dynamic_entry (DT_DEBUG, 0)) return FALSE; @@ -3839,7 +3842,7 @@ elfNN_ia64_final_link (abfd, info) } /* Invoke the regular ELF backend linker to do all the work. */ - if (!bfd_elfNN_bfd_final_link (abfd, info)) + if (!bfd_elf_final_link (abfd, info)) return FALSE; if (unwind_output_sec) @@ -3976,12 +3979,12 @@ elfNN_ia64_relocate_section (output_bfd, info, input_bfd, input_section, { bfd_boolean unresolved_reloc; bfd_boolean warned; + struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (input_bfd); - RELOC_FOR_GLOBAL_SYMBOL (h, elf_sym_hashes (input_bfd), - r_symndx, - symtab_hdr, value, sym_sec, - unresolved_reloc, info, - warned); + RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel, + r_symndx, symtab_hdr, sym_hashes, + h, sym_sec, value, + unresolved_reloc, warned); if (h->root.type == bfd_link_hash_undefweak) undef_weak_ref = TRUE; @@ -4597,7 +4600,7 @@ elfNN_ia64_finish_dynamic_symbol (output_bfd, info, h, sym) /* Mark the symbol as undefined, rather than as defined in the plt section. Leave the value alone. */ /* ??? We didn't redefine it in adjust_dynamic_symbol in the - first place. But perhaps elflink.h did some for us. */ + first place. But perhaps elflink.c did some for us. */ if ((h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR) == 0) sym->st_shndx = SHN_UNDEF; } |