diff --git a/binutils-Intel-APX-part-1.patch b/binutils-Intel-APX-part-1.patch index d6adf95..7d26ad6 100644 --- a/binutils-Intel-APX-part-1.patch +++ b/binutils-Intel-APX-part-1.patch @@ -117073,3 +117073,675 @@ diff -rupN binutils.orig/opcodes/i386-tbl.h binutils-2.41/opcodes/i386-tbl.h }; /* i386 mnemonics table. */ +diff -rup binutils.orig/elfcpp/x86_64.h binutils-2.41/elfcpp/x86_64.h +--- binutils.orig/elfcpp/x86_64.h 2024-01-22 11:32:09.151805489 +0000 ++++ binutils-2.41/elfcpp/x86_64.h 2024-01-22 11:32:48.111841977 +0000 +@@ -95,9 +95,21 @@ enum + R_X86_64_PC32_BND = 39, // PC relative 32 bit signed with BND prefix + R_X86_64_PLT32_BND = 40, // 32 bit PLT address with BND prefix + R_X86_64_GOTPCRELX = 41, // 32 bit signed PC relative offset to GOT +- // without REX prefix, relaxable. ++ // without REX nor REX2 prefixes, relaxable. + R_X86_64_REX_GOTPCRELX = 42, // 32 bit signed PC relative offset to GOT + // with REX prefix, relaxable. ++ R_X86_64_CODE_4_GOTPCRELX = 43, // 32 bit signed PC relative offset to ++ // GOT if the instruction starts at 4 ++ // bytes before the relocation offset, ++ // relaxable. ++ R_X86_64_CODE_4_GOTTPOFF = 44, // 32 bit signed PC relative offset to ++ // GOT entry for IE symbol if the ++ // instruction starts at 4 bytes before ++ // the relocation offset. ++ R_X86_64_CODE_4_GOTPC32_TLSDESC = 45, // 32-bit PC relative to TLS ++ // descriptor in GOT if the ++ // instruction starts at 4 bytes ++ // before the relocation offset. + // GNU vtable garbage collection extensions. + R_X86_64_GNU_VTINHERIT = 250, + R_X86_64_GNU_VTENTRY = 251 +diff -rup binutils.orig/gold/testsuite/Makefile.am binutils-2.41/gold/testsuite/Makefile.am +--- binutils.orig/gold/testsuite/Makefile.am 2024-01-22 11:32:09.869806294 +0000 ++++ binutils-2.41/gold/testsuite/Makefile.am 2024-01-22 11:32:48.112841978 +0000 +@@ -1244,6 +1244,17 @@ x86_64_gd_to_le: x86_64_gd_to_le.o gccte + x86_64_gd_to_le.stdout: x86_64_gd_to_le + $(TEST_OBJDUMP) -dw $< > $@ + ++check_SCRIPTS += x86_64_ie_to_le.sh ++check_DATA += x86_64_ie_to_le.stdout ++MOSTLYCLEANFILES += x86_64_ie_to_le ++ ++x86_64_ie_to_le.o: x86_64_ie_to_le.s ++ $(TEST_AS) --64 -o $@ $< ++x86_64_ie_to_le: x86_64_ie_to_le.o gcctestdir/ld ++ gcctestdir/ld -o $@ $< ++x86_64_ie_to_le.stdout: x86_64_ie_to_le ++ $(TEST_OBJDUMP) -dw $< > $@ ++ + check_SCRIPTS += x86_64_overflow_pc32.sh + check_DATA += x86_64_overflow_pc32.err + MOSTLYCLEANFILES += x86_64_overflow_pc32.err +diff -rup binutils.orig/gold/testsuite/Makefile.in binutils-2.41/gold/testsuite/Makefile.in +--- binutils.orig/gold/testsuite/Makefile.in 2024-01-22 11:32:09.870806295 +0000 ++++ binutils-2.41/gold/testsuite/Makefile.in 2024-01-22 11:32:48.113841979 +0000 +@@ -296,6 +296,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__E + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_31 = x86_64_mov_to_lea.sh \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_indirect_call_to_direct.sh \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_gd_to_le.sh \ ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_ie_to_le.sh \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_overflow_pc32.sh \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x32_overflow_pc32.sh \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ pr23016_1.sh \ +@@ -319,6 +320,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__E + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_indirect_call_to_direct1.stdout \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_indirect_jump_to_direct1.stdout \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_gd_to_le.stdout \ ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_ie_to_le.stdout \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_overflow_pc32.err \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x32_overflow_pc32.err \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ pr23016_1.stdout \ +@@ -343,6 +345,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__E + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_indirect_call_to_direct1 \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_indirect_jump_to_direct1 \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_gd_to_le \ ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_ie_to_le \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x86_64_overflow_pc32.err \ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ x32_overflow_pc32.err + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_34 = pr17704a_test +@@ -5736,6 +5739,13 @@ x86_64_gd_to_le.sh.log: x86_64_gd_to_le. + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) ++x86_64_ie_to_le.sh.log: x86_64_ie_to_le.sh ++ @p='x86_64_ie_to_le.sh'; \ ++ b='x86_64_ie_to_le.sh'; \ ++ $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ ++ --log-file $$b.log --trs-file $$b.trs \ ++ $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ ++ "$$tst" $(AM_TESTS_FD_REDIRECT) + x86_64_overflow_pc32.sh.log: x86_64_overflow_pc32.sh + @p='x86_64_overflow_pc32.sh'; \ + b='x86_64_overflow_pc32.sh'; \ +@@ -8474,6 +8484,13 @@ uninstall-am: + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ gcctestdir/ld -o $@ $< + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_gd_to_le.stdout: x86_64_gd_to_le + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_OBJDUMP) -dw $< > $@ ++ ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_ie_to_le.o: x86_64_ie_to_le.s ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_AS) --64 -o $@ $< ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_ie_to_le: x86_64_ie_to_le.o gcctestdir/ld ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ gcctestdir/ld -o $@ $< ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_ie_to_le.stdout: x86_64_ie_to_le ++@DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_OBJDUMP) -dw $< > $@ + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_overflow_pc32.o: x86_64_overflow_pc32.s + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_AS) -o $@ $< + @DEFAULT_TARGET_X86_64_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@x86_64_overflow_pc32.err: x86_64_overflow_pc32.o gcctestdir/ld +diff -rup binutils.orig/gold/testsuite/x86_64_gd_to_le.s binutils-2.41/gold/testsuite/x86_64_gd_to_le.s +--- binutils.orig/gold/testsuite/x86_64_gd_to_le.s 2024-01-22 11:32:09.886806313 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_gd_to_le.s 2024-01-22 11:32:48.113841979 +0000 +@@ -7,6 +7,7 @@ _start: + subq $8, %rsp + .cfi_def_cfa_offset 16 + leaq foo@TLSDESC(%rip), %r9 ++ leaq foo@TLSDESC(%rip), %r29 + movq %r9, %rax + call *foo@TLSCALL(%rax) + addq %fs:0, %rax +diff -rup binutils.orig/gold/testsuite/x86_64_gd_to_le.sh binutils-2.41/gold/testsuite/x86_64_gd_to_le.sh +--- binutils.orig/gold/testsuite/x86_64_gd_to_le.sh 2024-01-22 11:32:09.886806313 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_gd_to_le.sh 2024-01-22 11:32:48.113841979 +0000 +@@ -24,3 +24,4 @@ + set -e + + grep -q "mov[ \t]\+\$0x[a-f0-9]\+,%r9" x86_64_gd_to_le.stdout ++grep -q "mov[ \t]\+\$0x[a-f0-9]\+,%r29" x86_64_gd_to_le.stdout +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea.sh binutils-2.41/gold/testsuite/x86_64_mov_to_lea.sh +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea.sh 2024-01-22 11:32:09.886806313 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea.sh 2024-01-22 11:32:40.599835054 +0000 +@@ -25,20 +25,36 @@ + set -e + + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea1.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea1.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea2.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea2.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea3.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea3.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea4.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea4.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea5.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea5.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea6.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea6.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea7.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea7.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea8.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea8.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea9.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea9.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea10.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea10.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea11.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea11.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea12.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea12.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea13.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea13.stdout + grep -q "lea -0x[a-f0-9]\+(%rip),%rax" x86_64_mov_to_lea14.stdout ++grep -q "lea -0x[a-f0-9]\+(%rip),%r26" x86_64_mov_to_lea14.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%eax" x86_64_mov_to_lea15.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26d" x86_64_mov_to_lea15.stdout + grep -q "mov 0x[a-f0-9]\+(%rip),%eax" x86_64_mov_to_lea16.stdout ++grep -q "mov 0x[a-f0-9]\+(%rip),%r26d" x86_64_mov_to_lea16.stdout + + exit 0 +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea1.s binutils-2.41/gold/testsuite/x86_64_mov_to_lea1.s +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea1.s 2024-01-22 11:32:09.886806313 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea1.s 2024-01-22 11:32:40.599835054 +0000 +@@ -8,4 +8,5 @@ foo: + .type _start, @function + _start: + movq foo@GOTPCREL(%rip), %rax ++ movq foo@GOTPCREL(%rip), %r26 + .size _start, .-_start +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea2.s binutils-2.41/gold/testsuite/x86_64_mov_to_lea2.s +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea2.s 2024-01-22 11:32:09.887806314 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea2.s 2024-01-22 11:32:40.599835054 +0000 +@@ -3,4 +3,5 @@ + .type _start, @function + _start: + movq _DYNAMIC@GOTPCREL(%rip), %rax ++ movq _DYNAMIC@GOTPCREL(%rip), %r26 + .size _start, .-_start +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea3.s binutils-2.41/gold/testsuite/x86_64_mov_to_lea3.s +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea3.s 2024-01-22 11:32:09.887806314 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea3.s 2024-01-22 11:32:40.599835054 +0000 +@@ -7,4 +7,5 @@ foo: + .type _start, @function + _start: + movq foo@GOTPCREL(%rip), %rax ++ movq foo@GOTPCREL(%rip), %r26 + .size _start, .-_start +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea4.s binutils-2.41/gold/testsuite/x86_64_mov_to_lea4.s +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea4.s 2024-01-22 11:32:09.887806314 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea4.s 2024-01-22 11:32:40.599835054 +0000 +@@ -9,4 +9,5 @@ foo: + .type _start, @function + _start: + movq foo@GOTPCREL(%rip), %rax ++ movq foo@GOTPCREL(%rip), %r26 + .size _start, .-_start +diff -rup binutils.orig/gold/testsuite/x86_64_mov_to_lea5.s binutils-2.41/gold/testsuite/x86_64_mov_to_lea5.s +--- binutils.orig/gold/testsuite/x86_64_mov_to_lea5.s 2024-01-22 11:32:09.887806314 +0000 ++++ binutils-2.41/gold/testsuite/x86_64_mov_to_lea5.s 2024-01-22 11:32:40.599835054 +0000 +@@ -9,4 +9,5 @@ foo: + .type _start, @function + _start: + movl foo@GOTPCREL+4(%rip), %eax ++ movl foo@GOTPCREL+4(%rip), %r26d + .size _start, .-_start +diff -rup binutils.orig/gold/x86_64.cc binutils-2.41/gold/x86_64.cc +--- binutils.orig/gold/x86_64.cc 2024-01-22 11:32:09.889806316 +0000 ++++ binutils-2.41/gold/x86_64.cc 2024-01-22 11:32:48.114841980 +0000 +@@ -1053,8 +1053,9 @@ class Target_x86_64 : public Sized_targe + gold_assert(gsym != NULL); + // We cannot do the conversion unless it's one of these relocations. + if (r_type != elfcpp::R_X86_64_GOTPCREL +- && r_type != elfcpp::R_X86_64_GOTPCRELX +- && r_type != elfcpp::R_X86_64_REX_GOTPCRELX) ++ && r_type != elfcpp::R_X86_64_GOTPCRELX ++ && r_type != elfcpp::R_X86_64_REX_GOTPCRELX ++ && r_type != elfcpp::R_X86_64_CODE_4_GOTPCRELX) + return false; + // We cannot convert references to IFUNC symbols, or to symbols that + // are not local to the current module. +@@ -1109,7 +1110,8 @@ class Target_x86_64 : public Sized_targe + // Adjust TLS relocation type based on the options and whether this + // is a local symbol. + static tls::Tls_optimization +- optimize_tls_reloc(bool is_final, int r_type); ++ optimize_tls_reloc(bool is_final, int r_type, size_t r_offset, ++ const unsigned char* reloc_view); + + // Get the GOT section, creating it if necessary. + Output_data_got<64, false>* +@@ -2877,11 +2879,13 @@ Target_x86_64::got_mod_index_entry + + // Optimize the TLS relocation type based on what we know about the + // symbol. IS_FINAL is true if the final address of this symbol is +-// known at link time. ++// known at link time. RELOC_VIEW points to the relocation offset. + + template + tls::Tls_optimization +-Target_x86_64::optimize_tls_reloc(bool is_final, int r_type) ++Target_x86_64::optimize_tls_reloc(bool is_final, int r_type, ++ size_t r_offset, ++ const unsigned char* reloc_view) + { + // If we are generating a shared library, then we can't do anything + // in the linker. +@@ -2890,6 +2894,10 @@ Target_x86_64::optimize_tls_reloc( + + switch (r_type) + { ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: ++ if (r_offset <= 4 || *(reloc_view - 4) != 0xd5) ++ return tls::TLSOPT_NONE; ++ // Fall through. + case elfcpp::R_X86_64_TLSGD: + case elfcpp::R_X86_64_GOTPC32_TLSDESC: + case elfcpp::R_X86_64_TLSDESC_CALL: +@@ -2912,6 +2920,10 @@ Target_x86_64::optimize_tls_reloc( + // Another Local-Dynamic reloc. + return tls::TLSOPT_TO_LE; + ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: ++ if (r_offset <= 4 || *(reloc_view - 4) != 0xd5) ++ return tls::TLSOPT_NONE; ++ // Fall through. + case elfcpp::R_X86_64_GOTTPOFF: + // These are Initial-Exec relocs which get the thread offset + // from the GOT. If we know that we are linking against the +@@ -2971,17 +2983,20 @@ Target_x86_64::Scan::get_reference + case elfcpp::R_X86_64_GOTPCREL: + case elfcpp::R_X86_64_GOTPCRELX: + case elfcpp::R_X86_64_REX_GOTPCRELX: ++ case elfcpp::R_X86_64_CODE_4_GOTPCRELX: + case elfcpp::R_X86_64_GOTPLT64: + // Absolute in GOT. + return Symbol::ABSOLUTE_REF; + + case elfcpp::R_X86_64_TLSGD: // Global-dynamic + case elfcpp::R_X86_64_GOTPC32_TLSDESC: // Global-dynamic (from ~oliva url) ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: + case elfcpp::R_X86_64_TLSDESC_CALL: + case elfcpp::R_X86_64_TLSLD: // Local-dynamic + case elfcpp::R_X86_64_DTPOFF32: + case elfcpp::R_X86_64_DTPOFF64: + case elfcpp::R_X86_64_GOTTPOFF: // Initial-exec ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: + case elfcpp::R_X86_64_TPOFF32: // Local-exec + return Symbol::TLS_REF; + +@@ -3146,6 +3161,8 @@ Target_x86_64::Scan::local(Symbol_ + target->make_local_ifunc_plt_entry(symtab, layout, object, r_sym); + } + ++ const unsigned char* reloc_view = NULL; ++ + switch (r_type) + { + case elfcpp::R_X86_64_NONE: +@@ -3251,6 +3268,7 @@ Target_x86_64::Scan::local(Symbol_ + case elfcpp::R_X86_64_GOTPCREL: + case elfcpp::R_X86_64_GOTPCRELX: + case elfcpp::R_X86_64_REX_GOTPCRELX: ++ case elfcpp::R_X86_64_CODE_4_GOTPCRELX: + case elfcpp::R_X86_64_GOTPLT64: + { + // The symbol requires a GOT section. +@@ -3261,21 +3279,30 @@ Target_x86_64::Scan::local(Symbol_ + // mov foo@GOTPCREL(%rip), %reg + // to lea foo(%rip), %reg. + // in Relocate::relocate. ++ size_t r_offset = reloc.get_r_offset(); + if (!parameters->incremental() +- && (r_type == elfcpp::R_X86_64_GOTPCREL +- || r_type == elfcpp::R_X86_64_GOTPCRELX +- || r_type == elfcpp::R_X86_64_REX_GOTPCRELX) ++ && (((r_type == elfcpp::R_X86_64_GOTPCREL ++ || r_type == elfcpp::R_X86_64_GOTPCRELX ++ || r_type == elfcpp::R_X86_64_REX_GOTPCRELX) ++ && r_offset >= 2) ++ || (r_type == elfcpp::R_X86_64_CODE_4_GOTPCRELX ++ && r_offset >= 4)) + && reloc.get_r_addend() == -4 +- && reloc.get_r_offset() >= 2 + && !is_ifunc) + { + section_size_type stype; + const unsigned char* view = object->section_contents(data_shndx, + &stype, true); +- if (view[reloc.get_r_offset() - 2] == 0x8b) ++ if (r_type == elfcpp::R_X86_64_CODE_4_GOTPCRELX ++ && view[r_offset - 4] != 0xd5) ++ goto need_got; ++ ++ if (view[r_offset - 2] == 0x8b) + break; + } + ++need_got: ++ + // The symbol requires a GOT entry. + unsigned int r_sym = elfcpp::elf_r_sym(reloc.get_r_info()); + +@@ -3333,6 +3360,13 @@ Target_x86_64::Scan::local(Symbol_ + break; + + // These are initial tls relocs, which are expected when linking ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: ++ { ++ section_size_type stype; ++ reloc_view = object->section_contents(data_shndx, &stype, true); ++ } ++ // Fall through. + case elfcpp::R_X86_64_TLSGD: // Global-dynamic + case elfcpp::R_X86_64_GOTPC32_TLSDESC: // Global-dynamic (from ~oliva url) + case elfcpp::R_X86_64_TLSDESC_CALL: +@@ -3343,9 +3377,11 @@ Target_x86_64::Scan::local(Symbol_ + case elfcpp::R_X86_64_TPOFF32: // Local-exec + { + bool output_is_shared = parameters->options().shared(); ++ size_t r_offset = reloc.get_r_offset(); + const tls::Tls_optimization optimized_type + = Target_x86_64::optimize_tls_reloc(!output_is_shared, +- r_type); ++ r_type, r_offset, ++ reloc_view + r_offset); + switch (r_type) + { + case elfcpp::R_X86_64_TLSGD: // General-dynamic +@@ -3374,6 +3410,7 @@ Target_x86_64::Scan::local(Symbol_ + break; + + case elfcpp::R_X86_64_GOTPC32_TLSDESC: ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: + target->define_tls_base_symbol(symtab, layout); + if (optimized_type == tls::TLSOPT_NONE) + { +@@ -3426,6 +3463,7 @@ Target_x86_64::Scan::local(Symbol_ + break; + + case elfcpp::R_X86_64_GOTTPOFF: // Initial-exec ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: + layout->set_has_static_tls(); + if (optimized_type == tls::TLSOPT_NONE) + { +@@ -3498,6 +3536,7 @@ Target_x86_64::Scan::possible_func + case elfcpp::R_X86_64_GOTPCREL: + case elfcpp::R_X86_64_GOTPCRELX: + case elfcpp::R_X86_64_REX_GOTPCRELX: ++ case elfcpp::R_X86_64_CODE_4_GOTPCRELX: + case elfcpp::R_X86_64_GOTPLT64: + { + return true; +@@ -3602,6 +3641,8 @@ Target_x86_64::Scan::global(Symbol + && this->reloc_needs_plt_for_ifunc(object, r_type)) + target->make_plt_entry(symtab, layout, gsym); + ++ const unsigned char *reloc_view = NULL; ++ + switch (r_type) + { + case elfcpp::R_X86_64_NONE: +@@ -3714,6 +3755,7 @@ Target_x86_64::Scan::global(Symbol + case elfcpp::R_X86_64_GOTPCREL: + case elfcpp::R_X86_64_GOTPCRELX: + case elfcpp::R_X86_64_REX_GOTPCRELX: ++ case elfcpp::R_X86_64_CODE_4_GOTPCRELX: + case elfcpp::R_X86_64_GOTPLT64: + { + // The symbol requires a GOT entry. +@@ -3736,8 +3778,12 @@ Target_x86_64::Scan::global(Symbol + size_t r_offset = reloc.get_r_offset(); + if (!parameters->incremental() + && reloc.get_r_addend() == -4 +- && r_offset >= 2 +- && Target_x86_64::can_convert_mov_to_lea(gsym, r_type, ++ && ((r_type != elfcpp::R_X86_64_CODE_4_GOTPCRELX ++ && r_offset >= 2) ++ || (r_type == elfcpp::R_X86_64_CODE_4_GOTPCRELX ++ && r_offset >= 4 ++ && view[r_offset - 4] == 0xd5)) ++ && Target_x86_64::can_convert_mov_to_lea(gsym, r_type, + r_offset, &view)) + break; + +@@ -3854,6 +3900,13 @@ Target_x86_64::Scan::global(Symbol + break; + + // These are initial tls relocs, which are expected for global() ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: ++ { ++ section_size_type stype; ++ reloc_view = object->section_contents(data_shndx, &stype, true); ++ } ++ // Fall through. + case elfcpp::R_X86_64_TLSGD: // Global-dynamic + case elfcpp::R_X86_64_GOTPC32_TLSDESC: // Global-dynamic (from ~oliva url) + case elfcpp::R_X86_64_TLSDESC_CALL: +@@ -3866,11 +3919,15 @@ Target_x86_64::Scan::global(Symbol + // For the Initial-Exec model, we can treat undef symbols as final + // when building an executable. + const bool is_final = (gsym->final_value_is_known() || +- (r_type == elfcpp::R_X86_64_GOTTPOFF && ++ ((r_type == elfcpp::R_X86_64_GOTTPOFF || ++ r_type == elfcpp::R_X86_64_CODE_4_GOTTPOFF) && + gsym->is_undefined() && + parameters->options().output_is_executable())); ++ size_t r_offset = reloc.get_r_offset(); + const tls::Tls_optimization optimized_type +- = Target_x86_64::optimize_tls_reloc(is_final, r_type); ++ = Target_x86_64::optimize_tls_reloc(is_final, r_type, ++ r_offset, ++ reloc_view + r_offset); + switch (r_type) + { + case elfcpp::R_X86_64_TLSGD: // General-dynamic +@@ -3899,6 +3956,7 @@ Target_x86_64::Scan::global(Symbol + break; + + case elfcpp::R_X86_64_GOTPC32_TLSDESC: ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: + target->define_tls_base_symbol(symtab, layout); + if (optimized_type == tls::TLSOPT_NONE) + { +@@ -3947,6 +4005,7 @@ Target_x86_64::Scan::global(Symbol + break; + + case elfcpp::R_X86_64_GOTTPOFF: // Initial-exec ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: + layout->set_has_static_tls(); + if (optimized_type == tls::TLSOPT_NONE) + { +@@ -4420,6 +4479,7 @@ Target_x86_64::Relocate::relocate( + case elfcpp::R_X86_64_GOTPCREL: + case elfcpp::R_X86_64_GOTPCRELX: + case elfcpp::R_X86_64_REX_GOTPCRELX: ++ case elfcpp::R_X86_64_CODE_4_GOTPCRELX: + { + bool converted_p = false; + +@@ -4541,11 +4601,13 @@ Target_x86_64::Relocate::relocate( + // These are initial tls relocs, which are expected when linking + case elfcpp::R_X86_64_TLSGD: // Global-dynamic + case elfcpp::R_X86_64_GOTPC32_TLSDESC: // Global-dynamic (from ~oliva url) ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: + case elfcpp::R_X86_64_TLSDESC_CALL: + case elfcpp::R_X86_64_TLSLD: // Local-dynamic + case elfcpp::R_X86_64_DTPOFF32: + case elfcpp::R_X86_64_DTPOFF64: + case elfcpp::R_X86_64_GOTTPOFF: // Initial-exec ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: + case elfcpp::R_X86_64_TPOFF32: // Local-exec + this->relocate_tls(relinfo, target, relnum, rela, r_type, gsym, psymval, + view, address, view_size); +@@ -4617,8 +4679,10 @@ Target_x86_64::Relocate::relocate_ + const bool is_final = (gsym == NULL + ? !parameters->options().shared() + : gsym->final_value_is_known()); ++ size_t r_offset = rela.get_r_offset(); + tls::Tls_optimization optimized_type +- = Target_x86_64::optimize_tls_reloc(is_final, r_type); ++ = Target_x86_64::optimize_tls_reloc(is_final, r_type, ++ r_offset, view); + switch (r_type) + { + case elfcpp::R_X86_64_TLSGD: // Global-dynamic +@@ -4685,6 +4749,7 @@ Target_x86_64::Relocate::relocate_ + break; + + case elfcpp::R_X86_64_GOTPC32_TLSDESC: // Global-dynamic (from ~oliva url) ++ case elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC: + case elfcpp::R_X86_64_TLSDESC_CALL: + if (!is_executable && optimized_type == tls::TLSOPT_TO_LE) + { +@@ -4710,7 +4775,8 @@ Target_x86_64::Relocate::relocate_ + ? GOT_TYPE_TLS_OFFSET + : GOT_TYPE_TLS_DESC); + unsigned int got_offset = 0; +- if (r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC ++ if ((r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC ++ || r_type == elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC) + && optimized_type == tls::TLSOPT_NONE) + { + // We created GOT entries in the .got.tlsdesc portion of +@@ -4741,7 +4807,8 @@ Target_x86_64::Relocate::relocate_ + } + else if (optimized_type == tls::TLSOPT_NONE) + { +- if (r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC) ++ if (r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC ++ || r_type == elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC) + { + // Relocate the field with the offset of the pair of GOT + // entries. +@@ -4826,6 +4893,7 @@ Target_x86_64::Relocate::relocate_ + break; + + case elfcpp::R_X86_64_GOTTPOFF: // Initial-exec ++ case elfcpp::R_X86_64_CODE_4_GOTTPOFF: + if (gsym != NULL + && gsym->is_undefined() + && parameters->options().output_is_executable()) +@@ -5032,7 +5100,8 @@ Target_x86_64::Relocate::tls_desc_ + typename elfcpp::Elf_types::Elf_Addr address, + section_size_type view_size) + { +- if (r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC) ++ if (r_type == elfcpp::R_X86_64_GOTPC32_TLSDESC ++ || r_type == elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC) + { + // LP64: leaq foo@tlsdesc(%rip), %rax + // ==> movq foo@gottpoff(%rip), %rax +@@ -5041,7 +5110,8 @@ Target_x86_64::Relocate::tls_desc_ + tls::check_range(relinfo, relnum, rela.get_r_offset(), view_size, -3); + tls::check_range(relinfo, relnum, rela.get_r_offset(), view_size, 4); + tls::check_tls(relinfo, relnum, rela.get_r_offset(), +- (((view[-3] & 0xfb) == 0x48 ++ ((r_type == elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC ++ || (view[-3] & 0xfb) == 0x48 + || (size == 32 && (view[-3] & 0xfb) == 0x40)) + && view[-2] == 0x8d + && (view[-1] & 0xc7) == 0x05)); +@@ -5113,6 +5183,22 @@ Target_x86_64::Relocate::tls_desc_ + value -= tls_segment->memsz(); + Relocate_functions::rela32(view, value, 0); + } ++ else if (r_type == elfcpp::R_X86_64_CODE_4_GOTPC32_TLSDESC) ++ { ++ // REX2: lea foo@tlsdesc(%rip), %reg ++ // ==> mov foo@tpoff, %reg ++ tls::check_range(relinfo, relnum, rela.get_r_offset(), view_size, -3); ++ tls::check_range(relinfo, relnum, rela.get_r_offset(), view_size, 4); ++ tls::check_tls(relinfo, relnum, rela.get_r_offset(), ++ (view[-2] == 0x8d ++ && (view[-1] & 0xc7) == 0x05)); ++ unsigned char rex2_mask = 4 | 4 << 4; ++ view[-3] = (view[-3] & ~rex2_mask) | ((view[-3] & rex2_mask) >> 2); ++ view[-2] = 0xc7; ++ view[-1] = 0xc0 | ((view[-1] >> 3) & 7); ++ value -= tls_segment->memsz(); ++ Relocate_functions::rela32(view, value, 0); ++ } + else + { + // LP64: call *foo@tlscall(%rax) +@@ -5212,7 +5298,7 @@ Target_x86_64::Relocate::tls_ie_to + size_t relnum, + Output_segment* tls_segment, + const elfcpp::Rela& rela, +- unsigned int, ++ unsigned int r_type, + typename elfcpp::Elf_types::Elf_Addr value, + unsigned char* view, + section_size_type view_size) +@@ -5231,35 +5317,50 @@ Target_x86_64::Relocate::tls_ie_to + unsigned char op3 = view[-1]; + unsigned char reg = op3 >> 3; + +- if (op2 == 0x8b) ++ if (r_type == elfcpp::R_X86_64_GOTTPOFF) + { +- // movq +- if (op1 == 0x4c) +- view[-3] = 0x49; +- else if (size == 32 && op1 == 0x44) +- view[-3] = 0x41; +- view[-2] = 0xc7; +- view[-1] = 0xc0 | reg; +- } +- else if (reg == 4) +- { +- // Special handling for %rsp. +- if (op1 == 0x4c) +- view[-3] = 0x49; +- else if (size == 32 && op1 == 0x44) +- view[-3] = 0x41; +- view[-2] = 0x81; +- view[-1] = 0xc0 | reg; ++ if (op2 == 0x8b) ++ { ++ // movq ++ if (op1 == 0x4c) ++ view[-3] = 0x49; ++ else if (size == 32 && op1 == 0x44) ++ view[-3] = 0x41; ++ view[-2] = 0xc7; ++ view[-1] = 0xc0 | reg; ++ } ++ else if (reg == 4) ++ { ++ // Special handling for %rsp. ++ if (op1 == 0x4c) ++ view[-3] = 0x49; ++ else if (size == 32 && op1 == 0x44) ++ view[-3] = 0x41; ++ view[-2] = 0x81; ++ view[-1] = 0xc0 | reg; ++ } ++ else ++ { ++ // addq ++ if (op1 == 0x4c) ++ view[-3] = 0x4d; ++ else if (size == 32 && op1 == 0x44) ++ view[-3] = 0x45; ++ view[-2] = 0x8d; ++ view[-1] = 0x80 | reg | (reg << 3); ++ } + } + else + { +- // addq +- if (op1 == 0x4c) +- view[-3] = 0x4d; +- else if (size == 32 && op1 == 0x44) +- view[-3] = 0x45; +- view[-2] = 0x8d; +- view[-1] = 0x80 | reg | (reg << 3); ++ if (op2 == 0x8b) ++ op2 = 0xc7; ++ else ++ op2 = 0x81; ++ ++ unsigned char rex2_mask = 4 | 4 << 4; ++ view[-3] = (view[-3] & ~rex2_mask) | ((view[-3] & rex2_mask) >> 2); ++ view[-2] = op2; ++ view[-1] = 0xc0 | reg; + } + + if (tls_segment != NULL) diff --git a/binutils.spec b/binutils.spec index fd1bac7..c894cb1 100644 --- a/binutils.spec +++ b/binutils.spec @@ -2,7 +2,7 @@ Summary: A GNU collection of binary utilities Name: binutils%{?_with_debug:-debug} Version: 2.41 -Release: 29%{?dist} +Release: 30%{?dist} License: GPL-3.0-or-later AND (GPL-3.0-or-later WITH Bison-exception-2.2) AND (LGPL-2.0-or-later WITH GCC-exception-2.0) AND BSD-3-Clause AND GFDL-1.3-or-later AND GPL-2.0-or-later AND LGPL-2.1-or-later AND LGPL-2.0-or-later URL: https://sourceware.org/binutils @@ -1354,6 +1354,9 @@ exit 0 #---------------------------------------------------------------------------- %changelog +* Mon Jan 22 2024 Nick Clifton - 2.41-30 +- Import commits 4a54cb06585f568031dfd291d0fe45979ad75e98 and 00a17c6ad068c95019e1f37cfc2d1b8aaebd6ecb to add APX support to GOLD. + * Sat Jan 20 2024 Jakub Jelinek - 2.41-29 - Import commit eed38d8a02b2 to update APX support. (#2259333)