#ifndef LLVM_DEBUGINFO_CODEVIEW_DEBUGSTRINGTABLESUBSECTION_H
#define LLVM_DEBUGINFO_CODEVIEW_DEBUGSTRINGTABLESUBSECTION_H
+#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/DebugInfo/CodeView/CodeView.h"
uint32_t insert(StringRef S);
// Return the ID for string S. Assumes S exists in the table.
- uint32_t getStringId(StringRef S) const;
+ uint32_t getIdForString(StringRef S) const;
+
+ StringRef getStringForId(uint32_t Id) const;
uint32_t calculateSerializedSize() const override;
Error commit(BinaryStreamWriter &Writer) const override;
uint32_t size() const;
- StringMap<uint32_t>::const_iterator begin() const { return Strings.begin(); }
+ StringMap<uint32_t>::const_iterator begin() const {
+ return StringToId.begin();
+ }
- StringMap<uint32_t>::const_iterator end() const { return Strings.end(); }
+ StringMap<uint32_t>::const_iterator end() const { return StringToId.end(); }
private:
- StringMap<uint32_t> Strings;
+ DenseMap<uint32_t, StringRef> IdToString;
+ StringMap<uint32_t> StringToId;
uint32_t StringSize = 1;
};
Deleted.clear();
}
+ bool empty() const { return size() == 0; }
uint32_t capacity() const { return Buckets.size(); }
uint32_t size() const { return Present.count(); }
// Returns the ID for S.
uint32_t insert(StringRef S);
+ uint32_t getIdForString(StringRef S) const;
+ StringRef getStringForId(uint32_t Id) const;
+
uint32_t calculateSerializedSize() const;
Error commit(BinaryStreamWriter &Writer) const;
}
uint32_t DebugChecksumsSubsection::mapChecksumOffset(StringRef FileName) const {
- uint32_t Offset = Strings.getStringId(FileName);
+ uint32_t Offset = Strings.getIdForString(FileName);
auto Iter = OffsetMap.find(Offset);
assert(Iter != OffsetMap.end());
return Iter->second;
Ids.push_back(&M);
std::sort(Ids.begin(), Ids.end(), [this](const T &L1, const T &L2) {
- return Strings.getStringId(L1->getKey()) <
- Strings.getStringId(L2->getKey());
+ return Strings.getIdForString(L1->getKey()) <
+ Strings.getIdForString(L2->getKey());
});
for (const auto &Item : Ids) {
CrossModuleImport Imp;
- Imp.ModuleNameOffset = Strings.getStringId(Item->getKey());
+ Imp.ModuleNameOffset = Strings.getIdForString(Item->getKey());
Imp.Count = Item->getValue().size();
if (auto EC = Writer.writeObject(Imp))
return EC;
: DebugSubsection(DebugSubsectionKind::StringTable) {}
uint32_t DebugStringTableSubsection::insert(StringRef S) {
- auto P = Strings.insert({S, StringSize});
+ auto P = StringToId.insert({S, StringSize});
// If a given string didn't exist in the string table, we want to increment
- // the string table size.
- if (P.second)
+ // the string table size and insert it into the reverse lookup.
+ if (P.second) {
+ IdToString.insert({P.first->getValue(), P.first->getKey()});
StringSize += S.size() + 1; // +1 for '\0'
+ }
+
return P.first->second;
}
if (auto EC = Writer.writeCString(StringRef()))
return EC;
- for (auto &Pair : Strings) {
+ for (auto &Pair : StringToId) {
StringRef S = Pair.getKey();
uint32_t Offset = Begin + Pair.getValue();
Writer.setOffset(Offset);
return Error::success();
}
-uint32_t DebugStringTableSubsection::size() const { return Strings.size(); }
+uint32_t DebugStringTableSubsection::size() const { return StringToId.size(); }
+
+uint32_t DebugStringTableSubsection::getIdForString(StringRef S) const {
+ auto Iter = StringToId.find(S);
+ assert(Iter != StringToId.end());
+ return Iter->second;
+}
-uint32_t DebugStringTableSubsection::getStringId(StringRef S) const {
- auto Iter = Strings.find(S);
- assert(Iter != Strings.end());
+StringRef DebugStringTableSubsection::getStringForId(uint32_t Id) const {
+ auto Iter = IdToString.find(Id);
+ assert(Iter != IdToString.end());
return Iter->second;
}
return Strings.insert(S);
}
+uint32_t PDBStringTableBuilder::getIdForString(StringRef S) const {
+ return Strings.getIdForString(S);
+}
+
+StringRef PDBStringTableBuilder::getStringForId(uint32_t Id) const {
+ return Strings.getStringForId(Id);
+}
+
static uint32_t computeBucketCount(uint32_t NumStrings) {
// The /names stream is basically an on-disk open-addressing hash table.
// Hash collisions are resolved by linear probing. We cannot make