1aaad5744SZachary Turner //===-- SymbolDumper.cpp - CodeView symbol info dumper ----------*- C++ -*-===//
2aaad5744SZachary Turner //
3aaad5744SZachary Turner //                     The LLVM Compiler Infrastructure
4aaad5744SZachary Turner //
5aaad5744SZachary Turner // This file is distributed under the University of Illinois Open Source
6aaad5744SZachary Turner // License. See LICENSE.TXT for details.
7aaad5744SZachary Turner //
8aaad5744SZachary Turner //===----------------------------------------------------------------------===//
9aaad5744SZachary Turner 
10aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolDumper.h"
11aaad5744SZachary Turner #include "llvm/ADT/DenseMap.h"
12aaad5744SZachary Turner #include "llvm/ADT/SmallString.h"
13aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/CVSymbolVisitor.h"
14a9054dddSZachary Turner #include "llvm/DebugInfo/CodeView/CVTypeDumper.h"
1593839cb4SZachary Turner #include "llvm/DebugInfo/CodeView/EnumTables.h"
160d840744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolDeserializer.h"
17aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolDumpDelegate.h"
18aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolRecord.h"
190d840744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolVisitorCallbackPipeline.h"
200d840744SZachary Turner #include "llvm/DebugInfo/CodeView/SymbolVisitorCallbacks.h"
21aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/TypeIndex.h"
220d840744SZachary Turner #include "llvm/Support/Error.h"
23aaad5744SZachary Turner #include "llvm/Support/ScopedPrinter.h"
24aaad5744SZachary Turner 
25aaad5744SZachary Turner #include <system_error>
26aaad5744SZachary Turner 
27aaad5744SZachary Turner using namespace llvm;
28aaad5744SZachary Turner using namespace llvm::codeview;
29aaad5744SZachary Turner 
30aaad5744SZachary Turner namespace {
31aaad5744SZachary Turner /// Use this private dumper implementation to keep implementation details about
32aaad5744SZachary Turner /// the visitor out of SymbolDumper.h.
330d840744SZachary Turner class CVSymbolDumperImpl : public SymbolVisitorCallbacks {
34aaad5744SZachary Turner public:
35629cb7d8SZachary Turner   CVSymbolDumperImpl(TypeDatabase &TypeDB, SymbolDumpDelegate *ObjDelegate,
363e78e2d4SZachary Turner                      ScopedPrinter &W, bool PrintRecordBytes)
37629cb7d8SZachary Turner       : TypeDB(TypeDB), ObjDelegate(ObjDelegate), W(W),
380d840744SZachary Turner         PrintRecordBytes(PrintRecordBytes), InFunctionScope(false) {}
39aaad5744SZachary Turner 
40aaad5744SZachary Turner /// CVSymbolVisitor overrides.
41aaad5744SZachary Turner #define SYMBOL_RECORD(EnumName, EnumVal, Name)                                 \
420d840744SZachary Turner   Error visitKnownRecord(CVSymbol &CVR, Name &Record) override;
43aaad5744SZachary Turner #define SYMBOL_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName)
44aaad5744SZachary Turner #include "llvm/DebugInfo/CodeView/CVSymbolTypes.def"
45aaad5744SZachary Turner 
460d840744SZachary Turner   Error visitSymbolBegin(CVSymbol &Record) override;
470d840744SZachary Turner   Error visitSymbolEnd(CVSymbol &Record) override;
480d840744SZachary Turner   Error visitUnknownSymbol(CVSymbol &Record) override;
49aaad5744SZachary Turner 
50aaad5744SZachary Turner private:
51aaad5744SZachary Turner   void printLocalVariableAddrRange(const LocalVariableAddrRange &Range,
52aaad5744SZachary Turner                                    uint32_t RelocationOffset);
53aaad5744SZachary Turner   void printLocalVariableAddrGap(ArrayRef<LocalVariableAddrGap> Gaps);
54629cb7d8SZachary Turner   void printTypeIndex(StringRef FieldName, TypeIndex TI);
55aaad5744SZachary Turner 
56629cb7d8SZachary Turner   TypeDatabase &TypeDB;
57aaad5744SZachary Turner   SymbolDumpDelegate *ObjDelegate;
58aaad5744SZachary Turner   ScopedPrinter &W;
59aaad5744SZachary Turner 
60aaad5744SZachary Turner   bool PrintRecordBytes;
61aaad5744SZachary Turner   bool InFunctionScope;
62aaad5744SZachary Turner };
63aaad5744SZachary Turner }
64aaad5744SZachary Turner 
65aaad5744SZachary Turner void CVSymbolDumperImpl::printLocalVariableAddrRange(
66aaad5744SZachary Turner     const LocalVariableAddrRange &Range, uint32_t RelocationOffset) {
67aaad5744SZachary Turner   DictScope S(W, "LocalVariableAddrRange");
68aaad5744SZachary Turner   if (ObjDelegate)
69aaad5744SZachary Turner     ObjDelegate->printRelocatedField("OffsetStart", RelocationOffset,
70aaad5744SZachary Turner                                      Range.OffsetStart);
71aaad5744SZachary Turner   W.printHex("ISectStart", Range.ISectStart);
72aaad5744SZachary Turner   W.printHex("Range", Range.Range);
73aaad5744SZachary Turner }
74aaad5744SZachary Turner 
75aaad5744SZachary Turner void CVSymbolDumperImpl::printLocalVariableAddrGap(
76aaad5744SZachary Turner     ArrayRef<LocalVariableAddrGap> Gaps) {
77aaad5744SZachary Turner   for (auto &Gap : Gaps) {
78aaad5744SZachary Turner     ListScope S(W, "LocalVariableAddrGap");
79aaad5744SZachary Turner     W.printHex("GapStartOffset", Gap.GapStartOffset);
80aaad5744SZachary Turner     W.printHex("Range", Gap.Range);
81aaad5744SZachary Turner   }
82aaad5744SZachary Turner }
83aaad5744SZachary Turner 
84629cb7d8SZachary Turner void CVSymbolDumperImpl::printTypeIndex(StringRef FieldName, TypeIndex TI) {
85629cb7d8SZachary Turner   CVTypeDumper::printTypeIndex(W, FieldName, TI, TypeDB);
86629cb7d8SZachary Turner }
87629cb7d8SZachary Turner 
880d840744SZachary Turner Error CVSymbolDumperImpl::visitSymbolBegin(CVSymbol &CVR) {
890d840744SZachary Turner   return Error::success();
90aaad5744SZachary Turner }
91aaad5744SZachary Turner 
920d840744SZachary Turner Error CVSymbolDumperImpl::visitSymbolEnd(CVSymbol &CVR) {
930d840744SZachary Turner   if (PrintRecordBytes && ObjDelegate)
940d840744SZachary Turner     ObjDelegate->printBinaryBlockWithRelocs("SymData", CVR.content());
950d840744SZachary Turner   return Error::success();
960d840744SZachary Turner }
970d840744SZachary Turner 
980d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, BlockSym &Block) {
99aaad5744SZachary Turner   DictScope S(W, "BlockStart");
100aaad5744SZachary Turner 
101aaad5744SZachary Turner   StringRef LinkageName;
10246225b19SZachary Turner   W.printHex("PtrParent", Block.Parent);
10346225b19SZachary Turner   W.printHex("PtrEnd", Block.End);
10446225b19SZachary Turner   W.printHex("CodeSize", Block.CodeSize);
105aaad5744SZachary Turner   if (ObjDelegate) {
106aaad5744SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset", Block.getRelocationOffset(),
10746225b19SZachary Turner                                      Block.CodeOffset, &LinkageName);
108aaad5744SZachary Turner   }
10946225b19SZachary Turner   W.printHex("Segment", Block.Segment);
110aaad5744SZachary Turner   W.printString("BlockName", Block.Name);
111aaad5744SZachary Turner   W.printString("LinkageName", LinkageName);
1120d840744SZachary Turner   return Error::success();
113aaad5744SZachary Turner }
114aaad5744SZachary Turner 
1150d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, Thunk32Sym &Thunk) {
1164caa1bf0SZachary Turner   DictScope S(W, "Thunk32");
11746225b19SZachary Turner   W.printNumber("Parent", Thunk.Parent);
11846225b19SZachary Turner   W.printNumber("End", Thunk.End);
11946225b19SZachary Turner   W.printNumber("Next", Thunk.Next);
12046225b19SZachary Turner   W.printNumber("Off", Thunk.Offset);
12146225b19SZachary Turner   W.printNumber("Seg", Thunk.Segment);
12246225b19SZachary Turner   W.printNumber("Len", Thunk.Length);
12346225b19SZachary Turner   W.printEnum("Ordinal", uint8_t(Thunk.Thunk), getThunkOrdinalNames());
1240d840744SZachary Turner   return Error::success();
1254caa1bf0SZachary Turner }
1264caa1bf0SZachary Turner 
1270d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
1284caa1bf0SZachary Turner                                            TrampolineSym &Tramp) {
1294caa1bf0SZachary Turner   DictScope S(W, "Trampoline");
13046225b19SZachary Turner   W.printEnum("Type", uint16_t(Tramp.Type), getTrampolineNames());
13146225b19SZachary Turner   W.printNumber("Size", Tramp.Size);
13246225b19SZachary Turner   W.printNumber("ThunkOff", Tramp.ThunkOffset);
13346225b19SZachary Turner   W.printNumber("TargetOff", Tramp.TargetOffset);
13446225b19SZachary Turner   W.printNumber("ThunkSection", Tramp.ThunkSection);
13546225b19SZachary Turner   W.printNumber("TargetSection", Tramp.TargetSection);
1360d840744SZachary Turner   return Error::success();
1374caa1bf0SZachary Turner }
1384caa1bf0SZachary Turner 
1390d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, SectionSym &Section) {
1404caa1bf0SZachary Turner   DictScope S(W, "Section");
14146225b19SZachary Turner   W.printNumber("SectionNumber", Section.SectionNumber);
14246225b19SZachary Turner   W.printNumber("Alignment", Section.Alignment);
14346225b19SZachary Turner   W.printNumber("Rva", Section.Rva);
14446225b19SZachary Turner   W.printNumber("Length", Section.Length);
14546225b19SZachary Turner   W.printFlags("Characteristics", Section.Characteristics,
14693839cb4SZachary Turner                getImageSectionCharacteristicNames(),
14793839cb4SZachary Turner                COFF::SectionCharacteristics(0x00F00000));
14893839cb4SZachary Turner 
1494caa1bf0SZachary Turner   W.printString("Name", Section.Name);
1500d840744SZachary Turner   return Error::success();
1514caa1bf0SZachary Turner }
1524caa1bf0SZachary Turner 
1530d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
1544caa1bf0SZachary Turner                                            CoffGroupSym &CoffGroup) {
1554caa1bf0SZachary Turner   DictScope S(W, "COFF Group");
15646225b19SZachary Turner   W.printNumber("Size", CoffGroup.Size);
15746225b19SZachary Turner   W.printFlags("Characteristics", CoffGroup.Characteristics,
15893839cb4SZachary Turner                getImageSectionCharacteristicNames(),
15993839cb4SZachary Turner                COFF::SectionCharacteristics(0x00F00000));
16046225b19SZachary Turner   W.printNumber("Offset", CoffGroup.Offset);
16146225b19SZachary Turner   W.printNumber("Segment", CoffGroup.Segment);
1624caa1bf0SZachary Turner   W.printString("Name", CoffGroup.Name);
1630d840744SZachary Turner   return Error::success();
1644caa1bf0SZachary Turner }
1654caa1bf0SZachary Turner 
1660d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
167aaad5744SZachary Turner                                            BPRelativeSym &BPRel) {
168aaad5744SZachary Turner   DictScope S(W, "BPRelativeSym");
169aaad5744SZachary Turner 
17046225b19SZachary Turner   W.printNumber("Offset", BPRel.Offset);
171629cb7d8SZachary Turner   printTypeIndex("Type", BPRel.Type);
172aaad5744SZachary Turner   W.printString("VarName", BPRel.Name);
1730d840744SZachary Turner   return Error::success();
174aaad5744SZachary Turner }
175aaad5744SZachary Turner 
1760d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
177aaad5744SZachary Turner                                            BuildInfoSym &BuildInfo) {
178aaad5744SZachary Turner   DictScope S(W, "BuildInfo");
179aaad5744SZachary Turner 
18046225b19SZachary Turner   W.printNumber("BuildId", BuildInfo.BuildId);
1810d840744SZachary Turner   return Error::success();
182aaad5744SZachary Turner }
183aaad5744SZachary Turner 
1840d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
185aaad5744SZachary Turner                                            CallSiteInfoSym &CallSiteInfo) {
186aaad5744SZachary Turner   DictScope S(W, "CallSiteInfo");
187aaad5744SZachary Turner 
188aaad5744SZachary Turner   StringRef LinkageName;
189aaad5744SZachary Turner   if (ObjDelegate) {
19046225b19SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset",
19146225b19SZachary Turner                                      CallSiteInfo.getRelocationOffset(),
19246225b19SZachary Turner                                      CallSiteInfo.CodeOffset, &LinkageName);
193aaad5744SZachary Turner   }
19446225b19SZachary Turner   W.printHex("Segment", CallSiteInfo.Segment);
195629cb7d8SZachary Turner   printTypeIndex("Type", CallSiteInfo.Type);
196aaad5744SZachary Turner   if (!LinkageName.empty())
197aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
1980d840744SZachary Turner   return Error::success();
199aaad5744SZachary Turner }
200aaad5744SZachary Turner 
2010d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
2024caa1bf0SZachary Turner                                            EnvBlockSym &EnvBlock) {
2034caa1bf0SZachary Turner   DictScope S(W, "EnvBlock");
2044caa1bf0SZachary Turner 
2054caa1bf0SZachary Turner   ListScope L(W, "Entries");
2064caa1bf0SZachary Turner   for (auto Entry : EnvBlock.Fields) {
2074caa1bf0SZachary Turner     W.printString(Entry);
2084caa1bf0SZachary Turner   }
2090d840744SZachary Turner   return Error::success();
2104caa1bf0SZachary Turner }
2114caa1bf0SZachary Turner 
2120d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
2134caa1bf0SZachary Turner                                            FileStaticSym &FileStatic) {
2144caa1bf0SZachary Turner   DictScope S(W, "FileStatic");
21546225b19SZachary Turner   W.printNumber("Index", FileStatic.Index);
21646225b19SZachary Turner   W.printNumber("ModFilenameOffset", FileStatic.ModFilenameOffset);
21746225b19SZachary Turner   W.printFlags("Flags", uint16_t(FileStatic.Flags), getLocalFlagNames());
2184caa1bf0SZachary Turner   W.printString("Name", FileStatic.Name);
2190d840744SZachary Turner   return Error::success();
2204caa1bf0SZachary Turner }
2214caa1bf0SZachary Turner 
2220d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, ExportSym &Export) {
2239f054d42SZachary Turner   DictScope S(W, "Export");
22446225b19SZachary Turner   W.printNumber("Ordinal", Export.Ordinal);
22546225b19SZachary Turner   W.printFlags("Flags", uint16_t(Export.Flags), getExportSymFlagNames());
2269f054d42SZachary Turner   W.printString("Name", Export.Name);
2270d840744SZachary Turner   return Error::success();
2289f054d42SZachary Turner }
2299f054d42SZachary Turner 
2300d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
2314caa1bf0SZachary Turner                                            Compile2Sym &Compile2) {
2324caa1bf0SZachary Turner   DictScope S(W, "CompilerFlags2");
2334caa1bf0SZachary Turner 
23446225b19SZachary Turner   W.printEnum("Language", Compile2.getLanguage(), getSourceLanguageNames());
23546225b19SZachary Turner   W.printFlags("Flags", Compile2.getFlags(), getCompileSym2FlagNames());
23646225b19SZachary Turner   W.printEnum("Machine", unsigned(Compile2.Machine), getCPUTypeNames());
2374caa1bf0SZachary Turner   std::string FrontendVersion;
2384caa1bf0SZachary Turner   {
2394caa1bf0SZachary Turner     raw_string_ostream Out(FrontendVersion);
24046225b19SZachary Turner     Out << Compile2.VersionFrontendMajor << '.' << Compile2.VersionFrontendMinor
24146225b19SZachary Turner         << '.' << Compile2.VersionFrontendBuild;
2424caa1bf0SZachary Turner   }
2434caa1bf0SZachary Turner   std::string BackendVersion;
2444caa1bf0SZachary Turner   {
2454caa1bf0SZachary Turner     raw_string_ostream Out(BackendVersion);
24646225b19SZachary Turner     Out << Compile2.VersionBackendMajor << '.' << Compile2.VersionBackendMinor
24746225b19SZachary Turner         << '.' << Compile2.VersionBackendBuild;
2484caa1bf0SZachary Turner   }
2494caa1bf0SZachary Turner   W.printString("FrontendVersion", FrontendVersion);
2504caa1bf0SZachary Turner   W.printString("BackendVersion", BackendVersion);
2514caa1bf0SZachary Turner   W.printString("VersionName", Compile2.Version);
2520d840744SZachary Turner   return Error::success();
2534caa1bf0SZachary Turner }
2544caa1bf0SZachary Turner 
2550d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
256aaad5744SZachary Turner                                            Compile3Sym &Compile3) {
2574caa1bf0SZachary Turner   DictScope S(W, "CompilerFlags3");
258aaad5744SZachary Turner 
25946225b19SZachary Turner   W.printEnum("Language", Compile3.getLanguage(), getSourceLanguageNames());
26046225b19SZachary Turner   W.printFlags("Flags", Compile3.getFlags(), getCompileSym3FlagNames());
26146225b19SZachary Turner   W.printEnum("Machine", unsigned(Compile3.Machine), getCPUTypeNames());
262aaad5744SZachary Turner   std::string FrontendVersion;
263aaad5744SZachary Turner   {
264aaad5744SZachary Turner     raw_string_ostream Out(FrontendVersion);
26546225b19SZachary Turner     Out << Compile3.VersionFrontendMajor << '.' << Compile3.VersionFrontendMinor
26646225b19SZachary Turner         << '.' << Compile3.VersionFrontendBuild << '.'
26746225b19SZachary Turner         << Compile3.VersionFrontendQFE;
268aaad5744SZachary Turner   }
269aaad5744SZachary Turner   std::string BackendVersion;
270aaad5744SZachary Turner   {
271aaad5744SZachary Turner     raw_string_ostream Out(BackendVersion);
27246225b19SZachary Turner     Out << Compile3.VersionBackendMajor << '.' << Compile3.VersionBackendMinor
27346225b19SZachary Turner         << '.' << Compile3.VersionBackendBuild << '.'
27446225b19SZachary Turner         << Compile3.VersionBackendQFE;
275aaad5744SZachary Turner   }
276aaad5744SZachary Turner   W.printString("FrontendVersion", FrontendVersion);
277aaad5744SZachary Turner   W.printString("BackendVersion", BackendVersion);
278aaad5744SZachary Turner   W.printString("VersionName", Compile3.Version);
2790d840744SZachary Turner   return Error::success();
280aaad5744SZachary Turner }
281aaad5744SZachary Turner 
2820d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
283aaad5744SZachary Turner                                            ConstantSym &Constant) {
284aaad5744SZachary Turner   DictScope S(W, "Constant");
285aaad5744SZachary Turner 
286629cb7d8SZachary Turner   printTypeIndex("Type", Constant.Type);
287aaad5744SZachary Turner   W.printNumber("Value", Constant.Value);
288aaad5744SZachary Turner   W.printString("Name", Constant.Name);
2890d840744SZachary Turner   return Error::success();
290aaad5744SZachary Turner }
291aaad5744SZachary Turner 
2920d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, DataSym &Data) {
293aaad5744SZachary Turner   DictScope S(W, "DataSym");
294aaad5744SZachary Turner 
2950d840744SZachary Turner   W.printEnum("Kind", uint16_t(CVR.kind()), getSymbolTypeNames());
296aaad5744SZachary Turner   StringRef LinkageName;
297aaad5744SZachary Turner   if (ObjDelegate) {
298aaad5744SZachary Turner     ObjDelegate->printRelocatedField("DataOffset", Data.getRelocationOffset(),
29946225b19SZachary Turner                                      Data.DataOffset, &LinkageName);
300aaad5744SZachary Turner   }
301629cb7d8SZachary Turner   printTypeIndex("Type", Data.Type);
302aaad5744SZachary Turner   W.printString("DisplayName", Data.Name);
303aaad5744SZachary Turner   if (!LinkageName.empty())
304aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
3050d840744SZachary Turner   return Error::success();
306aaad5744SZachary Turner }
307aaad5744SZachary Turner 
3080d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3090d840744SZachary Turner     CVSymbol &CVR,
310aaad5744SZachary Turner     DefRangeFramePointerRelFullScopeSym &DefRangeFramePointerRelFullScope) {
311aaad5744SZachary Turner   DictScope S(W, "DefRangeFramePointerRelFullScope");
31246225b19SZachary Turner   W.printNumber("Offset", DefRangeFramePointerRelFullScope.Offset);
3130d840744SZachary Turner   return Error::success();
314aaad5744SZachary Turner }
315aaad5744SZachary Turner 
3160d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3170d840744SZachary Turner     CVSymbol &CVR, DefRangeFramePointerRelSym &DefRangeFramePointerRel) {
318aaad5744SZachary Turner   DictScope S(W, "DefRangeFramePointerRel");
319aaad5744SZachary Turner 
32046225b19SZachary Turner   W.printNumber("Offset", DefRangeFramePointerRel.Offset);
32146225b19SZachary Turner   printLocalVariableAddrRange(DefRangeFramePointerRel.Range,
322aaad5744SZachary Turner                               DefRangeFramePointerRel.getRelocationOffset());
323aaad5744SZachary Turner   printLocalVariableAddrGap(DefRangeFramePointerRel.Gaps);
3240d840744SZachary Turner   return Error::success();
325aaad5744SZachary Turner }
326aaad5744SZachary Turner 
3270d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3280d840744SZachary Turner     CVSymbol &CVR, DefRangeRegisterRelSym &DefRangeRegisterRel) {
329aaad5744SZachary Turner   DictScope S(W, "DefRangeRegisterRel");
330aaad5744SZachary Turner 
33146225b19SZachary Turner   W.printNumber("BaseRegister", DefRangeRegisterRel.Hdr.Register);
332aaad5744SZachary Turner   W.printBoolean("HasSpilledUDTMember",
333aaad5744SZachary Turner                  DefRangeRegisterRel.hasSpilledUDTMember());
334aaad5744SZachary Turner   W.printNumber("OffsetInParent", DefRangeRegisterRel.offsetInParent());
33546225b19SZachary Turner   W.printNumber("BasePointerOffset", DefRangeRegisterRel.Hdr.BasePointerOffset);
33646225b19SZachary Turner   printLocalVariableAddrRange(DefRangeRegisterRel.Range,
337aaad5744SZachary Turner                               DefRangeRegisterRel.getRelocationOffset());
338aaad5744SZachary Turner   printLocalVariableAddrGap(DefRangeRegisterRel.Gaps);
3390d840744SZachary Turner   return Error::success();
340aaad5744SZachary Turner }
341aaad5744SZachary Turner 
3420d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3430d840744SZachary Turner     CVSymbol &CVR, DefRangeRegisterSym &DefRangeRegister) {
344aaad5744SZachary Turner   DictScope S(W, "DefRangeRegister");
345aaad5744SZachary Turner 
34646225b19SZachary Turner   W.printNumber("Register", DefRangeRegister.Hdr.Register);
34746225b19SZachary Turner   W.printNumber("MayHaveNoName", DefRangeRegister.Hdr.MayHaveNoName);
34846225b19SZachary Turner   printLocalVariableAddrRange(DefRangeRegister.Range,
349aaad5744SZachary Turner                               DefRangeRegister.getRelocationOffset());
350aaad5744SZachary Turner   printLocalVariableAddrGap(DefRangeRegister.Gaps);
3510d840744SZachary Turner   return Error::success();
352aaad5744SZachary Turner }
353aaad5744SZachary Turner 
3540d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3550d840744SZachary Turner     CVSymbol &CVR, DefRangeSubfieldRegisterSym &DefRangeSubfieldRegister) {
356aaad5744SZachary Turner   DictScope S(W, "DefRangeSubfieldRegister");
357aaad5744SZachary Turner 
35846225b19SZachary Turner   W.printNumber("Register", DefRangeSubfieldRegister.Hdr.Register);
35946225b19SZachary Turner   W.printNumber("MayHaveNoName", DefRangeSubfieldRegister.Hdr.MayHaveNoName);
36046225b19SZachary Turner   W.printNumber("OffsetInParent", DefRangeSubfieldRegister.Hdr.OffsetInParent);
36146225b19SZachary Turner   printLocalVariableAddrRange(DefRangeSubfieldRegister.Range,
362aaad5744SZachary Turner                               DefRangeSubfieldRegister.getRelocationOffset());
363aaad5744SZachary Turner   printLocalVariableAddrGap(DefRangeSubfieldRegister.Gaps);
3640d840744SZachary Turner   return Error::success();
365aaad5744SZachary Turner }
366aaad5744SZachary Turner 
3670d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
3680d840744SZachary Turner     CVSymbol &CVR, DefRangeSubfieldSym &DefRangeSubfield) {
369aaad5744SZachary Turner   DictScope S(W, "DefRangeSubfield");
370aaad5744SZachary Turner 
371aaad5744SZachary Turner   if (ObjDelegate) {
372aaad5744SZachary Turner     StringRef StringTable = ObjDelegate->getStringTable();
37346225b19SZachary Turner     auto ProgramStringTableOffset = DefRangeSubfield.Program;
374c6cb2ec3SDavid Majnemer     if (ProgramStringTableOffset >= StringTable.size())
3750d840744SZachary Turner       return llvm::make_error<CodeViewError>(
3760d840744SZachary Turner           "String table offset outside of bounds of String Table!");
377c6cb2ec3SDavid Majnemer     StringRef Program =
378c6cb2ec3SDavid Majnemer         StringTable.drop_front(ProgramStringTableOffset).split('\0').first;
379c6cb2ec3SDavid Majnemer     W.printString("Program", Program);
380aaad5744SZachary Turner   }
38146225b19SZachary Turner   W.printNumber("OffsetInParent", DefRangeSubfield.OffsetInParent);
38246225b19SZachary Turner   printLocalVariableAddrRange(DefRangeSubfield.Range,
383aaad5744SZachary Turner                               DefRangeSubfield.getRelocationOffset());
384aaad5744SZachary Turner   printLocalVariableAddrGap(DefRangeSubfield.Gaps);
3850d840744SZachary Turner   return Error::success();
386aaad5744SZachary Turner }
387aaad5744SZachary Turner 
3880d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
389aaad5744SZachary Turner                                            DefRangeSym &DefRange) {
390aaad5744SZachary Turner   DictScope S(W, "DefRange");
391aaad5744SZachary Turner 
392aaad5744SZachary Turner   if (ObjDelegate) {
393aaad5744SZachary Turner     StringRef StringTable = ObjDelegate->getStringTable();
39446225b19SZachary Turner     auto ProgramStringTableOffset = DefRange.Program;
395b343310bSDavid Majnemer     if (ProgramStringTableOffset >= StringTable.size())
3960d840744SZachary Turner       return llvm::make_error<CodeViewError>(
3970d840744SZachary Turner           "String table offset outside of bounds of String Table!");
398b343310bSDavid Majnemer     StringRef Program =
399b343310bSDavid Majnemer         StringTable.drop_front(ProgramStringTableOffset).split('\0').first;
400b343310bSDavid Majnemer     W.printString("Program", Program);
401aaad5744SZachary Turner   }
40246225b19SZachary Turner   printLocalVariableAddrRange(DefRange.Range, DefRange.getRelocationOffset());
403aaad5744SZachary Turner   printLocalVariableAddrGap(DefRange.Gaps);
4040d840744SZachary Turner   return Error::success();
405aaad5744SZachary Turner }
406aaad5744SZachary Turner 
4070d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
408aaad5744SZachary Turner                                            FrameCookieSym &FrameCookie) {
409aaad5744SZachary Turner   DictScope S(W, "FrameCookie");
410aaad5744SZachary Turner 
411aaad5744SZachary Turner   StringRef LinkageName;
412aaad5744SZachary Turner   if (ObjDelegate) {
41346225b19SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset",
41446225b19SZachary Turner                                      FrameCookie.getRelocationOffset(),
41546225b19SZachary Turner                                      FrameCookie.CodeOffset, &LinkageName);
416aaad5744SZachary Turner   }
41746225b19SZachary Turner   W.printHex("Register", FrameCookie.Register);
41846225b19SZachary Turner   W.printEnum("CookieKind", uint16_t(FrameCookie.CookieKind),
41993839cb4SZachary Turner               getFrameCookieKindNames());
42046225b19SZachary Turner   W.printHex("Flags", FrameCookie.Flags);
4210d840744SZachary Turner   return Error::success();
422aaad5744SZachary Turner }
423aaad5744SZachary Turner 
4240d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
425aaad5744SZachary Turner                                            FrameProcSym &FrameProc) {
426aaad5744SZachary Turner   DictScope S(W, "FrameProc");
427aaad5744SZachary Turner 
42846225b19SZachary Turner   W.printHex("TotalFrameBytes", FrameProc.TotalFrameBytes);
42946225b19SZachary Turner   W.printHex("PaddingFrameBytes", FrameProc.PaddingFrameBytes);
43046225b19SZachary Turner   W.printHex("OffsetToPadding", FrameProc.OffsetToPadding);
431aaad5744SZachary Turner   W.printHex("BytesOfCalleeSavedRegisters",
43246225b19SZachary Turner              FrameProc.BytesOfCalleeSavedRegisters);
43346225b19SZachary Turner   W.printHex("OffsetOfExceptionHandler", FrameProc.OffsetOfExceptionHandler);
434aaad5744SZachary Turner   W.printHex("SectionIdOfExceptionHandler",
43546225b19SZachary Turner              FrameProc.SectionIdOfExceptionHandler);
43646225b19SZachary Turner   W.printFlags("Flags", static_cast<uint32_t>(FrameProc.Flags),
43746225b19SZachary Turner                getFrameProcSymFlagNames());
4380d840744SZachary Turner   return Error::success();
439aaad5744SZachary Turner }
440aaad5744SZachary Turner 
4410d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(
4420d840744SZachary Turner     CVSymbol &CVR, HeapAllocationSiteSym &HeapAllocSite) {
443aaad5744SZachary Turner   DictScope S(W, "HeapAllocationSite");
444aaad5744SZachary Turner 
445aaad5744SZachary Turner   StringRef LinkageName;
446aaad5744SZachary Turner   if (ObjDelegate) {
44746225b19SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset",
44846225b19SZachary Turner                                      HeapAllocSite.getRelocationOffset(),
44946225b19SZachary Turner                                      HeapAllocSite.CodeOffset, &LinkageName);
450aaad5744SZachary Turner   }
45146225b19SZachary Turner   W.printHex("Segment", HeapAllocSite.Segment);
45246225b19SZachary Turner   W.printHex("CallInstructionSize", HeapAllocSite.CallInstructionSize);
453629cb7d8SZachary Turner   printTypeIndex("Type", HeapAllocSite.Type);
454aaad5744SZachary Turner   if (!LinkageName.empty())
455aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
4560d840744SZachary Turner   return Error::success();
457aaad5744SZachary Turner }
458aaad5744SZachary Turner 
4590d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
460aaad5744SZachary Turner                                            InlineSiteSym &InlineSite) {
461aaad5744SZachary Turner   DictScope S(W, "InlineSite");
462aaad5744SZachary Turner 
46346225b19SZachary Turner   W.printHex("PtrParent", InlineSite.Parent);
46446225b19SZachary Turner   W.printHex("PtrEnd", InlineSite.End);
465629cb7d8SZachary Turner   printTypeIndex("Inlinee", InlineSite.Inlinee);
466aaad5744SZachary Turner 
467aaad5744SZachary Turner   ListScope BinaryAnnotations(W, "BinaryAnnotations");
468aaad5744SZachary Turner   for (auto &Annotation : InlineSite.annotations()) {
469aaad5744SZachary Turner     switch (Annotation.OpCode) {
470aaad5744SZachary Turner     case BinaryAnnotationsOpCode::Invalid:
471*42cb87f4SZachary Turner       W.printString("(Annotation Padding)");
472*42cb87f4SZachary Turner       break;
473aaad5744SZachary Turner     case BinaryAnnotationsOpCode::CodeOffset:
474aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeCodeOffset:
475aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeCodeLength:
476aaad5744SZachary Turner       W.printHex(Annotation.Name, Annotation.U1);
477aaad5744SZachary Turner       break;
478aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeCodeOffsetBase:
479aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeLineEndDelta:
480aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeRangeKind:
481aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeColumnStart:
482aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeColumnEnd:
483aaad5744SZachary Turner       W.printNumber(Annotation.Name, Annotation.U1);
484aaad5744SZachary Turner       break;
485aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeLineOffset:
486aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeColumnEndDelta:
487aaad5744SZachary Turner       W.printNumber(Annotation.Name, Annotation.S1);
488aaad5744SZachary Turner       break;
489aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeFile:
490aaad5744SZachary Turner       if (ObjDelegate) {
491aaad5744SZachary Turner         W.printHex("ChangeFile",
492aaad5744SZachary Turner                    ObjDelegate->getFileNameForFileOffset(Annotation.U1),
493aaad5744SZachary Turner                    Annotation.U1);
494aaad5744SZachary Turner       } else {
495aaad5744SZachary Turner         W.printHex("ChangeFile", Annotation.U1);
496aaad5744SZachary Turner       }
497aaad5744SZachary Turner 
498aaad5744SZachary Turner       break;
499aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeCodeOffsetAndLineOffset: {
500aaad5744SZachary Turner       W.startLine() << "ChangeCodeOffsetAndLineOffset: {CodeOffset: "
501aaad5744SZachary Turner                     << W.hex(Annotation.U1) << ", LineOffset: " << Annotation.S1
502aaad5744SZachary Turner                     << "}\n";
503aaad5744SZachary Turner       break;
504aaad5744SZachary Turner     }
505aaad5744SZachary Turner     case BinaryAnnotationsOpCode::ChangeCodeLengthAndCodeOffset: {
506aaad5744SZachary Turner       W.startLine() << "ChangeCodeLengthAndCodeOffset: {CodeOffset: "
507aaad5744SZachary Turner                     << W.hex(Annotation.U2)
508aaad5744SZachary Turner                     << ", Length: " << W.hex(Annotation.U1) << "}\n";
509aaad5744SZachary Turner       break;
510aaad5744SZachary Turner     }
511aaad5744SZachary Turner     }
512aaad5744SZachary Turner   }
5130d840744SZachary Turner   return Error::success();
514aaad5744SZachary Turner }
515aaad5744SZachary Turner 
5160d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
5174caa1bf0SZachary Turner                                            RegisterSym &Register) {
5184caa1bf0SZachary Turner   DictScope S(W, "RegisterSym");
51946225b19SZachary Turner   W.printNumber("Type", Register.Index);
52046225b19SZachary Turner   W.printEnum("Seg", uint16_t(Register.Register), getRegisterNames());
5214caa1bf0SZachary Turner   W.printString("Name", Register.Name);
5220d840744SZachary Turner   return Error::success();
5234caa1bf0SZachary Turner }
5244caa1bf0SZachary Turner 
5250d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, PublicSym32 &Public) {
5269e33e6f8SZachary Turner   DictScope S(W, "PublicSym");
52746225b19SZachary Turner   W.printNumber("Type", Public.Index);
52846225b19SZachary Turner   W.printNumber("Seg", Public.Segment);
52946225b19SZachary Turner   W.printNumber("Off", Public.Offset);
5309e33e6f8SZachary Turner   W.printString("Name", Public.Name);
5310d840744SZachary Turner   return Error::success();
5329e33e6f8SZachary Turner }
5339e33e6f8SZachary Turner 
5340d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, ProcRefSym &ProcRef) {
5359e33e6f8SZachary Turner   DictScope S(W, "ProcRef");
53646225b19SZachary Turner   W.printNumber("SumName", ProcRef.SumName);
53746225b19SZachary Turner   W.printNumber("SymOffset", ProcRef.SymOffset);
53846225b19SZachary Turner   W.printNumber("Mod", ProcRef.Module);
5399e33e6f8SZachary Turner   W.printString("Name", ProcRef.Name);
5400d840744SZachary Turner   return Error::success();
5419e33e6f8SZachary Turner }
5429e33e6f8SZachary Turner 
5430d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, LabelSym &Label) {
544aaad5744SZachary Turner   DictScope S(W, "Label");
545aaad5744SZachary Turner 
546aaad5744SZachary Turner   StringRef LinkageName;
547aaad5744SZachary Turner   if (ObjDelegate) {
548aaad5744SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset", Label.getRelocationOffset(),
54946225b19SZachary Turner                                      Label.CodeOffset, &LinkageName);
550aaad5744SZachary Turner   }
55146225b19SZachary Turner   W.printHex("Segment", Label.Segment);
55246225b19SZachary Turner   W.printHex("Flags", uint8_t(Label.Flags));
55346225b19SZachary Turner   W.printFlags("Flags", uint8_t(Label.Flags), getProcSymFlagNames());
554aaad5744SZachary Turner   W.printString("DisplayName", Label.Name);
555aaad5744SZachary Turner   if (!LinkageName.empty())
556aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
5570d840744SZachary Turner   return Error::success();
558aaad5744SZachary Turner }
559aaad5744SZachary Turner 
5600d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, LocalSym &Local) {
561aaad5744SZachary Turner   DictScope S(W, "Local");
562aaad5744SZachary Turner 
563629cb7d8SZachary Turner   printTypeIndex("Type", Local.Type);
56446225b19SZachary Turner   W.printFlags("Flags", uint16_t(Local.Flags), getLocalFlagNames());
565aaad5744SZachary Turner   W.printString("VarName", Local.Name);
5660d840744SZachary Turner   return Error::success();
567aaad5744SZachary Turner }
568aaad5744SZachary Turner 
5690d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, ObjNameSym &ObjName) {
570aaad5744SZachary Turner   DictScope S(W, "ObjectName");
571aaad5744SZachary Turner 
57246225b19SZachary Turner   W.printHex("Signature", ObjName.Signature);
573aaad5744SZachary Turner   W.printString("ObjectName", ObjName.Name);
5740d840744SZachary Turner   return Error::success();
575aaad5744SZachary Turner }
576aaad5744SZachary Turner 
5770d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, ProcSym &Proc) {
578aaad5744SZachary Turner   DictScope S(W, "ProcStart");
579aaad5744SZachary Turner 
580aaad5744SZachary Turner   if (InFunctionScope)
5810d840744SZachary Turner     return llvm::make_error<CodeViewError>(
5820d840744SZachary Turner         "Visiting a ProcSym while inside function scope!");
583aaad5744SZachary Turner 
584aaad5744SZachary Turner   InFunctionScope = true;
585aaad5744SZachary Turner 
586aaad5744SZachary Turner   StringRef LinkageName;
5870d840744SZachary Turner   W.printEnum("Kind", uint16_t(CVR.kind()), getSymbolTypeNames());
58846225b19SZachary Turner   W.printHex("PtrParent", Proc.Parent);
58946225b19SZachary Turner   W.printHex("PtrEnd", Proc.End);
59046225b19SZachary Turner   W.printHex("PtrNext", Proc.Next);
59146225b19SZachary Turner   W.printHex("CodeSize", Proc.CodeSize);
59246225b19SZachary Turner   W.printHex("DbgStart", Proc.DbgStart);
59346225b19SZachary Turner   W.printHex("DbgEnd", Proc.DbgEnd);
594629cb7d8SZachary Turner   printTypeIndex("FunctionType", Proc.FunctionType);
595aaad5744SZachary Turner   if (ObjDelegate) {
596aaad5744SZachary Turner     ObjDelegate->printRelocatedField("CodeOffset", Proc.getRelocationOffset(),
59746225b19SZachary Turner                                      Proc.CodeOffset, &LinkageName);
598aaad5744SZachary Turner   }
59946225b19SZachary Turner   W.printHex("Segment", Proc.Segment);
60046225b19SZachary Turner   W.printFlags("Flags", static_cast<uint8_t>(Proc.Flags),
60193839cb4SZachary Turner                getProcSymFlagNames());
602aaad5744SZachary Turner   W.printString("DisplayName", Proc.Name);
603aaad5744SZachary Turner   if (!LinkageName.empty())
604aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
6050d840744SZachary Turner   return Error::success();
606aaad5744SZachary Turner }
607aaad5744SZachary Turner 
6080d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
609aaad5744SZachary Turner                                            ScopeEndSym &ScopeEnd) {
6100d840744SZachary Turner   if (CVR.kind() == SymbolKind::S_END)
611cac29ae0SZachary Turner     DictScope S(W, "BlockEnd");
6120d840744SZachary Turner   else if (CVR.kind() == SymbolKind::S_PROC_ID_END)
613cac29ae0SZachary Turner     DictScope S(W, "ProcEnd");
6140d840744SZachary Turner   else if (CVR.kind() == SymbolKind::S_INLINESITE_END)
615aaad5744SZachary Turner     DictScope S(W, "InlineSiteEnd");
616aaad5744SZachary Turner 
617aaad5744SZachary Turner   InFunctionScope = false;
6180d840744SZachary Turner   return Error::success();
619aaad5744SZachary Turner }
620aaad5744SZachary Turner 
6210d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, CallerSym &Caller) {
6220d840744SZachary Turner   ListScope S(W, CVR.kind() == S_CALLEES ? "Callees" : "Callers");
623aaad5744SZachary Turner   for (auto FuncID : Caller.Indices)
624629cb7d8SZachary Turner     printTypeIndex("FuncID", FuncID);
6250d840744SZachary Turner   return Error::success();
626aaad5744SZachary Turner }
627aaad5744SZachary Turner 
6280d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
629aaad5744SZachary Turner                                            RegRelativeSym &RegRel) {
630aaad5744SZachary Turner   DictScope S(W, "RegRelativeSym");
631aaad5744SZachary Turner 
63246225b19SZachary Turner   W.printHex("Offset", RegRel.Offset);
633629cb7d8SZachary Turner   printTypeIndex("Type", RegRel.Type);
63446225b19SZachary Turner   W.printHex("Register", RegRel.Register);
635aaad5744SZachary Turner   W.printString("VarName", RegRel.Name);
6360d840744SZachary Turner   return Error::success();
637aaad5744SZachary Turner }
638aaad5744SZachary Turner 
6390d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR,
640aaad5744SZachary Turner                                            ThreadLocalDataSym &Data) {
641aaad5744SZachary Turner   DictScope S(W, "ThreadLocalDataSym");
642aaad5744SZachary Turner 
643aaad5744SZachary Turner   StringRef LinkageName;
644aaad5744SZachary Turner   if (ObjDelegate) {
645aaad5744SZachary Turner     ObjDelegate->printRelocatedField("DataOffset", Data.getRelocationOffset(),
64646225b19SZachary Turner                                      Data.DataOffset, &LinkageName);
647aaad5744SZachary Turner   }
648629cb7d8SZachary Turner   printTypeIndex("Type", Data.Type);
649aaad5744SZachary Turner   W.printString("DisplayName", Data.Name);
650aaad5744SZachary Turner   if (!LinkageName.empty())
651aaad5744SZachary Turner     W.printString("LinkageName", LinkageName);
6520d840744SZachary Turner   return Error::success();
653aaad5744SZachary Turner }
654aaad5744SZachary Turner 
6550d840744SZachary Turner Error CVSymbolDumperImpl::visitKnownRecord(CVSymbol &CVR, UDTSym &UDT) {
656aaad5744SZachary Turner   DictScope S(W, "UDT");
657629cb7d8SZachary Turner   printTypeIndex("Type", UDT.Type);
658aaad5744SZachary Turner   W.printString("UDTName", UDT.Name);
6590d840744SZachary Turner   return Error::success();
660aaad5744SZachary Turner }
661aaad5744SZachary Turner 
6620d840744SZachary Turner Error CVSymbolDumperImpl::visitUnknownSymbol(CVSymbol &CVR) {
663aaad5744SZachary Turner   DictScope S(W, "UnknownSym");
6640d840744SZachary Turner   W.printEnum("Kind", uint16_t(CVR.kind()), getSymbolTypeNames());
6650d840744SZachary Turner   W.printNumber("Length", CVR.length());
6660d840744SZachary Turner   return Error::success();
667aaad5744SZachary Turner }
668aaad5744SZachary Turner 
6690d840744SZachary Turner Error CVSymbolDumper::dump(CVRecord<SymbolKind> &Record) {
6700d840744SZachary Turner   SymbolVisitorCallbackPipeline Pipeline;
6710d840744SZachary Turner   SymbolDeserializer Deserializer(ObjDelegate.get());
672629cb7d8SZachary Turner   CVSymbolDumperImpl Dumper(TypeDB, ObjDelegate.get(), W, PrintRecordBytes);
6730d840744SZachary Turner 
6740d840744SZachary Turner   Pipeline.addCallbackToPipeline(Deserializer);
6750d840744SZachary Turner   Pipeline.addCallbackToPipeline(Dumper);
6760d840744SZachary Turner   CVSymbolVisitor Visitor(Pipeline);
6770d840744SZachary Turner   return Visitor.visitSymbolRecord(Record);
678aaad5744SZachary Turner }
679aaad5744SZachary Turner 
6800d840744SZachary Turner Error CVSymbolDumper::dump(const CVSymbolArray &Symbols) {
6810d840744SZachary Turner   SymbolVisitorCallbackPipeline Pipeline;
6820d840744SZachary Turner   SymbolDeserializer Deserializer(ObjDelegate.get());
683629cb7d8SZachary Turner   CVSymbolDumperImpl Dumper(TypeDB, ObjDelegate.get(), W, PrintRecordBytes);
6840d840744SZachary Turner 
6850d840744SZachary Turner   Pipeline.addCallbackToPipeline(Deserializer);
6860d840744SZachary Turner   Pipeline.addCallbackToPipeline(Dumper);
6870d840744SZachary Turner   CVSymbolVisitor Visitor(Pipeline);
6880d840744SZachary Turner   return Visitor.visitSymbolStream(Symbols);
689aaad5744SZachary Turner }
690