diff options
author | H.J. Lu <hjl.tools@gmail.com> | 2017-04-27 13:55:31 -0700 |
---|---|---|
committer | H.J. Lu <hjl.tools@gmail.com> | 2017-04-27 13:55:48 -0700 |
commit | de9a3c4285fad1914929ee304ddaa26e76af8031 (patch) | |
tree | e3368c31ed041c51a8a396d4e758a3f10417ab25 /bfd/elf64-x86-64.c | |
parent | da3d25afa26476bf24247b8696fd00ab31f39db9 (diff) | |
download | gdb-de9a3c4285fad1914929ee304ddaa26e76af8031.zip gdb-de9a3c4285fad1914929ee304ddaa26e76af8031.tar.gz gdb-de9a3c4285fad1914929ee304ddaa26e76af8031.tar.bz2 |
x86: Create dynamic sections in create_dynamic_sections
This patch creates dynamic sections in i386/x86-64 create_dynamic_sections
instead of creating them on demend. Linker will strip them if they are
empty. It changes order in x86-64 .eh_frame section. The extra DW_CFA_nop
paddings is due to
https://sourceware.org/bugzilla/show_bug.cgi?id=21441
bfd/
* elf32-i386.c (elf_i386_create_dynamic_sections): Create the
.plt.got section here.
(elf_i386_check_relocs): Don't create the .plt.got section.
* elf64-x86-64.c (elf_x86_64_create_dynamic_sections): Create
the .plt.got and .plt.bnd sections here.
(elf_x86_64_check_relocs): Don't create the .plt.got nor
.plt.bnd sections.
ld/
* testsuite/ld-x86-64/pr21038a.d: Update DW_CFA_nop paddings
in .eh_frame section.
* testsuite/ld-x86-64/pr21038c.d: Update .eh_frame order.
Diffstat (limited to 'bfd/elf64-x86-64.c')
-rw-r--r-- | bfd/elf64-x86-64.c | 219 |
1 files changed, 99 insertions, 120 deletions
diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index c491628..5985319 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -1197,19 +1197,106 @@ elf_x86_64_create_dynamic_sections (bfd *dynobj, htab->interp = s; } - if (!info->no_ld_generated_unwind_info - && htab->plt_eh_frame == NULL - && htab->elf.splt != NULL) + if (htab->elf.splt != NULL) { - flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY - | SEC_HAS_CONTENTS | SEC_IN_MEMORY - | SEC_LINKER_CREATED); - htab->plt_eh_frame - = bfd_make_section_anyway_with_flags (dynobj, ".eh_frame", flags); - if (htab->plt_eh_frame == NULL - || !bfd_set_section_alignment (dynobj, htab->plt_eh_frame, - ABI_64_P (dynobj) ? 3 : 2)) - return FALSE; + const struct elf_backend_data *bed + = get_elf_backend_data (dynobj); + flagword pltflags = (bed->dynamic_sec_flags + | SEC_ALLOC + | SEC_CODE + | SEC_LOAD + | SEC_READONLY); + + if (htab->plt_got == NULL + && get_elf_x86_64_backend_data (dynobj) == &elf_x86_64_arch_bed) + { + /* Create the GOT procedure linkage table. */ + unsigned int plt_got_align; + + BFD_ASSERT (sizeof (elf_x86_64_legacy_plt2_entry) == 8 + && (sizeof (elf_x86_64_bnd_plt2_entry) + == sizeof (elf_x86_64_legacy_plt2_entry))); + plt_got_align = 3; + + htab->plt_got + = bfd_make_section_anyway_with_flags (dynobj, + ".plt.got", + pltflags); + if (htab->plt_got == NULL + || !bfd_set_section_alignment (dynobj, + htab->plt_got, + plt_got_align)) + return FALSE; + } + + /* MPX PLT is supported only if elf_x86_64_arch_bed is used in + 64-bit mode. */ + if (ABI_64_P (dynobj) + && info->bndplt + && get_elf_x86_64_backend_data (dynobj) == &elf_x86_64_arch_bed + && htab->plt_bnd == NULL) + { + /* Create the second PLT for Intel MPX support. */ + BFD_ASSERT (sizeof (elf_x86_64_bnd_plt2_entry) == 8 + && (sizeof (elf_x86_64_bnd_plt2_entry) + == sizeof (elf_x86_64_legacy_plt2_entry))); + + htab->plt_bnd + = bfd_make_section_anyway_with_flags (dynobj, + ".plt.bnd", + pltflags); + if (htab->plt_bnd == NULL + || !bfd_set_section_alignment (dynobj, htab->plt_bnd, 3)) + return FALSE; + } + + if (!info->no_ld_generated_unwind_info) + { + flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY + | SEC_HAS_CONTENTS | SEC_IN_MEMORY + | SEC_LINKER_CREATED); + + if (htab->plt_eh_frame == NULL) + { + htab->plt_eh_frame + = bfd_make_section_anyway_with_flags (dynobj, + ".eh_frame", + flags); + if (htab->plt_eh_frame == NULL + || !bfd_set_section_alignment (dynobj, + htab->plt_eh_frame, + ABI_64_P (dynobj) ? 3 : 2)) + return FALSE; + } + + if (htab->plt_got_eh_frame == NULL + && htab->plt_got != NULL) + { + htab->plt_got_eh_frame + = bfd_make_section_anyway_with_flags (htab->elf.dynobj, + ".eh_frame", + flags); + if (htab->plt_got_eh_frame == NULL + || !bfd_set_section_alignment (dynobj, + htab->plt_got_eh_frame, + ABI_64_P (dynobj) ? 3 : 2)) + return FALSE; + } + + if (htab->plt_bnd_eh_frame == NULL + && htab->plt_bnd != NULL) + { + htab->plt_bnd_eh_frame + = bfd_make_section_anyway_with_flags (dynobj, + ".eh_frame", + flags); + if (htab->plt_bnd_eh_frame == NULL + || !bfd_set_section_alignment (dynobj, + htab->plt_bnd_eh_frame, + 3)) + return FALSE; + } + } } /* Align .got section to its entry size. */ @@ -2198,7 +2285,6 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info, const Elf_Internal_Rela *rel_end; asection *sreloc; bfd_byte *contents; - bfd_boolean use_plt_got; if (bfd_link_relocatable (info)) return TRUE; @@ -2230,8 +2316,6 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info, return FALSE; } - use_plt_got = get_elf_x86_64_backend_data (abfd) == &elf_x86_64_arch_bed; - symtab_hdr = &elf_symtab_hdr (abfd); sym_hashes = elf_sym_hashes (abfd); @@ -2340,59 +2424,6 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info, case R_X86_64_PLT32: case R_X86_64_32: case R_X86_64_64: - /* MPX PLT is supported only if elf_x86_64_arch_bed - is used in 64-bit mode. */ - if (ABI_64_P (abfd) - && info->bndplt - && (get_elf_x86_64_backend_data (abfd) - == &elf_x86_64_arch_bed)) - { - /* Create the second PLT for Intel MPX support. */ - if (htab->plt_bnd == NULL) - { - const struct elf_backend_data *bed; - - bed = get_elf_backend_data (info->output_bfd); - BFD_ASSERT (sizeof (elf_x86_64_bnd_plt2_entry) == 8 - && (sizeof (elf_x86_64_bnd_plt2_entry) - == sizeof (elf_x86_64_legacy_plt2_entry))); - - if (htab->elf.dynobj == NULL) - htab->elf.dynobj = abfd; - htab->plt_bnd - = bfd_make_section_anyway_with_flags (htab->elf.dynobj, - ".plt.bnd", - (bed->dynamic_sec_flags - | SEC_ALLOC - | SEC_CODE - | SEC_LOAD - | SEC_READONLY)); - if (htab->plt_bnd == NULL - || !bfd_set_section_alignment (htab->elf.dynobj, - htab->plt_bnd, - 3)) - goto error_return; - } - - if (!info->no_ld_generated_unwind_info - && htab->plt_bnd_eh_frame == NULL) - { - flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY - | SEC_HAS_CONTENTS | SEC_IN_MEMORY - | SEC_LINKER_CREATED); - htab->plt_bnd_eh_frame - = bfd_make_section_anyway_with_flags (htab->elf.dynobj, - ".eh_frame", - flags); - if (htab->plt_bnd_eh_frame == NULL - || !bfd_set_section_alignment (htab->elf.dynobj, - htab->plt_bnd_eh_frame, - 3)) - goto error_return; - } - } - /* Fall through. */ - case R_X86_64_32S: case R_X86_64_PC64: case R_X86_64_GOTPCREL: @@ -2798,58 +2829,6 @@ do_size: break; } - if (use_plt_got - && h != NULL - && h->plt.refcount > 0 - && (((info->flags & DF_BIND_NOW) && !h->pointer_equality_needed) - || h->got.refcount > 0) - && htab->plt_got == NULL) - { - /* Create the GOT procedure linkage table. */ - unsigned int plt_got_align; - const struct elf_backend_data *bed; - - bed = get_elf_backend_data (info->output_bfd); - BFD_ASSERT (sizeof (elf_x86_64_legacy_plt2_entry) == 8 - && (sizeof (elf_x86_64_bnd_plt2_entry) - == sizeof (elf_x86_64_legacy_plt2_entry))); - plt_got_align = 3; - - if (htab->elf.dynobj == NULL) - htab->elf.dynobj = abfd; - htab->plt_got - = bfd_make_section_anyway_with_flags (htab->elf.dynobj, - ".plt.got", - (bed->dynamic_sec_flags - | SEC_ALLOC - | SEC_CODE - | SEC_LOAD - | SEC_READONLY)); - if (htab->plt_got == NULL - || !bfd_set_section_alignment (htab->elf.dynobj, - htab->plt_got, - plt_got_align)) - goto error_return; - - if (!info->no_ld_generated_unwind_info - && htab->plt_got_eh_frame == NULL - && get_elf_x86_64_backend_data (abfd)->eh_frame_plt_got != NULL) - { - flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY - | SEC_HAS_CONTENTS | SEC_IN_MEMORY - | SEC_LINKER_CREATED); - htab->plt_got_eh_frame - = bfd_make_section_anyway_with_flags (htab->elf.dynobj, - ".eh_frame", - flags); - if (htab->plt_got_eh_frame == NULL - || !bfd_set_section_alignment (htab->elf.dynobj, - htab->plt_got_eh_frame, - ABI_64_P (htab->elf.dynobj) ? 3 : 2)) - goto error_return; - } - } - if ((r_type == R_X86_64_GOTPCREL || r_type == R_X86_64_GOTPCRELX || r_type == R_X86_64_REX_GOTPCRELX) |