diff options
-rw-r--r-- | llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp | 111 | ||||
-rw-r--r-- | llvm/tools/llvm-pdbdump/LLVMOutputStyle.h | 7 |
2 files changed, 77 insertions, 41 deletions
diff --git a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp index ec1325ff233..06d8ced128a 100644 --- a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp +++ b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.cpp @@ -609,11 +609,8 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) { VerLabel = "IPI Version"; } - bool IsSilentDatabaseBuild = !DumpRecordBytes && !DumpRecords && !DumpTpiHash; - if (IsSilentDatabaseBuild) { - outs().flush(); - errs() << "Building Type Information For " << Label << "\n"; - } + if (!DumpRecordBytes && !DumpRecords && !DumpTpiHash) + return Error::success(); auto Tpi = (StreamIdx == StreamTPI) ? File.getPDBTpiStream() : File.getPDBIpiStream(); @@ -623,38 +620,43 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) { std::unique_ptr<DictScope> StreamScope; std::unique_ptr<ListScope> RecordScope; - if (!IsSilentDatabaseBuild) { - StreamScope = llvm::make_unique<DictScope>(P, Label); - P.printNumber(VerLabel, Tpi->getTpiVersion()); - P.printNumber("Record count", Tpi->NumTypeRecords()); - } - - TypeDatabase &StreamDB = (StreamIdx == StreamTPI) ? TypeDB : ItemDB; + StreamScope = llvm::make_unique<DictScope>(P, Label); + P.printNumber(VerLabel, Tpi->getTpiVersion()); + P.printNumber("Record count", Tpi->NumTypeRecords()); - TypeDatabaseVisitor DBV(StreamDB); - CompactTypeDumpVisitor CTDV(StreamDB, &P); - TypeDumpVisitor TDV(TypeDB, &P, false); - if (StreamIdx == StreamIPI) - TDV.setItemDB(ItemDB); - RecordBytesVisitor RBV(P); - TypeDeserializer Deserializer; + Optional<TypeDatabase> &StreamDB = (StreamIdx == StreamTPI) ? TypeDB : ItemDB; - // We always need to deserialize and add it to the type database. This is - // true if even if we're not dumping anything, because we could need the - // type database for the purposes of dumping symbols. - TypeVisitorCallbackPipeline Pipeline; - Pipeline.addCallbackToPipeline(Deserializer); - Pipeline.addCallbackToPipeline(DBV); + std::vector<std::unique_ptr<TypeVisitorCallbacks>> Visitors; + Visitors.push_back(make_unique<TypeDeserializer>()); + if (!StreamDB.hasValue()) { + StreamDB.emplace(); + 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) - Pipeline.addCallbackToPipeline(CTDV); - else - Pipeline.addCallbackToPipeline(TDV); + Dumper = make_unique<CompactTypeDumpVisitor>(*StreamDB, &P); + else { + assert(TypeDB.hasValue()); + + auto X = make_unique<TypeDumpVisitor>(*TypeDB, &P, false); + if (StreamIdx == StreamIPI) + X->setItemDB(*ItemDB); + Dumper = std::move(X); + } + Visitors.push_back(std::move(Dumper)); } if (DumpRecordBytes) - Pipeline.addCallbackToPipeline(RBV); + Visitors.push_back(make_unique<RecordBytesVisitor>(P)); + + // We always need to deserialize and add it to the type database. This is + // true if even if we're not dumping anything, because we could need the + // type database for the purposes of dumping symbols. + TypeVisitorCallbackPipeline Pipeline; + for (const auto &V : Visitors) + Pipeline.addCallbackToPipeline(*V); CVTypeVisitor Visitor(Pipeline); @@ -700,19 +702,42 @@ Error LLVMOutputStyle::dumpTpiStream(uint32_t StreamIdx) { } } - if (!IsSilentDatabaseBuild) { - ListScope L(P, "TypeIndexOffsets"); - for (const auto &IO : Tpi->getTypeIndexOffsets()) { - P.printString(formatv("Index: {0:x}, Offset: {1:N}", IO.Type.getIndex(), - (uint32_t)IO.Offset) - .str()); - } + ListScope L(P, "TypeIndexOffsets"); + for (const auto &IO : Tpi->getTypeIndexOffsets()) { + P.printString(formatv("Index: {0:x}, Offset: {1:N}", IO.Type.getIndex(), + (uint32_t)IO.Offset) + .str()); } P.flush(); return Error::success(); } +Error LLVMOutputStyle::buildTypeDatabase(uint32_t SN) { + assert(SN == StreamIPI || SN == StreamTPI); + + auto &DB = (SN == StreamIPI) ? ItemDB : TypeDB; + + if (DB.hasValue()) + return Error::success(); + + DB.emplace(); + + TypeVisitorCallbackPipeline Pipeline; + TypeDeserializer Deserializer; + TypeDatabaseVisitor DBV(*DB); + Pipeline.addCallbackToPipeline(Deserializer); + Pipeline.addCallbackToPipeline(DBV); + + auto Tpi = + (SN == StreamTPI) ? File.getPDBTpiStream() : File.getPDBIpiStream(); + if (!Tpi) + return Tpi.takeError(); + + CVTypeVisitor Visitor(Pipeline); + return Visitor.visitTypeStream(Tpi->types(nullptr)); +} + Error LLVMOutputStyle::dumpDbiStream() { bool DumpModules = opts::raw::DumpModules || opts::raw::DumpModuleSyms || opts::raw::DumpModuleFiles || opts::raw::DumpLineInfo; @@ -785,8 +810,11 @@ Error LLVMOutputStyle::dumpDbiStream() { return EC; if (ShouldDumpSymbols) { + if (auto EC = buildTypeDatabase(StreamTPI)) + return EC; + ListScope SS(P, "Symbols"); - codeview::CVSymbolDumper SD(P, TypeDB, nullptr, false); + codeview::CVSymbolDumper SD(P, *TypeDB, nullptr, false); bool HadError = false; for (auto S : ModS.symbols(&HadError)) { DictScope LL(P, ""); @@ -807,8 +835,10 @@ Error LLVMOutputStyle::dumpDbiStream() { } if (opts::raw::DumpLineInfo) { ListScope SS(P, "LineInfo"); + if (auto EC = buildTypeDatabase(StreamIPI)) + return EC; - C13RawVisitor V(P, File, ItemDB); + C13RawVisitor V(P, File, *ItemDB); if (auto EC = codeview::visitModuleDebugFragments( ModS.linesAndChecksums(), V)) return EC; @@ -925,7 +955,10 @@ Error LLVMOutputStyle::dumpPublicsStream() { P.printList("Section Offsets", Publics->getSectionOffsets(), printSectionOffset); ListScope L(P, "Symbols"); - codeview::CVSymbolDumper SD(P, TypeDB, nullptr, false); + if (auto EC = buildTypeDatabase(StreamTPI)) + return EC; + + codeview::CVSymbolDumper SD(P, *TypeDB, nullptr, false); bool HadError = false; for (auto S : Publics->getSymbols(&HadError)) { DictScope DD(P, ""); diff --git a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.h b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.h index bfff3b8308d..b0e7e3406b3 100644 --- a/llvm/tools/llvm-pdbdump/LLVMOutputStyle.h +++ b/llvm/tools/llvm-pdbdump/LLVMOutputStyle.h @@ -12,6 +12,7 @@ #include "OutputStyle.h" +#include "llvm/ADT/Optional.h" #include "llvm/ADT/SmallVector.h" #include "llvm/DebugInfo/CodeView/TypeDatabase.h" #include "llvm/Support/ScopedPrinter.h" @@ -28,6 +29,8 @@ public: Error dump() override; private: + Error buildTypeDatabase(uint32_t SN); + Error dumpFileHeaders(); Error dumpStreamSummary(); Error dumpFreePageMap(); @@ -51,8 +54,8 @@ private: PDBFile &File; ScopedPrinter P; - codeview::TypeDatabase TypeDB; - codeview::TypeDatabase ItemDB; + Optional<codeview::TypeDatabase> TypeDB; + Optional<codeview::TypeDatabase> ItemDB; SmallVector<std::string, 32> StreamPurposes; }; } |