aboutsummaryrefslogtreecommitdiff
path: root/ELF
diff options
context:
space:
mode:
authorRui Ueyama <ruiu@google.com>2017-09-25 02:29:51 +0000
committerRui Ueyama <ruiu@google.com>2017-09-25 02:29:51 +0000
commit253af14cc25332a395e231dd131e2bb2002d4d6d (patch)
treeeb9a8bdf47ec7c015aeefe65b123b52edbc26366 /ELF
parent4a8e0b7cc47add188be306ffecabb94d1f0be267 (diff)
Do not use StringTableBuilder to build symbol table for .gdb_index.
Previously, we had two levels of hash table lookup. The first hash lookup uses CachedHashStringRefs as keys and returns offsets in string table. Then, we did the second hash table lookup to obtain GdbSymbol pointers. But we can directly map strings to GDbSymbols. One test file is updated in this patch because we no longer have a '\0' byte at the start of the string pool, which was automatically inserted by StringTableBuilder. This patch speeds up Clang debug build (with -gdb-index) link time by 0.3 seconds. git-svn-id: https://llvm.org/svn/llvm-project/lld/trunk@314092 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'ELF')
-rw-r--r--ELF/SyntheticSections.cpp31
-rw-r--r--ELF/SyntheticSections.h9
2 files changed, 23 insertions, 17 deletions
diff --git a/ELF/SyntheticSections.cpp b/ELF/SyntheticSections.cpp
index 8d4e09e8b..b006c0bcb 100644
--- a/ELF/SyntheticSections.cpp
+++ b/ELF/SyntheticSections.cpp
@@ -1787,19 +1787,22 @@ void GdbIndexSection::fixCuIndex() {
std::vector<std::set<uint32_t>> GdbIndexSection::createCuVectors() {
std::vector<std::set<uint32_t>> Ret;
uint32_t Idx = 0;
+ uint32_t Off = 0;
for (GdbIndexChunk &Chunk : Chunks) {
for (GdbIndexChunk::NameTypeEntry &Ent : Chunk.NamesAndTypes) {
- size_t Offset = StringPool.add(Ent.Name);
- GdbSymbol *&Sym = SymbolMap[Offset];
+ GdbSymbol *&Sym = Symbols[Ent.Name];
if (!Sym) {
- Sym = make<GdbSymbol>(GdbSymbol{Ent.Name.hash(), Offset, Ret.size()});
+ Sym = make<GdbSymbol>(GdbSymbol{Ent.Name.hash(), Off, Ret.size()});
+ Off += Ent.Name.size() + 1;
Ret.resize(Ret.size() + 1);
}
Ret[Sym->CuVectorIndex].insert((Ent.Type << 24) | Idx);
}
Idx += Chunk.CompilationUnits.size();
}
+
+ StringPoolSize = Off;
return Ret;
}
@@ -1835,12 +1838,14 @@ static size_t getAddressAreaSize(ArrayRef<GdbIndexChunk> Arr) {
}
std::vector<GdbSymbol *> GdbIndexSection::createGdbSymtab() {
- uint32_t Size =
- std::max<uint32_t>(1024, NextPowerOf2(SymbolMap.size() * 4 / 3));
+ uint32_t Size = NextPowerOf2(Symbols.size() * 4 / 3);
+ if (Size < 1024)
+ Size = 1024;
+
uint32_t Mask = Size - 1;
std::vector<GdbSymbol *> Ret(Size);
- for (auto &KV : SymbolMap) {
+ for (auto &KV : Symbols) {
GdbSymbol *Sym = KV.second;
uint32_t I = Sym->NameHash & Mask;
uint32_t Step = ((Sym->NameHash * 17) & Mask) | 1;
@@ -1853,8 +1858,7 @@ std::vector<GdbSymbol *> GdbIndexSection::createGdbSymtab() {
}
GdbIndexSection::GdbIndexSection(std::vector<GdbIndexChunk> &&C)
- : SyntheticSection(0, SHT_PROGBITS, 1, ".gdb_index"),
- StringPool(llvm::StringTableBuilder::ELF), Chunks(std::move(C)) {
+ : SyntheticSection(0, SHT_PROGBITS, 1, ".gdb_index"), Chunks(std::move(C)) {
fixCuIndex();
CuVectors = createCuVectors();
GdbSymtab = createGdbSymtab();
@@ -1871,11 +1875,10 @@ GdbIndexSection::GdbIndexSection(std::vector<GdbIndexChunk> &&C)
Off += (CuVec.size() + 1) * 4;
}
StringPoolOffset = ConstantPoolOffset + Off;
- StringPool.finalizeInOrder();
}
size_t GdbIndexSection::getSize() const {
- return StringPoolOffset + StringPool.getSize();
+ return StringPoolOffset + StringPoolSize;
}
void GdbIndexSection::writeTo(uint8_t *Buf) {
@@ -1929,7 +1932,13 @@ void GdbIndexSection::writeTo(uint8_t *Buf) {
}
// Write the string pool.
- StringPool.write(Buf);
+ for (auto &KV : Symbols) {
+ CachedHashStringRef S = KV.first;
+ GdbSymbol *Sym = KV.second;
+ size_t Off = Sym->NameOffset;
+ memcpy(Buf + Off, S.val().data(), S.size());
+ Buf[Off + S.size() + 1] = '\0';
+ }
}
bool GdbIndexSection::empty() const { return !Out::DebugInfo; }
diff --git a/ELF/SyntheticSections.h b/ELF/SyntheticSections.h
index 200ae95a8..019949918 100644
--- a/ELF/SyntheticSections.h
+++ b/ELF/SyntheticSections.h
@@ -542,15 +542,11 @@ private:
// A symbol table for this .gdb_index section.
std::vector<GdbSymbol *> GdbSymtab;
- // Symbol table entries are uniquified by their offsets, so
- // we need a map from offsets to symbols.
- llvm::DenseMap<size_t, GdbSymbol *> SymbolMap;
-
// CU vector is a part of constant pool area of section.
std::vector<std::set<uint32_t>> CuVectors;
- // String pool is also a part of constant pool, it follows CU vectors.
- llvm::StringTableBuilder StringPool;
+ // Symbol table contents.
+ llvm::DenseMap<llvm::CachedHashStringRef, GdbSymbol *> Symbols;
// Each chunk contains information gathered from a debug sections of single
// object and used to build different areas of gdb index.
@@ -561,6 +557,7 @@ private:
uint32_t SymtabOffset;
uint32_t ConstantPoolOffset;
uint32_t StringPoolOffset;
+ uint32_t StringPoolSize;
std::vector<size_t> CuVectorOffsets;
};