diff options
-rw-r--r-- | lld/ELF/Writer.cpp | 33 | ||||
-rw-r--r-- | lld/test/elf2/shared.s | 15 |
2 files changed, 36 insertions, 12 deletions
diff --git a/lld/ELF/Writer.cpp b/lld/ELF/Writer.cpp index 4856c5d41a5..24e74e654b0 100644 --- a/lld/ELF/Writer.cpp +++ b/lld/ELF/Writer.cpp @@ -174,6 +174,8 @@ public: ++NumVisible; } + StringTableSection<ELFT::Is64Bits> &getStrTabSec() { return StrTabSec; } + private: SymbolTable &Table; StringTableSection<ELFT::Is64Bits> &StrTabSec; @@ -181,23 +183,25 @@ private: const Writer<ELFT> &W; }; -template <bool Is64Bits> -class DynamicSection final : public OutputSectionBase<Is64Bits> { - typedef OutputSectionBase<Is64Bits> Base; +template <class ELFT> +class DynamicSection final : public OutputSectionBase<ELFT::Is64Bits> { + typedef OutputSectionBase<ELFT::Is64Bits> Base; typedef typename Base::HeaderT HeaderT; typedef typename Base::Elf_Dyn Elf_Dyn; public: - DynamicSection(SymbolTable &SymTab, StringTableSection<Is64Bits> &DynStrSec) - : OutputSectionBase<Is64Bits>(".dynamic", SHT_DYNAMIC, - SHF_ALLOC | SHF_WRITE), - DynStrSec(DynStrSec), SymTab(SymTab) { + DynamicSection(SymbolTable &SymTab, SymbolTableSection<ELFT> &DynSymSec) + : OutputSectionBase<ELFT::Is64Bits>(".dynamic", SHT_DYNAMIC, + SHF_ALLOC | SHF_WRITE), + DynStrSec(DynSymSec.getStrTabSec()), DynSymSec(DynSymSec), + SymTab(SymTab) { typename Base::HeaderT &Header = this->Header; - Header.sh_addralign = Is64Bits ? 8 : 4; - Header.sh_entsize = Is64Bits ? 16 : 8; + Header.sh_addralign = ELFT::Is64Bits ? 8 : 4; + Header.sh_entsize = ELFT::Is64Bits ? 16 : 8; unsigned NumEntries = 0; + ++NumEntries; // DT_SYMTAB ++NumEntries; // DT_STRTAB ++NumEntries; // DT_STRSZ @@ -219,6 +223,10 @@ public: void writeTo(uint8_t *Buf) override { auto *P = reinterpret_cast<Elf_Dyn *>(Buf); + P->d_tag = DT_SYMTAB; + P->d_un.d_ptr = DynSymSec.getVA(); + ++P; + P->d_tag = DT_STRTAB; P->d_un.d_ptr = DynStrSec.getVA(); ++P; @@ -241,7 +249,8 @@ public: } private: - StringTableSection<Is64Bits> &DynStrSec; + StringTableSection<ELFT::Is64Bits> &DynStrSec; + SymbolTableSection<ELFT> &DynSymSec; SymbolTable &SymTab; }; @@ -255,7 +264,7 @@ public: typedef typename ELFFile<ELFT>::Elf_Sym Elf_Sym; Writer(SymbolTable *T) : StrTabSec(false), DynStrSec(true), SymTabSec(*this, *T, StrTabSec), - DynSymSec(*this, *T, DynStrSec), DynamicSec(*T, DynStrSec) {} + DynSymSec(*this, *T, DynStrSec), DynamicSec(*T, DynSymSec) {} void run(); const OutputSection<ELFT> &getBSS() const { @@ -286,7 +295,7 @@ private: SymbolTableSection<ELFT> SymTabSec; SymbolTableSection<ELFT> DynSymSec; - DynamicSection<ELFT::Is64Bits> DynamicSec; + DynamicSection<ELFT> DynamicSec; OutputSection<ELFT> *BSSSec = nullptr; }; diff --git a/lld/test/elf2/shared.s b/lld/test/elf2/shared.s index 2e7c41337c9..707efded9ff 100644 --- a/lld/test/elf2/shared.s +++ b/lld/test/elf2/shared.s @@ -3,6 +3,20 @@ // RUN: llvm-readobj --program-headers --dynamic-table -t -s -dyn-symbols %t | FileCheck %s // REQUIRES: x86 +// CHECK: Name: .dynsym +// CHECK-NEXT: Type: SHT_DYNSYM +// CHECK-NEXT: Flags [ +// CHECK-NEXT: SHF_ALLOC +// CHECK-NEXT: ] +// CHECK-NEXT: Address: [[DYNSYMADDR:.*]] +// CHECK-NEXT: Offset: 0x2000 +// CHECK-NEXT: Size: 48 +// CHECK-NEXT: Link: 6 +// CHECK-NEXT: Info: 1 +// CHECK-NEXT: AddressAlignment: 4 +// CHECK-NEXT: EntrySize: 16 +// CHECK-NEXT: } + // CHECK: Name: .dynamic // CHECK-NEXT: Type: SHT_DYNAMIC // CHECK-NEXT: Flags [ @@ -96,6 +110,7 @@ // CHECK: DynamicSection [ // CHECK-NEXT: Tag Type Name/Value +// CHECK-NEXT: 0x00000006 SYMTAB [[DYNSYMADDR]] // CHECK-NEXT: 0x00000005 STRTAB [[DYNSTRADDR]] // CHECK-NEXT: 0x0000000A STRSZ // CHECK-NEXT: 0x00000001 NEEDED SharedLibrary ({{.*}}/Inputs/i686-simple-library.so) |