summaryrefslogtreecommitdiffstats
path: root/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp')
-rw-r--r--llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp120
1 files changed, 66 insertions, 54 deletions
diff --git a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp
index f75a2411ac2..c4fecb80ea5 100644
--- a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp
+++ b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp
@@ -14,9 +14,9 @@
#include "StreamUtil.h"
#include "llvm-pdbdump.h"
+#include "llvm/DebugInfo/CodeView/CVTypeDumper.h"
#include "llvm/DebugInfo/CodeView/CVTypeVisitor.h"
#include "llvm/DebugInfo/CodeView/EnumTables.h"
-#include "llvm/DebugInfo/CodeView/LazyRandomTypeCollection.h"
#include "llvm/DebugInfo/CodeView/Line.h"
#include "llvm/DebugInfo/CodeView/ModuleDebugFileChecksumFragment.h"
#include "llvm/DebugInfo/CodeView/ModuleDebugFragmentVisitor.h"
@@ -25,6 +25,7 @@
#include "llvm/DebugInfo/CodeView/ModuleDebugUnknownFragment.h"
#include "llvm/DebugInfo/CodeView/SymbolDumper.h"
#include "llvm/DebugInfo/CodeView/TypeDatabaseVisitor.h"
+#include "llvm/DebugInfo/CodeView/TypeDeserializer.h"
#include "llvm/DebugInfo/CodeView/TypeDumpVisitor.h"
#include "llvm/DebugInfo/CodeView/TypeVisitorCallbackPipeline.h"
#include "llvm/DebugInfo/MSF/MappedBlockStream.h"
@@ -83,7 +84,7 @@ struct PageStats {
class C13RawVisitor : public C13DebugFragmentVisitor {
public:
- C13RawVisitor(ScopedPrinter &P, PDBFile &F, LazyRandomTypeCollection &IPI)
+ C13RawVisitor(ScopedPrinter &P, PDBFile &F, TypeDatabase &IPI)
: C13DebugFragmentVisitor(F), P(P), IPI(IPI) {}
Error handleLines() override {
@@ -159,7 +160,7 @@ public:
if (auto EC = printFileName("FileName", L.Header->FileID))
return EC;
- if (auto EC = dumpTypeRecord("Function", L.Header->Inlinee))
+ if (auto EC = dumpTypeRecord("Function", IPI, L.Header->Inlinee))
return EC;
P.printNumber("SourceLine", L.Header->SourceLineNum);
if (IL.hasExtraFiles()) {
@@ -175,11 +176,11 @@ public:
}
private:
- Error dumpTypeRecord(StringRef Label, TypeIndex Index) {
- CompactTypeDumpVisitor CTDV(IPI, Index, &P);
+ Error dumpTypeRecord(StringRef Label, TypeDatabase &DB, TypeIndex Index) {
+ CompactTypeDumpVisitor CTDV(DB, Index, &P);
DictScope D(P, Label);
- if (IPI.contains(Index)) {
- CVType Type = IPI.getType(Index);
+ if (DB.contains(Index)) {
+ CVType &Type = DB.getTypeRecord(Index);
if (auto EC = codeview::visitTypeRecord(Type, CTDV))
return EC;
} else {
@@ -198,7 +199,7 @@ private:
}
ScopedPrinter &P;
- LazyRandomTypeCollection &IPI;
+ TypeDatabase &IPI;
};
}
@@ -608,19 +609,14 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) {
VerLabel = "IPI Version";
}
+ if (!DumpRecordBytes && !DumpRecords && !DumpTpiHash)
+ return Error::success();
+
auto Tpi = (StreamIdx == StreamTPI) ? File.getPDBTpiStream()
: File.getPDBIpiStream();
if (!Tpi)
return Tpi.takeError();
- auto ExpectedTypes = initializeTypeDatabase(StreamIdx);
- if (!ExpectedTypes)
- return ExpectedTypes.takeError();
- auto &Types = *ExpectedTypes;
-
- if (!DumpRecordBytes && !DumpRecords && !DumpTpiHash)
- return Error::success();
-
std::unique_ptr<DictScope> StreamScope;
std::unique_ptr<ListScope> RecordScope;
@@ -628,19 +624,25 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) {
P.printNumber(VerLabel, Tpi->getTpiVersion());
P.printNumber("Record count", Tpi->getNumTypeRecords());
+ Optional<TypeDatabase> &StreamDB = (StreamIdx == StreamTPI) ? TypeDB : ItemDB;
+
std::vector<std::unique_ptr<TypeVisitorCallbacks>> Visitors;
+ if (!StreamDB.hasValue()) {
+ StreamDB.emplace(Tpi->getNumTypeRecords());
+ Visitors.push_back(make_unique<TypeDatabaseVisitor>(*StreamDB));
+ }
// If we're in dump mode, add a dumper with the appropriate detail level.
if (DumpRecords) {
std::unique_ptr<TypeVisitorCallbacks> Dumper;
if (opts::raw::CompactRecords)
- Dumper = make_unique<CompactTypeDumpVisitor>(Types, &P);
+ Dumper = make_unique<CompactTypeDumpVisitor>(*StreamDB, &P);
else {
- assert(TpiTypes);
+ assert(TypeDB.hasValue());
- auto X = make_unique<TypeDumpVisitor>(*TpiTypes, &P, false);
+ auto X = make_unique<TypeDumpVisitor>(*TypeDB, &P, false);
if (StreamIdx == StreamIPI)
- X->setIpiTypes(*IpiTypes);
+ X->setItemDB(*ItemDB);
Dumper = std::move(X);
}
Visitors.push_back(std::move(Dumper));
@@ -658,17 +660,23 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) {
if (DumpRecords || DumpRecordBytes)
RecordScope = llvm::make_unique<ListScope>(P, "Records");
- Optional<TypeIndex> I = Types.getFirst();
- do {
+ bool HadError = false;
+
+ TypeIndex T(TypeIndex::FirstNonSimpleIndex);
+ for (auto Type : Tpi->types(&HadError)) {
std::unique_ptr<DictScope> OneRecordScope;
if ((DumpRecords || DumpRecordBytes) && !opts::raw::CompactRecords)
OneRecordScope = llvm::make_unique<DictScope>(P, "");
- auto T = Types.getType(*I);
- if (auto EC = codeview::visitTypeRecord(T, *I, Pipeline))
+ if (auto EC = codeview::visitTypeRecord(Type, Pipeline))
return EC;
- } while ((I = Types.getNext(*I)));
+
+ ++T;
+ }
+ if (HadError)
+ return make_error<RawError>(raw_error_code::corrupt_file,
+ "TPI stream contained corrupt record");
if (DumpTpiHash) {
DictScope DD(P, "Hash");
@@ -703,26 +711,35 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) {
return Error::success();
}
-Expected<codeview::LazyRandomTypeCollection &>
-LLVMOutputStyle::initializeTypeDatabase(uint32_t SN) {
- auto &TypeCollection = (SN == StreamTPI) ? TpiTypes : IpiTypes;
+Error LLVMOutputStyle::buildTypeDatabase(uint32_t SN) {
+ assert(SN == StreamIPI || SN == StreamTPI);
+
+ auto &DB = (SN == StreamIPI) ? ItemDB : TypeDB;
+
+ if (DB.hasValue())
+ return Error::success();
+
auto Tpi =
(SN == StreamTPI) ? File.getPDBTpiStream() : File.getPDBIpiStream();
+
if (!Tpi)
return Tpi.takeError();
- if (!TypeCollection) {
- // Initialize the type collection, even if we're not going to dump it. This
- // way if some other part of the dumper decides it wants to use some or all
- // of the records for whatever purposes, it can still access them lazily.
- auto &Types = Tpi->typeArray();
- uint32_t Count = Tpi->getNumTypeRecords();
- auto Offsets = Tpi->getTypeIndexOffsets();
- TypeCollection =
- llvm::make_unique<LazyRandomTypeCollection>(Types, Count, Offsets);
- }
+ DB.emplace(Tpi->getNumTypeRecords());
+
+ TypeDatabaseVisitor DBV(*DB);
+
+ auto HashValues = Tpi->getHashValues();
+ if (HashValues.empty())
+ return codeview::visitTypeStream(Tpi->typeArray(), DBV);
- return *TypeCollection;
+ TypeVisitorCallbackPipeline Pipeline;
+ Pipeline.addCallbackToPipeline(DBV);
+
+ TpiHashVerifier HashVerifier(HashValues, Tpi->getNumHashBuckets());
+ Pipeline.addCallbackToPipeline(HashVerifier);
+
+ return codeview::visitTypeStream(Tpi->typeArray(), Pipeline);
}
Error LLVMOutputStyle::dumpDbiStream() {
@@ -797,13 +814,11 @@ Error LLVMOutputStyle::dumpDbiStream() {
return EC;
if (ShouldDumpSymbols) {
- auto ExpectedTypes = initializeTypeDatabase(StreamTPI);
- if (!ExpectedTypes)
- return ExpectedTypes.takeError();
- auto &Types = *ExpectedTypes;
+ if (auto EC = buildTypeDatabase(StreamTPI))
+ return EC;
ListScope SS(P, "Symbols");
- codeview::CVSymbolDumper SD(P, Types, nullptr, false);
+ codeview::CVSymbolDumper SD(P, *TypeDB, nullptr, false);
bool HadError = false;
for (auto S : ModS.symbols(&HadError)) {
DictScope LL(P, "");
@@ -824,11 +839,10 @@ Error LLVMOutputStyle::dumpDbiStream() {
}
if (opts::raw::DumpLineInfo) {
ListScope SS(P, "LineInfo");
- auto ExpectedTypes = initializeTypeDatabase(StreamIPI);
- if (!ExpectedTypes)
- return ExpectedTypes.takeError();
- auto &IpiItems = *ExpectedTypes;
- C13RawVisitor V(P, File, IpiItems);
+ if (auto EC = buildTypeDatabase(StreamIPI))
+ return EC;
+
+ C13RawVisitor V(P, File, *ItemDB);
if (auto EC = codeview::visitModuleDebugFragments(
ModS.linesAndChecksums(), V))
return EC;
@@ -946,12 +960,10 @@ Error LLVMOutputStyle::dumpPublicsStream() {
P.printList("Section Offsets", Publics->getSectionOffsets(),
printSectionOffset);
ListScope L(P, "Symbols");
- auto ExpectedTypes = initializeTypeDatabase(StreamTPI);
- if (!ExpectedTypes)
- return ExpectedTypes.takeError();
- auto &Tpi = *ExpectedTypes;
+ if (auto EC = buildTypeDatabase(StreamTPI))
+ return EC;
- codeview::CVSymbolDumper SD(P, Tpi, nullptr, false);
+ codeview::CVSymbolDumper SD(P, *TypeDB, nullptr, false);
bool HadError = false;
for (auto S : Publics->getSymbols(&HadError)) {
DictScope DD(P, "");
OpenPOWER on IntegriCloud