diff --git a/lld/ELF/Writer.cpp b/lld/ELF/Writer.cpp index 5adeea94380e..5d2e3c54b4b0 100644 --- a/lld/ELF/Writer.cpp +++ b/lld/ELF/Writer.cpp @@ -329,13 +329,24 @@ template void Writer::createSections() { DynamicSec.FiniArraySec = Map.lookup({".fini_array", SHT_FINI_ARRAY, SHF_WRITE | SHF_ALLOC}); - if (OutputSection *OS = DynamicSec.InitArraySec) { - Symtab.addSyntheticSym("__init_array_start", *OS, 0); - Symtab.addSyntheticSym("__init_array_end", *OS, OS->getSize()); - } else { - Symtab.addIgnoredSym("__init_array_start"); - Symtab.addIgnoredSym("__init_array_end"); - } + auto addStartEnd = [&Symtab](StringRef StartName, StringRef EndName, + OutputSection *OS) { + if (OS) { + Symtab.addSyntheticSym(StartName, *OS, 0); + Symtab.addSyntheticSym(EndName, *OS, OS->getSize()); + } + else { + Symtab.addIgnoredSym(StartName); + Symtab.addIgnoredSym(EndName); + } + }; + + addStartEnd("__preinit_array_start", "__preinit_array_end", + DynamicSec.PreInitArraySec); + addStartEnd("__init_array_start", "__init_array_end", + DynamicSec.InitArraySec); + addStartEnd("__fini_array_start", "__fini_array_end", + DynamicSec.FiniArraySec); // FIXME: Try to avoid the extra walk over all global symbols. std::vector *> CommonSymbols; diff --git a/lld/test/elf2/init_array_missing.s b/lld/test/elf2/init_array_missing.s deleted file mode 100644 index 38aa9cf8057b..000000000000 --- a/lld/test/elf2/init_array_missing.s +++ /dev/null @@ -1,18 +0,0 @@ -// RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t -// RUN: lld -flavor gnu2 %t -o %t2 -// RUN: llvm-objdump -d %t2 | FileCheck %s -// REQUIRES: x86 - -.globl _start -_start: - call __init_array_start - call __init_array_end - -// With no .init_array section the symbols resolve to 0 -// 0 - (0x11000 + 5) = -69637 -// 0 - (0x11005 + 5) = -69642 - -// CHECK: Disassembly of section .text: -// CHECK-NEXT: _start: -// CHECK-NEXT: 11000: e8 fb ef fe ff callq -69637 -// CHECK-NEXT: 11005: e8 f6 ef fe ff callq -69642 diff --git a/lld/test/elf2/init_array.s b/lld/test/elf2/pre_init_fini_array.s similarity index 57% rename from lld/test/elf2/init_array.s rename to lld/test/elf2/pre_init_fini_array.s index c2d1b672642a..da73f85aebe1 100644 --- a/lld/test/elf2/init_array.s +++ b/lld/test/elf2/pre_init_fini_array.s @@ -8,8 +8,12 @@ .globl _start _start: + call __preinit_array_start + call __preinit_array_end call __init_array_start call __init_array_end + call __fini_array_start + call __fini_array_end .section .init_array,"aw",@init_array @@ -55,7 +59,25 @@ _start: // CHECK-NEXT: Offset: // CHECK-NEXT: Size: [[FINI_SIZE:.*]] -// CHECK: Name: __init_array_end +// CHECK: Name: __fini_array_end +// CHECK-NEXT: Value: 0x1301B +// CHECK-NEXT: Size: 0 +// CHECK-NEXT: Binding: Local +// CHECK-NEXT: Type: None +// CHECK-NEXT: Other: 0 +// CHECK-NEXT: Section: .fini_array +// CHECK-NEXT: } +// CHECK-NEXT: Symbol { +// CHECK-NEXT: Name: __fini_array_start +// CHECK-NEXT: Value: [[FINI_ADDR]] +// CHECK-NEXT: Size: 0 +// CHECK-NEXT: Binding: Local +// CHECK-NEXT: Type: None +// CHECK-NEXT: Other: 0 +// CHECK-NEXT: Section: .fini_array +// CHECK-NEXT: } +// CHECK-NEXT: Symbol { +// CHECK-NEXT: Name: __init_array_end // CHECK-NEXT: Value: 0x13008 // CHECK-NEXT: Size: 0 // CHECK-NEXT: Binding: Local @@ -72,7 +94,24 @@ _start: // CHECK-NEXT: Other: 0 // CHECK-NEXT: Section: .init_array // CHECK-NEXT: } - +// CHECK-NEXT: Symbol { +// CHECK-NEXT: Name: __preinit_array_end +// CHECK-NEXT: Value: 0x13011 +// CHECK-NEXT: Size: 0 +// CHECK-NEXT: Binding: Local +// CHECK-NEXT: Type: None +// CHECK-NEXT: Other: 0 +// CHECK-NEXT: Section: .preinit_array +// CHECK-NEXT: } +// CHECK-NEXT: Symbol { +// CHECK-NEXT: Name: __preinit_array_start +// CHECK-NEXT: Value: [[PREINIT_ADDR]] +// CHECK-NEXT: Size: 0 +// CHECK-NEXT: Binding: Local +// CHECK-NEXT: Type: None +// CHECK-NEXT: Other: 0 +// CHECK-NEXT: Section: .preinit_array +// CHECK-NEXT: } // CHECK: DynamicSection // CHECK: PREINIT_ARRAY [[PREINIT_ADDR]] @@ -83,8 +122,16 @@ _start: // CHECK: FINI_ARRAYSZ [[FINI_SIZE]] (bytes) -// 0x13000 - (0x12000 + 5) = 4091 -// 0x13008 - (0x12005 + 5) = 4094 +// 0x13008 - (0x12000 + 5) = 4099 +// 0x13011 - (0x12005 + 5) = 4103 +// 0x13000 - (0x1200a + 5) = 4081 +// 0x13008 - (0x1200f + 5) = 4084 +// 0x13011 - (0x12014 + 5) = 4088 +// 0x1301B - (0x12019 + 5) = 4093 // DISASM: _start: -// DISASM-NEXT: 12000: e8 fb 0f 00 00 callq 4091 -// DISASM-NEXT: 12005: e8 fe 0f 00 00 callq 4094 +// DISASM-NEXT: 12000: e8 {{.*}} callq 4099 +// DISASM-NEXT: 12005: e8 {{.*}} callq 4103 +// DISASM-NEXT: 1200a: e8 {{.*}} callq 4081 +// DISASM-NEXT: 1200f: e8 {{.*}} callq 4084 +// DISASM-NEXT: 12014: e8 {{.*}} callq 4088 +// DISASM-NEXT: 12019: e8 {{.*}} callq 4093 diff --git a/lld/test/elf2/pre_init_fini_array_missing.s b/lld/test/elf2/pre_init_fini_array_missing.s new file mode 100644 index 000000000000..d740f8c86008 --- /dev/null +++ b/lld/test/elf2/pre_init_fini_array_missing.s @@ -0,0 +1,30 @@ +// RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t +// RUN: lld -flavor gnu2 %t -o %t2 +// RUN: llvm-objdump -d %t2 | FileCheck %s +// REQUIRES: x86 + +.globl _start +_start: + call __preinit_array_start + call __preinit_array_end + call __init_array_start + call __init_array_end + call __fini_array_start + call __fini_array_end + +// With no .init_array section the symbols resolve to 0 +// 0 - (0x11000 + 5) = -69637 +// 0 - (0x11005 + 5) = -69642 +// 0 - (0x1100a + 5) = -69647 +// 0 - (0x1100f + 5) = -69652 +// 0 - (0x11014 + 5) = -69657 +// 0 - (0x11019 + 5) = -69662 + +// CHECK: Disassembly of section .text: +// CHECK-NEXT: _start: +// CHECK-NEXT: 11000: e8 fb ef fe ff callq -69637 +// CHECK-NEXT: 11005: e8 f6 ef fe ff callq -69642 +// CHECK-NEXT: 1100a: e8 f1 ef fe ff callq -69647 +// CHECK-NEXT: 1100f: e8 ec ef fe ff callq -69652 +// CHECK-NEXT: 11014: e8 e7 ef fe ff callq -69657 +// CHECK-NEXT: 11019: e8 e2 ef fe ff callq -69662