Index: ELF/InputSection.cpp =================================================================== --- ELF/InputSection.cpp +++ ELF/InputSection.cpp @@ -130,7 +130,7 @@ template static typename llvm::object::ELFFile::uintX_t getSymSize(SymbolBody &Body) { - if (auto *SS = dyn_cast>(&Body)) + if (auto *SS = dyn_cast>(&Body)) return SS->Sym.st_size; return 0; } Index: ELF/OutputSections.cpp =================================================================== --- ELF/OutputSections.cpp +++ ELF/OutputSections.cpp @@ -787,7 +787,7 @@ switch (S.kind()) { case SymbolBody::DefinedSyntheticKind: { auto &D = cast>(S); - return D.Section.getVA() + D.Sym.st_value; + return D.Section.getVA() + D.Value; } case SymbolBody::DefinedAbsoluteKind: return cast>(S).Sym.st_value; @@ -1320,7 +1320,7 @@ template static const typename llvm::object::ELFFile::Elf_Sym * getElfSym(SymbolBody &Body) { - if (auto *EBody = dyn_cast>(&Body)) + if (auto *EBody = dyn_cast>(&Body)) return &EBody->Sym; if (auto *EBody = dyn_cast>(&Body)) return &EBody->Sym; @@ -1392,6 +1392,8 @@ return STB_LOCAL; if (const Elf_Sym *ESym = getElfSym(*Body)) return ESym->getBinding(); + if (isa>(Body)) + return STB_LOCAL; return Body->isWeak() ? STB_WEAK : STB_GLOBAL; } Index: ELF/SymbolTable.cpp =================================================================== --- ELF/SymbolTable.cpp +++ ELF/SymbolTable.cpp @@ -102,11 +102,7 @@ void SymbolTable::addSynthetic(StringRef Name, OutputSectionBase &Section, typename ELFFile::uintX_t Value) { - typedef typename DefinedSynthetic::Elf_Sym Elf_Sym; - auto *ESym = new (Alloc) Elf_Sym; - memset(ESym, 0, sizeof(Elf_Sym)); - ESym->st_value = Value; - auto *Sym = new (Alloc) DefinedSynthetic(Name, *ESym, Section); + auto *Sym = new (Alloc) DefinedSynthetic(Name, Value, Section); resolve(Sym); } Index: ELF/Symbols.h =================================================================== --- ELF/Symbols.h +++ ELF/Symbols.h @@ -59,9 +59,9 @@ DefinedRegularKind = DefinedFirst, DefinedAbsoluteKind, DefinedCommonKind, - DefinedSyntheticKind, SharedKind, - DefinedLast = SharedKind, + DefinedSyntheticKind, + DefinedLast = DefinedSyntheticKind, UndefinedElfKind, UndefinedKind, LazyKind @@ -131,21 +131,28 @@ }; // The base class for any defined symbols, including absolute symbols, etc. -template class Defined : public SymbolBody { +class Defined : public SymbolBody { +public: + Defined(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility, bool IsTls); + static bool classof(const SymbolBody *S) { return S->isDefined(); } +}; + +// Any defined symbol from an elf file. +template class DefinedElf : public Defined { protected: typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; public: - Defined(Kind K, StringRef N, const Elf_Sym &Sym) - : SymbolBody(K, N, Sym.getBinding() == llvm::ELF::STB_WEAK, - Sym.getVisibility(), Sym.getType() == llvm::ELF::STT_TLS), + DefinedElf(Kind K, StringRef N, const Elf_Sym &Sym) + : Defined(K, N, Sym.getBinding() == llvm::ELF::STB_WEAK, + Sym.getVisibility(), Sym.getType() == llvm::ELF::STT_TLS), Sym(Sym) {} const Elf_Sym &Sym; - static bool classof(const SymbolBody *S) { return S->isDefined(); } + static bool classof(const SymbolBody *S) { return S->kind() <= SharedKind; } }; -template class DefinedAbsolute : public Defined { +template class DefinedAbsolute : public DefinedElf { typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; public: @@ -167,7 +174,7 @@ static Elf_Sym RelaIpltEnd; DefinedAbsolute(StringRef N, const Elf_Sym &Sym) - : Defined(SymbolBody::DefinedAbsoluteKind, N, Sym) {} + : DefinedElf(SymbolBody::DefinedAbsoluteKind, N, Sym) {} static bool classof(const SymbolBody *S) { return S->kind() == SymbolBody::DefinedAbsoluteKind; @@ -189,13 +196,13 @@ template typename DefinedAbsolute::Elf_Sym DefinedAbsolute::RelaIpltEnd; -template class DefinedCommon : public Defined { +template class DefinedCommon : public DefinedElf { typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; public: typedef typename llvm::object::ELFFile::uintX_t uintX_t; DefinedCommon(StringRef N, const Elf_Sym &Sym) - : Defined(SymbolBody::DefinedCommonKind, N, Sym) { + : DefinedElf(SymbolBody::DefinedCommonKind, N, Sym) { MaxAlignment = Sym.st_value; } @@ -212,13 +219,13 @@ }; // Regular defined symbols read from object file symbol tables. -template class DefinedRegular : public Defined { +template class DefinedRegular : public DefinedElf { typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; public: DefinedRegular(StringRef N, const Elf_Sym &Sym, InputSectionBase &Section) - : Defined(SymbolBody::DefinedRegularKind, N, Sym), + : DefinedElf(SymbolBody::DefinedRegularKind, N, Sym), Section(Section) {} static bool classof(const SymbolBody *S) { @@ -232,18 +239,18 @@ // The difference from the regular symbol is that DefinedSynthetic symbols // don't belong to any input files or sections. Thus, its constructor // takes an output section to calculate output VA, etc. -template class DefinedSynthetic : public Defined { +template class DefinedSynthetic : public Defined { public: typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; - DefinedSynthetic(StringRef N, const Elf_Sym &Sym, - OutputSectionBase &Section) - : Defined(SymbolBody::DefinedSyntheticKind, N, Sym), - Section(Section) {} + typedef typename llvm::object::ELFFile::uintX_t uintX_t; + DefinedSynthetic(StringRef N, uintX_t Value, + OutputSectionBase &Section); static bool classof(const SymbolBody *S) { return S->kind() == SymbolBody::DefinedSyntheticKind; } + uintX_t Value; const OutputSectionBase &Section; }; @@ -276,7 +283,7 @@ } }; -template class SharedSymbol : public Defined { +template class SharedSymbol : public DefinedElf { typedef typename llvm::object::ELFFile::Elf_Sym Elf_Sym; typedef typename llvm::object::ELFFile::uintX_t uintX_t; @@ -286,7 +293,7 @@ } SharedSymbol(SharedFile *F, StringRef Name, const Elf_Sym &Sym) - : Defined(SymbolBody::SharedKind, Name, Sym), File(F) {} + : DefinedElf(SymbolBody::SharedKind, Name, Sym), File(F) {} SharedFile *File; Index: ELF/Symbols.cpp =================================================================== --- ELF/Symbols.cpp +++ ELF/Symbols.cpp @@ -73,6 +73,10 @@ return 0; } +Defined::Defined(Kind K, StringRef Name, bool IsWeak, uint8_t Visibility, + bool IsTls) + : SymbolBody(K, Name, IsWeak, Visibility, IsTls) {} + Undefined::Undefined(SymbolBody::Kind K, StringRef N, bool IsWeak, uint8_t Visibility, bool IsTls) : SymbolBody(K, N, IsWeak, Visibility, IsTls), CanKeepUndefined(false) {} @@ -91,6 +95,12 @@ Sym.getType() == llvm::ELF::STT_TLS), Sym(Sym) {} +template +DefinedSynthetic::DefinedSynthetic(StringRef N, uintX_t Value, + OutputSectionBase &Section) + : Defined(SymbolBody::DefinedSyntheticKind, N, false, STV_DEFAULT, false), + Value(Value), Section(Section) {} + std::unique_ptr Lazy::getMember() { MemoryBufferRef MBRef = File->getMember(&Sym); @@ -124,3 +134,8 @@ template class lld::elf2::UndefinedElf; template class lld::elf2::UndefinedElf; template class lld::elf2::UndefinedElf; + +template class lld::elf2::DefinedSynthetic; +template class lld::elf2::DefinedSynthetic; +template class lld::elf2::DefinedSynthetic; +template class lld::elf2::DefinedSynthetic; Index: ELF/Target.cpp =================================================================== --- ELF/Target.cpp +++ ELF/Target.cpp @@ -71,7 +71,7 @@ } template bool isGnuIFunc(const SymbolBody &S) { - if (auto *SS = dyn_cast>(&S)) + if (auto *SS = dyn_cast>(&S)) return SS->Sym.getType() == STT_GNU_IFUNC; return false; }