diff options
Diffstat (limited to 'bfd/elflink.c')
-rw-r--r-- | bfd/elflink.c | 116 |
1 files changed, 67 insertions, 49 deletions
diff --git a/bfd/elflink.c b/bfd/elflink.c index df6eb25..666399b 100644 --- a/bfd/elflink.c +++ b/bfd/elflink.c @@ -3384,12 +3384,9 @@ _bfd_elf_adjust_dynamic_copy (struct bfd_link_info *info, --power_of_two; } - if (power_of_two > bfd_section_alignment (dynbss)) - { - /* Adjust the section alignment if needed. */ - if (!bfd_set_section_alignment (dynbss, power_of_two)) - return false; - } + /* Adjust the section alignment if needed. */ + if (!bfd_link_align_section (dynbss, power_of_two)) + return false; /* We make sure that the symbol will be aligned properly. */ dynbss->size = BFD_ALIGN (dynbss->size, mask + 1); @@ -3609,7 +3606,7 @@ _bfd_elf_tls_setup (bfd *obfd, struct bfd_link_info *info) /* Ensure the alignment of the first section (usually .tdata) is the largest alignment, so that the tls segment starts aligned. */ if (tls != NULL) - tls->alignment_power = align; + (void) bfd_link_align_section (tls, align); return tls; } @@ -4362,8 +4359,8 @@ elf_link_add_to_first_hash (bfd *abfd, struct bfd_link_info *info, = ((struct elf_link_first_hash_entry *) bfd_hash_lookup (htab->first_hash, name, true, copy)); if (e == NULL) - info->callbacks->einfo - (_("%F%P: %pB: failed to add %s to first hash\n"), abfd, name); + info->callbacks->fatal + (_("%P: %pB: failed to add %s to first hash\n"), abfd, name); if (e->abfd == NULL) /* Store ABFD in abfd. */ @@ -4430,8 +4427,8 @@ elf_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) || !bfd_hash_table_init (htab->first_hash, elf_link_first_hash_newfunc, sizeof (struct elf_link_first_hash_entry))) - info->callbacks->einfo - (_("%F%P: first_hash failed to create: %E\n")); + info->callbacks->fatal + (_("%P: first_hash failed to create: %E\n")); } } else @@ -4968,6 +4965,7 @@ elf_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) asection *sec, *new_sec; flagword flags; const char *name; + const char *defvername; bool must_copy_name = false; struct elf_link_hash_entry *h; struct elf_link_hash_entry *hi; @@ -5144,6 +5142,7 @@ elf_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) old_alignment = 0; old_bfd = NULL; new_sec = sec; + defvername = NULL; if (is_elf_hash_table (&htab->root)) { @@ -5262,7 +5261,7 @@ elf_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) default version of the symbol. */ if ((iver.vs_vers & VERSYM_HIDDEN) == 0 && isym->st_shndx != SHN_UNDEF) - *p++ = ELF_VER_CHR; + *p++ = ELF_VER_CHR, defvername = name; memcpy (p, verstr, verlen + 1); name = newname; @@ -5712,9 +5711,15 @@ elf_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info) } else if (dynamic && h->root.u.def.section->owner == abfd) - /* Add this symbol to first hash if this shared - object has the first definition. */ - elf_link_add_to_first_hash (abfd, info, name, must_copy_name); + { + /* Add this symbol to first hash if this shared + object has the first definition. */ + elf_link_add_to_first_hash (abfd, info, name, must_copy_name); + /* And if it was the default symbol version definition, + also add the short name. */ + if (defvername) + elf_link_add_to_first_hash (abfd, info, defvername, false); + } } } } @@ -6276,12 +6281,30 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info) if (h->type == bfd_link_hash_undefined) { - /* If the archive element has already been loaded then one - of the symbols defined by that element might have been - made undefined due to being in a discarded section. */ - if (is_elf_hash_table (info->hash) - && ((struct elf_link_hash_entry *) h)->indx == -3) - continue; + if (is_elf_hash_table (info->hash)) + { + /* If the archive element has already been loaded then one + of the symbols defined by that element might have been + made undefined due to being in a discarded section. */ + if (((struct elf_link_hash_entry *) h)->indx == -3) + continue; + + /* In the pre-LTO-plugin pass we must not mistakenly + include this archive member if an earlier shared + library defined this symbol. */ + struct elf_link_hash_table *htab = elf_hash_table (info); + if (htab->first_hash) + { + struct elf_link_first_hash_entry *e + = ((struct elf_link_first_hash_entry *) + bfd_hash_lookup (htab->first_hash, symdef->name, + false, false)); + if (e + && (e->abfd->flags & DYNAMIC) != 0 + && e->abfd != abfd) + continue; + } + } } else if (h->type == bfd_link_hash_common) { @@ -12209,9 +12232,9 @@ elf_link_input_bfd (struct elf_final_link_info *flinfo, bfd *input_bfd) break; case SEC_INFO_TYPE_SFRAME: { - /* Merge .sframe sections into the ctf frame encoder - context of the output_bfd's section. The final .sframe - output section will be written out later. */ + /* Merge SFrame section into the SFrame encoder context of the + output_bfd's section. The final .sframe output section will + be written out later. */ if (!_bfd_elf_merge_section_sframe (output_bfd, flinfo->info, o, contents)) return false; @@ -12613,9 +12636,6 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info) size_t relr_entsize; asection *reldyn = 0; bfd_size_type amt; - asection *attr_section = NULL; - bfd_vma attr_size = 0; - const char *std_attrs_section; struct elf_link_hash_table *htab = elf_hash_table (info); bool sections_removed; @@ -12661,12 +12681,12 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info) sections from the link, and set the contents of the output section. */ sections_removed = false; - std_attrs_section = get_elf_backend_data (abfd)->obj_attrs_section; + const char *obj_attrs_section = get_elf_backend_data (abfd)->obj_attrs_section; for (o = abfd->sections; o != NULL; o = o->next) { bool remove_section = false; - if ((std_attrs_section && strcmp (o->name, std_attrs_section) == 0) + if ((obj_attrs_section && strcmp (o->name, obj_attrs_section) == 0) || strcmp (o->name, ".gnu.attributes") == 0) { for (p = o->map_head.link_order; p != NULL; p = p->next) @@ -12681,12 +12701,16 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info) input_section->flags &= ~SEC_HAS_CONTENTS; } - attr_size = bfd_elf_obj_attr_size (abfd); - bfd_set_section_size (o, attr_size); /* Skip this section later on. */ o->map_head.link_order = NULL; - if (attr_size) - attr_section = o; + + bfd_vma attr_size = bfd_elf_obj_attr_size (abfd); + /* Once ELF headers have been written, the size of a section is + frozen. We need to set the size of the attribute section before + _bfd_elf_compute_section_file_positions. */ + bfd_set_section_size (o, attr_size); + if (attr_size > 0) + elf_obj_build_attributes (abfd) = o; else remove_section = true; } @@ -13122,8 +13146,8 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info) if (info->enable_dt_relr && bed->finish_relative_relocs && !bed->finish_relative_relocs (info)) - info->callbacks->einfo - (_("%F%P: %pB: failed to finish relative relocations\n"), abfd); + info->callbacks->fatal + (_("%P: %pB: failed to finish relative relocations\n"), abfd); /* Since ELF permits relocations to be against local symbols, we must have the local symbols available when we do the relocations. @@ -13801,21 +13825,14 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info) if (! _bfd_elf_write_section_sframe (abfd, info)) goto error_return; + if (! _bfd_elf_write_section_build_attributes (abfd, info)) + goto error_ret2; + if (info->callbacks->emit_ctf) info->callbacks->emit_ctf (); elf_final_link_free (abfd, &flinfo); - if (attr_section) - { - bfd_byte *contents = (bfd_byte *) bfd_malloc (attr_size); - if (contents == NULL) - goto error_ret2; - bfd_elf_set_obj_attr_contents (abfd, contents, attr_size); - bfd_set_section_contents (abfd, attr_section, contents, 0, attr_size); - free (contents); - } - if (info->unique_symbol) bfd_hash_table_free (&flinfo.local_hash_table); return true; @@ -14041,7 +14058,7 @@ _bfd_elf_gc_mark_rsec (struct bfd_link_info *info, asection *sec, h = get_ext_sym_hash_from_cookie (cookie, r_symndx); if (h == NULL) { - /* A corrup tinput file can lead to a situation where the index + /* A corrupt input file can lead to a situation where the index does not reference either a local or an external symbol. */ if (r_symndx >= cookie->locsymcount) return NULL; @@ -14292,7 +14309,7 @@ _bfd_elf_gc_mark_extra_sections (struct bfd_link_info *info, else if (strcmp (bfd_section_name (isec), "__patchable_function_entries") == 0 && elf_linked_to_section (isec) == NULL) - info->callbacks->einfo (_("%F%P: %pB(%pA): error: " + info->callbacks->fatal (_("%P: %pB(%pA): error: " "need linked-to section " "for --gc-sections\n"), isec->owner, isec); @@ -14393,7 +14410,8 @@ elf_gc_sweep (bfd *abfd, struct bfd_link_info *info) if (o->flags & SEC_GROUP) { asection *first = elf_next_in_group (o); - o->gc_mark = first->gc_mark; + if (first != NULL) + o->gc_mark = first->gc_mark; } if (o->gc_mark) @@ -15469,7 +15487,7 @@ _bfd_elf_section_already_linked (bfd *abfd, /* This is the first section with this name. Record it. */ if (!bfd_section_already_linked_table_insert (already_linked_list, sec)) - info->callbacks->einfo (_("%F%P: already_linked_table: %E\n")); + info->callbacks->fatal (_("%P: already_linked_table: %E\n")); return sec->output_section == bfd_abs_section_ptr; } |