forked from OSchip/llvm-project
[llvm-pdbutil] Dump raw bytes of various DBI stream subsections.
llvm-svn: 306160
This commit is contained in:
parent
9e0d3878fb
commit
dd73968256
|
@ -63,6 +63,13 @@ public:
|
|||
|
||||
PDB_Machine getMachineType() const;
|
||||
|
||||
BinarySubstreamRef getSectionContributionData() const;
|
||||
BinarySubstreamRef getSecMapSubstreamData() const;
|
||||
BinarySubstreamRef getModiSubstreamData() const;
|
||||
BinarySubstreamRef getFileInfoSubstreamData() const;
|
||||
BinarySubstreamRef getTypeServerMapSubstreamData() const;
|
||||
BinarySubstreamRef getECSubstreamData() const;
|
||||
|
||||
/// If the given stream type is present, returns its stream index. If it is
|
||||
/// not present, returns InvalidStreamIndex.
|
||||
uint32_t getDebugStreamIndex(DbgHeaderType Type) const;
|
||||
|
@ -87,10 +94,12 @@ private:
|
|||
|
||||
PDBStringTable ECNames;
|
||||
|
||||
BinaryStreamRef SecContrSubstream;
|
||||
BinaryStreamRef SecMapSubstream;
|
||||
BinaryStreamRef TypeServerMapSubstream;
|
||||
BinaryStreamRef ECSubstream;
|
||||
BinarySubstreamRef SecContrSubstream;
|
||||
BinarySubstreamRef SecMapSubstream;
|
||||
BinarySubstreamRef ModiSubstream;
|
||||
BinarySubstreamRef FileInfoSubstream;
|
||||
BinarySubstreamRef TypeServerMapSubstream;
|
||||
BinarySubstreamRef ECSubstream;
|
||||
|
||||
DbiModuleList Modules;
|
||||
|
||||
|
|
|
@ -169,6 +169,9 @@ public:
|
|||
struct BinarySubstreamRef {
|
||||
uint32_t Offset; // Offset in the parent stream
|
||||
BinaryStreamRef StreamData; // Stream Data
|
||||
|
||||
uint32_t size() const { return StreamData.getLength(); }
|
||||
bool empty() const { return size() == 0; }
|
||||
};
|
||||
|
||||
class WritableBinaryStreamRef
|
||||
|
|
|
@ -99,29 +99,27 @@ Error DbiStream::reload() {
|
|||
return make_error<RawError>(raw_error_code::corrupt_file,
|
||||
"DBI type server substream not aligned.");
|
||||
|
||||
BinaryStreamRef ModInfoSubstream;
|
||||
BinaryStreamRef FileInfoSubstream;
|
||||
if (auto EC =
|
||||
Reader.readStreamRef(ModInfoSubstream, Header->ModiSubstreamSize))
|
||||
if (auto EC = Reader.readSubstream(ModiSubstream, Header->ModiSubstreamSize))
|
||||
return EC;
|
||||
|
||||
if (auto EC = Reader.readStreamRef(SecContrSubstream,
|
||||
if (auto EC = Reader.readSubstream(SecContrSubstream,
|
||||
Header->SecContrSubstreamSize))
|
||||
return EC;
|
||||
if (auto EC = Reader.readStreamRef(SecMapSubstream, Header->SectionMapSize))
|
||||
if (auto EC = Reader.readSubstream(SecMapSubstream, Header->SectionMapSize))
|
||||
return EC;
|
||||
if (auto EC = Reader.readStreamRef(FileInfoSubstream, Header->FileInfoSize))
|
||||
if (auto EC = Reader.readSubstream(FileInfoSubstream, Header->FileInfoSize))
|
||||
return EC;
|
||||
if (auto EC =
|
||||
Reader.readStreamRef(TypeServerMapSubstream, Header->TypeServerSize))
|
||||
Reader.readSubstream(TypeServerMapSubstream, Header->TypeServerSize))
|
||||
return EC;
|
||||
if (auto EC = Reader.readStreamRef(ECSubstream, Header->ECSubstreamSize))
|
||||
if (auto EC = Reader.readSubstream(ECSubstream, Header->ECSubstreamSize))
|
||||
return EC;
|
||||
if (auto EC = Reader.readArray(
|
||||
DbgStreams, Header->OptionalDbgHdrSize / sizeof(ulittle16_t)))
|
||||
return EC;
|
||||
|
||||
if (auto EC = Modules.initialize(ModInfoSubstream, FileInfoSubstream))
|
||||
if (auto EC = Modules.initialize(ModiSubstream.StreamData,
|
||||
FileInfoSubstream.StreamData))
|
||||
return EC;
|
||||
|
||||
if (auto EC = initializeSectionContributionData())
|
||||
|
@ -137,8 +135,8 @@ Error DbiStream::reload() {
|
|||
return make_error<RawError>(raw_error_code::corrupt_file,
|
||||
"Found unexpected bytes in DBI Stream.");
|
||||
|
||||
if (ECSubstream.getLength() > 0) {
|
||||
BinaryStreamReader ECReader(ECSubstream);
|
||||
if (!ECSubstream.empty()) {
|
||||
BinaryStreamReader ECReader(ECSubstream.StreamData);
|
||||
if (auto EC = ECNames.reload(ECReader))
|
||||
return EC;
|
||||
}
|
||||
|
@ -228,10 +226,10 @@ void DbiStream::visitSectionContributions(
|
|||
}
|
||||
|
||||
Error DbiStream::initializeSectionContributionData() {
|
||||
if (SecContrSubstream.getLength() == 0)
|
||||
if (SecContrSubstream.empty())
|
||||
return Error::success();
|
||||
|
||||
BinaryStreamReader SCReader(SecContrSubstream);
|
||||
BinaryStreamReader SCReader(SecContrSubstream.StreamData);
|
||||
if (auto EC = SCReader.readEnum(SectionContribVersion))
|
||||
return EC;
|
||||
|
||||
|
@ -302,11 +300,33 @@ Error DbiStream::initializeFpoRecords() {
|
|||
return Error::success();
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getSectionContributionData() const {
|
||||
return SecContrSubstream;
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getSecMapSubstreamData() const {
|
||||
return SecMapSubstream;
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getModiSubstreamData() const {
|
||||
return ModiSubstream;
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getFileInfoSubstreamData() const {
|
||||
return FileInfoSubstream;
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getTypeServerMapSubstreamData() const {
|
||||
return TypeServerMapSubstream;
|
||||
}
|
||||
|
||||
BinarySubstreamRef DbiStream::getECSubstreamData() const { return ECSubstream; }
|
||||
|
||||
Error DbiStream::initializeSectionMapData() {
|
||||
if (SecMapSubstream.getLength() == 0)
|
||||
if (SecMapSubstream.empty())
|
||||
return Error::success();
|
||||
|
||||
BinaryStreamReader SMReader(SecMapSubstream);
|
||||
BinaryStreamReader SMReader(SecMapSubstream.StreamData);
|
||||
const SecMapHeader *Header;
|
||||
if (auto EC = SMReader.readObject(Header))
|
||||
return EC;
|
||||
|
|
|
@ -0,0 +1,59 @@
|
|||
; RUN: llvm-pdbutil bytes -ec %p/Inputs/empty.pdb | FileCheck --check-prefix=EC %s
|
||||
; RUN: llvm-pdbutil bytes -files %p/Inputs/empty.pdb | FileCheck --check-prefix=FILES %s
|
||||
; RUN: llvm-pdbutil bytes -modi %p/Inputs/empty.pdb | FileCheck --check-prefix=MODI %s
|
||||
; RUN: llvm-pdbutil bytes -sc %p/Inputs/empty.pdb | FileCheck --check-prefix=SC %s
|
||||
; RUN: llvm-pdbutil bytes -sm %p/Inputs/empty.pdb | FileCheck --check-prefix=SM %s
|
||||
; RUN: llvm-pdbutil bytes -type-server %p/Inputs/empty.pdb | FileCheck --check-prefix=TYPE-SERVER %s
|
||||
|
||||
EC: Edit and Continue Data
|
||||
EC-NEXT: ============================================================
|
||||
EC-NEXT: Edit and Continue Data (
|
||||
EC-NEXT: E280: FEEFFEEF 01000000 31000000 00643A5C 7372635C 6C6C766D 5C746573 745C4465 |........1....d:\src\llvm\test\De|
|
||||
EC-NEXT: E2A0: 62756749 6E666F5C 5044425C 496E7075 74735C65 6D707479 2E706462 00020000 |bugInfo\PDB\Inputs\empty.pdb....|
|
||||
EC-NEXT: E2C0: 00010000 00000000 00010000 00 |.............|
|
||||
EC-NEXT: )
|
||||
|
||||
FILES: File Info
|
||||
FILES-NEXT: ============================================================
|
||||
FILES-NEXT: File Info (
|
||||
FILES-NEXT: E240: 02000100 00000100 01000000 00000000 643A5C73 72635C6C 6C766D5C 74657374 |................d:\src\llvm\test|
|
||||
FILES-NEXT: E260: 5C646562 7567696E 666F5C70 64625C69 6E707574 735C656D 7074792E 63707000 |\debuginfo\pdb\inputs\empty.cpp.|
|
||||
FILES-NEXT: )
|
||||
|
||||
MODI: Module Infos
|
||||
MODI-NEXT: ============================================================
|
||||
MODI-NEXT: Module Infos (
|
||||
MODI-NEXT: E040: 00000000 01000000 10000000 0A000000 20005060 00000000 347497D7 00000000 |................ .P`....4t......|
|
||||
MODI-NEXT: E060: 00000C00 D0000000 00000000 58000000 01000000 D035E900 00000000 00000000 |............X........5..........|
|
||||
MODI-NEXT: E080: 643A5C73 72635C6C 6C766D5C 74657374 5C446562 7567496E 666F5C50 44425C49 |d:\src\llvm\test\DebugInfo\PDB\I|
|
||||
MODI-NEXT: E0A0: 6E707574 735C656D 7074792E 6F626A00 643A5C73 72635C6C 6C766D5C 74657374 |nputs\empty.obj.d:\src\llvm\test|
|
||||
MODI-NEXT: E0C0: 5C446562 7567496E 666F5C50 44425C49 6E707574 735C656D 7074792E 6F626A00 |\DebugInfo\PDB\Inputs\empty.obj.|
|
||||
MODI-NEXT: E0E0: 00000000 01000000 00000000 0A000000 20000060 01000000 00000000 00000000 |................ ..`............|
|
||||
MODI-NEXT: E100: 00000E00 04020000 00000000 00000000 00000000 00000000 00000000 01000000 |................................|
|
||||
MODI-NEXT: E120: 2A204C69 6E6B6572 202A0000 |* Linker *..|
|
||||
MODI-NEXT: )
|
||||
|
||||
SC: Section Contributions
|
||||
SC-NEXT: ============================================================
|
||||
SC-NEXT: Section Contributions (
|
||||
SC-NEXT: E12C: 2DBA2EF1 01002511 00000000 0A000000 20000060 01000000 00000000 00000000 |-.....%......... ..`............|
|
||||
SC-NEXT: E14C: 01000000 10000000 0A000000 20005060 00000000 347497D7 00000000 02000000 |............ .P`....4t..........|
|
||||
SC-NEXT: E16C: 00000000 38000000 40000040 01000000 00000000 00000000 02000000 44010000 |....8...@..@................D...|
|
||||
SC-NEXT: E18C: 48000000 40003040 01000000 00000000 00000000 02000000 8C010000 14000000 |H...@.0@........................|
|
||||
SC-NEXT: E1AC: 40003040 01000000 00000000 00000000 03000000 00000000 04000000 800030C0 |@.0@..........................0.|
|
||||
SC-NEXT: E1CC: 00000000 00000000 00000000 |............|
|
||||
SC-NEXT: )
|
||||
|
||||
SM: Section Map
|
||||
SM-NEXT: ============================================================
|
||||
SM-NEXT: Section Map (
|
||||
SM-NEXT: E1D8: 05000500 0D010000 00000100 FFFFFFFF 00000000 1A100000 09010000 00000200 |................................|
|
||||
SM-NEXT: E1F8: FFFFFFFF 00000000 B2020000 0B010000 00000300 FFFFFFFF 00000000 04000000 |................................|
|
||||
SM-NEXT: E218: 09010000 00000400 FFFFFFFF 00000000 08000000 08020000 00000000 FFFFFFFF |................................|
|
||||
SM-NEXT: E238: 00000000 FFFFFFFF |........|
|
||||
SM-NEXT: )
|
||||
|
||||
TYPE-SERVER: Type Server Map
|
||||
TYPE-SERVER-NEXT: ============================================================
|
||||
TYPE-SERVER-NEXT: Type Server Map (
|
||||
TYPE-SERVER-NEXT: )
|
|
@ -13,6 +13,7 @@
|
|||
#include "llvm-pdbutil.h"
|
||||
|
||||
#include "llvm/DebugInfo/MSF/MappedBlockStream.h"
|
||||
#include "llvm/DebugInfo/PDB/Native/DbiStream.h"
|
||||
#include "llvm/DebugInfo/PDB/Native/InfoStream.h"
|
||||
#include "llvm/DebugInfo/PDB/Native/PDBFile.h"
|
||||
#include "llvm/DebugInfo/PDB/Native/RawError.h"
|
||||
|
@ -122,6 +123,37 @@ Error BytesOutputStyle::dump() {
|
|||
dumpNameMap();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::SectionContributions) {
|
||||
dumpSectionContributions();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::SectionMap) {
|
||||
dumpSectionMap();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::ModuleInfos) {
|
||||
dumpModuleInfos();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::FileInfo) {
|
||||
dumpFileInfo();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::TypeServerMap) {
|
||||
dumpTypeServerMap();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
if (opts::bytes::ECData) {
|
||||
dumpECData();
|
||||
P.NewLine();
|
||||
}
|
||||
|
||||
return Error::success();
|
||||
}
|
||||
|
||||
|
@ -155,6 +187,72 @@ void BytesOutputStyle::dumpBlockRanges(uint32_t Min, uint32_t Max) {
|
|||
}
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpSectionContributions() {
|
||||
printHeader(P, "Section Contributions");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getSectionContributionData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("Section Contributions", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpSectionMap() {
|
||||
printHeader(P, "Section Map");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getSecMapSubstreamData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("Section Map", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpModuleInfos() {
|
||||
printHeader(P, "Module Infos");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getModiSubstreamData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("Module Infos", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpFileInfo() {
|
||||
printHeader(P, "File Info");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getFileInfoSubstreamData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("File Info", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpTypeServerMap() {
|
||||
printHeader(P, "Type Server Map");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getTypeServerMapSubstreamData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("Type Server Map", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpECData() {
|
||||
printHeader(P, "Edit and Continue Data");
|
||||
|
||||
AutoIndent Indent(P);
|
||||
|
||||
auto &DbiS = Err(File.getPDBDbiStream());
|
||||
BinarySubstreamRef NS = DbiS.getECSubstreamData();
|
||||
auto Layout = File.getStreamLayout(StreamDBI);
|
||||
P.formatMsfStreamData("Edit and Continue Data", File, Layout, NS);
|
||||
}
|
||||
|
||||
void BytesOutputStyle::dumpByteRanges(uint32_t Min, uint32_t Max) {
|
||||
printHeader(P, "MSF Bytes");
|
||||
|
||||
|
|
|
@ -33,6 +33,13 @@ private:
|
|||
void dumpByteRanges(uint32_t Min, uint32_t Max);
|
||||
void dumpStreamBytes();
|
||||
|
||||
void dumpSectionContributions();
|
||||
void dumpSectionMap();
|
||||
void dumpModuleInfos();
|
||||
void dumpFileInfo();
|
||||
void dumpTypeServerMap();
|
||||
void dumpECData();
|
||||
|
||||
PDBFile &File;
|
||||
LinePrinter P;
|
||||
ExitOnError Err;
|
||||
|
|
|
@ -146,18 +146,19 @@ static std::vector<Run> computeBlockRuns(uint32_t BlockSize,
|
|||
ArrayRef<support::ulittle32_t> Blocks = Layout.Blocks;
|
||||
assert(!Blocks.empty());
|
||||
uint32_t StreamBytesRemaining = Layout.Length;
|
||||
Runs.emplace_back(Blocks[0]);
|
||||
uint32_t CurrentBlock = Blocks[0];
|
||||
Runs.emplace_back(CurrentBlock);
|
||||
while (!Blocks.empty()) {
|
||||
Run *CurrentRun = &Runs.back();
|
||||
uint32_t NextBlock = Blocks.front();
|
||||
if (NextBlock < CurrentRun->Block || (NextBlock - CurrentRun->Block > 1)) {
|
||||
if (NextBlock < CurrentBlock || (NextBlock - CurrentBlock > 1)) {
|
||||
Runs.emplace_back(NextBlock);
|
||||
CurrentRun = &Runs.back();
|
||||
}
|
||||
|
||||
uint32_t Used = std::min(BlockSize, StreamBytesRemaining);
|
||||
CurrentRun->ByteLen += Used;
|
||||
StreamBytesRemaining -= Used;
|
||||
CurrentBlock = NextBlock;
|
||||
Blocks = Blocks.drop_front();
|
||||
}
|
||||
return Runs;
|
||||
|
|
|
@ -267,27 +267,44 @@ cl::list<std::string> InputFilenames(cl::Positional,
|
|||
cl::OptionCategory FileOptions("Module & File Options");
|
||||
|
||||
namespace bytes {
|
||||
cl::OptionCategory MsfBytes("MSF File Options");
|
||||
cl::OptionCategory DbiBytes("Dbi Stream Options");
|
||||
cl::OptionCategory PdbBytes("PDB Stream Options");
|
||||
|
||||
llvm::Optional<NumberRange> DumpBlockRange;
|
||||
llvm::Optional<NumberRange> DumpByteRange;
|
||||
|
||||
cl::opt<std::string> DumpBlockRangeOpt(
|
||||
"block-range", cl::value_desc("start[-end]"),
|
||||
cl::desc("Dump binary data from specified range of blocks."),
|
||||
cl::sub(BytesSubcommand));
|
||||
cl::sub(BytesSubcommand), cl::cat(MsfBytes));
|
||||
|
||||
cl::opt<std::string>
|
||||
DumpByteRangeOpt("byte-range", cl::value_desc("start[-end]"),
|
||||
cl::desc("Dump binary data from specified range of bytes"),
|
||||
cl::sub(BytesSubcommand));
|
||||
cl::sub(BytesSubcommand), cl::cat(MsfBytes));
|
||||
|
||||
cl::list<std::string>
|
||||
DumpStreamData("stream-data", cl::CommaSeparated, cl::ZeroOrMore,
|
||||
cl::desc("Dump binary data from specified streams. Format "
|
||||
"is SN[:Start][@Size]"),
|
||||
cl::sub(BytesSubcommand));
|
||||
cl::sub(BytesSubcommand), cl::cat(MsfBytes));
|
||||
|
||||
cl::opt<bool> NameMap("name-map", cl::desc("Dump bytes of PDB Name Map"),
|
||||
cl::sub(BytesSubcommand));
|
||||
cl::sub(BytesSubcommand), cl::cat(PdbBytes));
|
||||
|
||||
cl::opt<bool> SectionContributions("sc", cl::desc("Dump section contributions"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
cl::opt<bool> SectionMap("sm", cl::desc("Dump section map"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
cl::opt<bool> ModuleInfos("modi", cl::desc("Dump module info"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
cl::opt<bool> FileInfo("files", cl::desc("Dump source file info"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
cl::opt<bool> TypeServerMap("type-server", cl::desc("Dump type server map"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
cl::opt<bool> ECData("ec", cl::desc("Dump edit and continue map"),
|
||||
cl::sub(BytesSubcommand), cl::cat(DbiBytes));
|
||||
|
||||
cl::list<std::string> InputFilenames(cl::Positional,
|
||||
cl::desc("<input PDB files>"),
|
||||
|
|
|
@ -102,6 +102,14 @@ extern llvm::Optional<NumberRange> DumpBlockRange;
|
|||
extern llvm::Optional<NumberRange> DumpByteRange;
|
||||
extern llvm::cl::list<std::string> DumpStreamData;
|
||||
extern llvm::cl::opt<bool> NameMap;
|
||||
|
||||
extern llvm::cl::opt<bool> SectionContributions;
|
||||
extern llvm::cl::opt<bool> SectionMap;
|
||||
extern llvm::cl::opt<bool> ModuleInfos;
|
||||
extern llvm::cl::opt<bool> FileInfo;
|
||||
extern llvm::cl::opt<bool> TypeServerMap;
|
||||
extern llvm::cl::opt<bool> ECData;
|
||||
|
||||
} // namespace bytes
|
||||
|
||||
namespace dump {
|
||||
|
|
Loading…
Reference in New Issue