[lld] r250864 - [ELF2] Determine the order of entries of symbol tables in the finalize() phase.
Igor Kudrin via llvm-commits
llvm-commits at lists.llvm.org
Tue Oct 20 14:47:58 PDT 2015
Author: ikudrin
Date: Tue Oct 20 16:47:58 2015
New Revision: 250864
URL: http://llvm.org/viewvc/llvm-project?rev=250864&view=rev
Log:
[ELF2] Determine the order of entries of symbol tables in the finalize() phase.
* Move the responsibility to call SymbolBody::setDynamicSymbolTableIndex()
from the hash table to the dynamic symbol table.
* Hash table is not longer responsible for filling the dynamic symbol table.
* The final order of symbols of both symbol tables is set before writing
phase starts.
* Remove repeaded scan of the symbol table during writting SymbolTableSection.
Differential Revision: http://reviews.llvm.org/D13911
Modified:
lld/trunk/ELF/OutputSections.cpp
lld/trunk/ELF/OutputSections.h
lld/trunk/ELF/Writer.cpp
Modified: lld/trunk/ELF/OutputSections.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.cpp?rev=250864&r1=250863&r2=250864&view=diff
==============================================================================
--- lld/trunk/ELF/OutputSections.cpp (original)
+++ lld/trunk/ELF/OutputSections.cpp Tue Oct 20 16:47:58 2015
@@ -250,17 +250,9 @@ static uint32_t hash(StringRef Name) {
return H;
}
-template <class ELFT> void HashTableSection<ELFT>::addSymbol(SymbolBody *S) {
- StringRef Name = S->getName();
- Out<ELFT>::DynSymTab->addSymbol(Name);
- Hashes.push_back(hash(Name));
- S->setDynamicSymbolTableIndex(Hashes.size());
-}
-
template <class ELFT> void HashTableSection<ELFT>::finalize() {
this->Header.sh_link = Out<ELFT>::DynSymTab->SectionIndex;
- assert(Out<ELFT>::DynSymTab->getNumSymbols() == Hashes.size() + 1);
unsigned NumEntries = 2; // nbucket and nchain.
NumEntries += Out<ELFT>::DynSymTab->getNumSymbols(); // The chain entries.
@@ -280,8 +272,10 @@ template <class ELFT> void HashTableSect
Elf_Word *Buckets = P;
Elf_Word *Chains = P + NumSymbols;
- for (unsigned I = 1; I < NumSymbols; ++I) {
- uint32_t Hash = Hashes[I - 1] % NumSymbols;
+ for (SymbolBody *Body : Out<ELFT>::DynSymTab->getSymbols()) {
+ StringRef Name = Body->getName();
+ unsigned I = Body->getDynamicSymbolTableIndex();
+ uint32_t Hash = hash(Name) % NumSymbols;
Chains[I] = Buckets[Hash];
Buckets[Hash] = I;
}
@@ -696,14 +690,32 @@ template <class ELFT> void SymbolTableSe
this->Header.sh_size = getNumSymbols() * sizeof(Elf_Sym);
this->Header.sh_link = StrTabSec.SectionIndex;
this->Header.sh_info = NumLocals + 1;
+
+ if (!StrTabSec.isDynamic()) {
+ std::stable_sort(Symbols.begin(), Symbols.end(),
+ [](SymbolBody *L, SymbolBody *R) {
+ return getSymbolBinding(L) == STB_LOCAL &&
+ getSymbolBinding(R) != STB_LOCAL;
+ });
+ return;
+ }
+ size_t I = 0;
+ for (SymbolBody *Body : Symbols)
+ Body->setDynamicSymbolTableIndex(++I);
}
template <class ELFT>
-void SymbolTableSection<ELFT>::addSymbol(StringRef Name, bool isLocal) {
+void SymbolTableSection<ELFT>::addLocalSymbol(StringRef Name) {
StrTabSec.add(Name);
++NumVisible;
- if (isLocal)
- ++NumLocals;
+ ++NumLocals;
+}
+
+template <class ELFT>
+void SymbolTableSection<ELFT>::addSymbol(SymbolBody *Body) {
+ StrTabSec.add(Body->getName());
+ Symbols.push_back(Body);
+ ++NumVisible;
}
template <class ELFT> void SymbolTableSection<ELFT>::writeTo(uint8_t *Buf) {
@@ -754,18 +766,9 @@ template <class ELFT>
void SymbolTableSection<ELFT>::writeGlobalSymbols(uint8_t *Buf) {
// Write the internal symbol table contents to the output symbol table
// pointed by Buf.
- uint8_t *Start = Buf;
- for (const std::pair<StringRef, Symbol *> &P : Table.getSymbols()) {
- StringRef Name = P.first;
- Symbol *Sym = P.second;
- SymbolBody *Body = Sym->Body;
- if (!includeInSymtab<ELFT>(*Body))
- continue;
- if (StrTabSec.isDynamic() && !includeInDynamicSymtab(*Body))
- continue;
-
- auto *ESym = reinterpret_cast<Elf_Sym *>(Buf);
- Buf += sizeof(*ESym);
+ auto *ESym = reinterpret_cast<Elf_Sym *>(Buf);
+ for (SymbolBody *Body : Symbols) {
+ StringRef Name = Body->getName();
ESym->st_name = StrTabSec.getFileOff(Name);
@@ -809,13 +812,9 @@ void SymbolTableSection<ELFT>::writeGlob
ESym->st_shndx = SHN_ABS;
else if (OutSec)
ESym->st_shndx = OutSec->SectionIndex;
+
+ ++ESym;
}
- if (!StrTabSec.isDynamic())
- std::stable_sort(
- reinterpret_cast<Elf_Sym *>(Start), reinterpret_cast<Elf_Sym *>(Buf),
- [](const Elf_Sym &A, const Elf_Sym &B) -> bool {
- return A.getBinding() == STB_LOCAL && B.getBinding() != STB_LOCAL;
- });
}
template <class ELFT>
Modified: lld/trunk/ELF/OutputSections.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.h?rev=250864&r1=250863&r2=250864&view=diff
==============================================================================
--- lld/trunk/ELF/OutputSections.h (original)
+++ lld/trunk/ELF/OutputSections.h Tue Oct 20 16:47:58 2015
@@ -172,10 +172,13 @@ public:
void finalize() override;
void writeTo(uint8_t *Buf) override;
- void addSymbol(StringRef Name, bool isLocal = false);
+ void addLocalSymbol(StringRef Name);
+ void addSymbol(SymbolBody *Body);
StringTableSection<ELFT> &getStrTabSec() const { return StrTabSec; }
unsigned getNumSymbols() const { return NumVisible + 1; }
+ ArrayRef<SymbolBody *> getSymbols() const { return Symbols; }
+
private:
void writeLocalSymbols(uint8_t *&Buf);
void writeGlobalSymbols(uint8_t *Buf);
@@ -184,6 +187,7 @@ private:
SymbolTable<ELFT> &Table;
StringTableSection<ELFT> &StrTabSec;
+ std::vector<SymbolBody *> Symbols;
unsigned NumVisible = 0;
unsigned NumLocals = 0;
};
@@ -275,12 +279,8 @@ class HashTableSection final : public Ou
public:
HashTableSection();
- void addSymbol(SymbolBody *S);
void finalize() override;
void writeTo(uint8_t *Buf) override;
-
-private:
- std::vector<uint32_t> Hashes;
};
template <class ELFT>
Modified: lld/trunk/ELF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=250864&r1=250863&r2=250864&view=diff
==============================================================================
--- lld/trunk/ELF/Writer.cpp (original)
+++ lld/trunk/ELF/Writer.cpp Tue Oct 20 16:47:58 2015
@@ -282,7 +282,7 @@ template <class ELFT> void Writer<ELFT>:
StringRef SymName = *SymNameOrErr;
if (!shouldKeepInSymtab<ELFT>(*F, SymName, Sym))
continue;
- Out<ELFT>::SymTab->addSymbol(SymName, true);
+ Out<ELFT>::SymTab->addLocalSymbol(SymName);
}
}
}
@@ -498,7 +498,6 @@ template <class ELFT> void Writer<ELFT>:
// FIXME: Try to avoid the extra walk over all global symbols.
std::vector<DefinedCommon<ELFT> *> CommonSymbols;
for (auto &P : Symtab.getSymbols()) {
- StringRef Name = P.first;
SymbolBody *Body = P.second->Body;
if (auto *U = dyn_cast<Undefined<ELFT>>(Body))
if (!U->isWeak() && !U->canKeepUndefined())
@@ -508,10 +507,10 @@ template <class ELFT> void Writer<ELFT>:
CommonSymbols.push_back(C);
if (!includeInSymtab<ELFT>(*Body))
continue;
- Out<ELFT>::SymTab->addSymbol(Name);
+ Out<ELFT>::SymTab->addSymbol(Body);
if (isOutputDynamic() && includeInDynamicSymtab(*Body))
- Out<ELFT>::HashTab->addSymbol(Body);
+ Out<ELFT>::DynSymTab->addSymbol(Body);
}
addCommonSymbols(CommonSymbols);
More information about the llvm-commits
mailing list