blob: 4afcdf189f2975a6aa084bb3697b48a77151eed1 [file] [log] [blame]
Zachary Turneraaad5742016-05-23 23:41:13 +00001//===-- SymbolDumper.cpp - CodeView symbol info dumper ----------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "llvm/DebugInfo/CodeView/SymbolDumper.h"
11#include "llvm/ADT/DenseMap.h"
12#include "llvm/ADT/SmallString.h"
13#include "llvm/DebugInfo/CodeView/CVSymbolVisitor.h"
14#include "llvm/DebugInfo/CodeView/SymbolDumpDelegate.h"
15#include "llvm/DebugInfo/CodeView/SymbolRecord.h"
16#include "llvm/DebugInfo/CodeView/TypeDumper.h"
17#include "llvm/DebugInfo/CodeView/TypeIndex.h"
18#include "llvm/Support/ScopedPrinter.h"
19
20#include <system_error>
21
22using namespace llvm;
23using namespace llvm::codeview;
24
25static const EnumEntry<SymbolKind> SymbolTypeNames[] = {
26#define CV_SYMBOL(enum, val) {#enum, enum},
27#include "llvm/DebugInfo/CodeView/CVSymbolTypes.def"
28};
29
30namespace {
31#define CV_ENUM_CLASS_ENT(enum_class, enum) \
32 { #enum, std::underlying_type < enum_class > ::type(enum_class::enum) }
33
34#define CV_ENUM_ENT(ns, enum) \
35 { #enum, ns::enum }
36
Zachary Turner4caa1bf2016-05-24 22:58:46 +000037static const EnumEntry<uint16_t> RegisterNames[] = {
38 CV_ENUM_CLASS_ENT(RegisterId, Unknown),
39 CV_ENUM_CLASS_ENT(RegisterId, VFrame),
40 CV_ENUM_CLASS_ENT(RegisterId, AL),
41 CV_ENUM_CLASS_ENT(RegisterId, CL),
42 CV_ENUM_CLASS_ENT(RegisterId, DL),
43 CV_ENUM_CLASS_ENT(RegisterId, BL),
44 CV_ENUM_CLASS_ENT(RegisterId, AH),
45 CV_ENUM_CLASS_ENT(RegisterId, CH),
46 CV_ENUM_CLASS_ENT(RegisterId, DH),
47 CV_ENUM_CLASS_ENT(RegisterId, BH),
48 CV_ENUM_CLASS_ENT(RegisterId, AX),
49 CV_ENUM_CLASS_ENT(RegisterId, CX),
50 CV_ENUM_CLASS_ENT(RegisterId, DX),
51 CV_ENUM_CLASS_ENT(RegisterId, BX),
52 CV_ENUM_CLASS_ENT(RegisterId, SP),
53 CV_ENUM_CLASS_ENT(RegisterId, BP),
54 CV_ENUM_CLASS_ENT(RegisterId, SI),
55 CV_ENUM_CLASS_ENT(RegisterId, DI),
56 CV_ENUM_CLASS_ENT(RegisterId, EAX),
57 CV_ENUM_CLASS_ENT(RegisterId, ECX),
58 CV_ENUM_CLASS_ENT(RegisterId, EDX),
59 CV_ENUM_CLASS_ENT(RegisterId, EBX),
60 CV_ENUM_CLASS_ENT(RegisterId, ESP),
61 CV_ENUM_CLASS_ENT(RegisterId, EBP),
62 CV_ENUM_CLASS_ENT(RegisterId, ESI),
63 CV_ENUM_CLASS_ENT(RegisterId, EDI),
64 CV_ENUM_CLASS_ENT(RegisterId, ES),
65 CV_ENUM_CLASS_ENT(RegisterId, CS),
66 CV_ENUM_CLASS_ENT(RegisterId, SS),
67 CV_ENUM_CLASS_ENT(RegisterId, DS),
68 CV_ENUM_CLASS_ENT(RegisterId, FS),
69 CV_ENUM_CLASS_ENT(RegisterId, GS),
70 CV_ENUM_CLASS_ENT(RegisterId, IP),
71 CV_ENUM_CLASS_ENT(RegisterId, RAX),
72 CV_ENUM_CLASS_ENT(RegisterId, RBX),
73 CV_ENUM_CLASS_ENT(RegisterId, RCX),
74 CV_ENUM_CLASS_ENT(RegisterId, RDX),
75 CV_ENUM_CLASS_ENT(RegisterId, RSI),
76 CV_ENUM_CLASS_ENT(RegisterId, RDI),
77 CV_ENUM_CLASS_ENT(RegisterId, RBP),
78 CV_ENUM_CLASS_ENT(RegisterId, RSP),
79 CV_ENUM_CLASS_ENT(RegisterId, R8),
80 CV_ENUM_CLASS_ENT(RegisterId, R9),
81 CV_ENUM_CLASS_ENT(RegisterId, R10),
82 CV_ENUM_CLASS_ENT(RegisterId, R11),
83 CV_ENUM_CLASS_ENT(RegisterId, R12),
84 CV_ENUM_CLASS_ENT(RegisterId, R13),
85 CV_ENUM_CLASS_ENT(RegisterId, R14),
86 CV_ENUM_CLASS_ENT(RegisterId, R15),
87};
88
Zachary Turneraaad5742016-05-23 23:41:13 +000089static const EnumEntry<uint8_t> ProcSymFlagNames[] = {
90 CV_ENUM_CLASS_ENT(ProcSymFlags, HasFP),
91 CV_ENUM_CLASS_ENT(ProcSymFlags, HasIRET),
92 CV_ENUM_CLASS_ENT(ProcSymFlags, HasFRET),
93 CV_ENUM_CLASS_ENT(ProcSymFlags, IsNoReturn),
94 CV_ENUM_CLASS_ENT(ProcSymFlags, IsUnreachable),
95 CV_ENUM_CLASS_ENT(ProcSymFlags, HasCustomCallingConv),
96 CV_ENUM_CLASS_ENT(ProcSymFlags, IsNoInline),
97 CV_ENUM_CLASS_ENT(ProcSymFlags, HasOptimizedDebugInfo),
98};
99
100static const EnumEntry<uint16_t> LocalFlags[] = {
101 CV_ENUM_CLASS_ENT(LocalSymFlags, IsParameter),
102 CV_ENUM_CLASS_ENT(LocalSymFlags, IsAddressTaken),
103 CV_ENUM_CLASS_ENT(LocalSymFlags, IsCompilerGenerated),
104 CV_ENUM_CLASS_ENT(LocalSymFlags, IsAggregate),
105 CV_ENUM_CLASS_ENT(LocalSymFlags, IsAggregated),
106 CV_ENUM_CLASS_ENT(LocalSymFlags, IsAliased),
107 CV_ENUM_CLASS_ENT(LocalSymFlags, IsAlias),
108 CV_ENUM_CLASS_ENT(LocalSymFlags, IsReturnValue),
109 CV_ENUM_CLASS_ENT(LocalSymFlags, IsOptimizedOut),
110 CV_ENUM_CLASS_ENT(LocalSymFlags, IsEnregisteredGlobal),
111 CV_ENUM_CLASS_ENT(LocalSymFlags, IsEnregisteredStatic),
112};
113
114static const EnumEntry<uint32_t> FrameCookieKinds[] = {
115 CV_ENUM_CLASS_ENT(FrameCookieKind, Copy),
116 CV_ENUM_CLASS_ENT(FrameCookieKind, XorStackPointer),
117 CV_ENUM_CLASS_ENT(FrameCookieKind, XorFramePointer),
118 CV_ENUM_CLASS_ENT(FrameCookieKind, XorR13),
119};
120
121static const EnumEntry<codeview::SourceLanguage> SourceLanguages[] = {
122 CV_ENUM_ENT(SourceLanguage, C), CV_ENUM_ENT(SourceLanguage, Cpp),
123 CV_ENUM_ENT(SourceLanguage, Fortran), CV_ENUM_ENT(SourceLanguage, Masm),
124 CV_ENUM_ENT(SourceLanguage, Pascal), CV_ENUM_ENT(SourceLanguage, Basic),
125 CV_ENUM_ENT(SourceLanguage, Cobol), CV_ENUM_ENT(SourceLanguage, Link),
126 CV_ENUM_ENT(SourceLanguage, Cvtres), CV_ENUM_ENT(SourceLanguage, Cvtpgd),
127 CV_ENUM_ENT(SourceLanguage, CSharp), CV_ENUM_ENT(SourceLanguage, VB),
128 CV_ENUM_ENT(SourceLanguage, ILAsm), CV_ENUM_ENT(SourceLanguage, Java),
129 CV_ENUM_ENT(SourceLanguage, JScript), CV_ENUM_ENT(SourceLanguage, MSIL),
130 CV_ENUM_ENT(SourceLanguage, HLSL),
131};
132
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000133static const EnumEntry<uint32_t> CompileSym2FlagNames[] = {
134 CV_ENUM_CLASS_ENT(CompileSym2Flags, EC),
135 CV_ENUM_CLASS_ENT(CompileSym2Flags, NoDbgInfo),
136 CV_ENUM_CLASS_ENT(CompileSym2Flags, LTCG),
137 CV_ENUM_CLASS_ENT(CompileSym2Flags, NoDataAlign),
138 CV_ENUM_CLASS_ENT(CompileSym2Flags, ManagedPresent),
139 CV_ENUM_CLASS_ENT(CompileSym2Flags, SecurityChecks),
140 CV_ENUM_CLASS_ENT(CompileSym2Flags, HotPatch),
141 CV_ENUM_CLASS_ENT(CompileSym2Flags, CVTCIL),
142 CV_ENUM_CLASS_ENT(CompileSym2Flags, MSILModule),
143};
144
Zachary Turneraaad5742016-05-23 23:41:13 +0000145static const EnumEntry<uint32_t> CompileSym3FlagNames[] = {
146 CV_ENUM_CLASS_ENT(CompileSym3Flags, EC),
147 CV_ENUM_CLASS_ENT(CompileSym3Flags, NoDbgInfo),
148 CV_ENUM_CLASS_ENT(CompileSym3Flags, LTCG),
149 CV_ENUM_CLASS_ENT(CompileSym3Flags, NoDataAlign),
150 CV_ENUM_CLASS_ENT(CompileSym3Flags, ManagedPresent),
151 CV_ENUM_CLASS_ENT(CompileSym3Flags, SecurityChecks),
152 CV_ENUM_CLASS_ENT(CompileSym3Flags, HotPatch),
153 CV_ENUM_CLASS_ENT(CompileSym3Flags, CVTCIL),
154 CV_ENUM_CLASS_ENT(CompileSym3Flags, MSILModule),
155 CV_ENUM_CLASS_ENT(CompileSym3Flags, Sdl),
156 CV_ENUM_CLASS_ENT(CompileSym3Flags, PGO),
157 CV_ENUM_CLASS_ENT(CompileSym3Flags, Exp),
158};
159
160static const EnumEntry<unsigned> CPUTypeNames[] = {
161 CV_ENUM_CLASS_ENT(CPUType, Intel8080),
162 CV_ENUM_CLASS_ENT(CPUType, Intel8086),
163 CV_ENUM_CLASS_ENT(CPUType, Intel80286),
164 CV_ENUM_CLASS_ENT(CPUType, Intel80386),
165 CV_ENUM_CLASS_ENT(CPUType, Intel80486),
166 CV_ENUM_CLASS_ENT(CPUType, Pentium),
167 CV_ENUM_CLASS_ENT(CPUType, PentiumPro),
168 CV_ENUM_CLASS_ENT(CPUType, Pentium3),
169 CV_ENUM_CLASS_ENT(CPUType, MIPS),
170 CV_ENUM_CLASS_ENT(CPUType, MIPS16),
171 CV_ENUM_CLASS_ENT(CPUType, MIPS32),
172 CV_ENUM_CLASS_ENT(CPUType, MIPS64),
173 CV_ENUM_CLASS_ENT(CPUType, MIPSI),
174 CV_ENUM_CLASS_ENT(CPUType, MIPSII),
175 CV_ENUM_CLASS_ENT(CPUType, MIPSIII),
176 CV_ENUM_CLASS_ENT(CPUType, MIPSIV),
177 CV_ENUM_CLASS_ENT(CPUType, MIPSV),
178 CV_ENUM_CLASS_ENT(CPUType, M68000),
179 CV_ENUM_CLASS_ENT(CPUType, M68010),
180 CV_ENUM_CLASS_ENT(CPUType, M68020),
181 CV_ENUM_CLASS_ENT(CPUType, M68030),
182 CV_ENUM_CLASS_ENT(CPUType, M68040),
183 CV_ENUM_CLASS_ENT(CPUType, Alpha),
184 CV_ENUM_CLASS_ENT(CPUType, Alpha21164),
185 CV_ENUM_CLASS_ENT(CPUType, Alpha21164A),
186 CV_ENUM_CLASS_ENT(CPUType, Alpha21264),
187 CV_ENUM_CLASS_ENT(CPUType, Alpha21364),
188 CV_ENUM_CLASS_ENT(CPUType, PPC601),
189 CV_ENUM_CLASS_ENT(CPUType, PPC603),
190 CV_ENUM_CLASS_ENT(CPUType, PPC604),
191 CV_ENUM_CLASS_ENT(CPUType, PPC620),
192 CV_ENUM_CLASS_ENT(CPUType, PPCFP),
193 CV_ENUM_CLASS_ENT(CPUType, PPCBE),
194 CV_ENUM_CLASS_ENT(CPUType, SH3),
195 CV_ENUM_CLASS_ENT(CPUType, SH3E),
196 CV_ENUM_CLASS_ENT(CPUType, SH3DSP),
197 CV_ENUM_CLASS_ENT(CPUType, SH4),
198 CV_ENUM_CLASS_ENT(CPUType, SHMedia),
199 CV_ENUM_CLASS_ENT(CPUType, ARM3),
200 CV_ENUM_CLASS_ENT(CPUType, ARM4),
201 CV_ENUM_CLASS_ENT(CPUType, ARM4T),
202 CV_ENUM_CLASS_ENT(CPUType, ARM5),
203 CV_ENUM_CLASS_ENT(CPUType, ARM5T),
204 CV_ENUM_CLASS_ENT(CPUType, ARM6),
205 CV_ENUM_CLASS_ENT(CPUType, ARM_XMAC),
206 CV_ENUM_CLASS_ENT(CPUType, ARM_WMMX),
207 CV_ENUM_CLASS_ENT(CPUType, ARM7),
208 CV_ENUM_CLASS_ENT(CPUType, Omni),
209 CV_ENUM_CLASS_ENT(CPUType, Ia64),
210 CV_ENUM_CLASS_ENT(CPUType, Ia64_2),
211 CV_ENUM_CLASS_ENT(CPUType, CEE),
212 CV_ENUM_CLASS_ENT(CPUType, AM33),
213 CV_ENUM_CLASS_ENT(CPUType, M32R),
214 CV_ENUM_CLASS_ENT(CPUType, TriCore),
215 CV_ENUM_CLASS_ENT(CPUType, X64),
216 CV_ENUM_CLASS_ENT(CPUType, EBC),
217 CV_ENUM_CLASS_ENT(CPUType, Thumb),
218 CV_ENUM_CLASS_ENT(CPUType, ARMNT),
219 CV_ENUM_CLASS_ENT(CPUType, D3D11_Shader),
220};
221
222static const EnumEntry<uint32_t> FrameProcSymFlags[] = {
223 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasAlloca),
224 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasSetJmp),
225 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasLongJmp),
226 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasInlineAssembly),
227 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasExceptionHandling),
228 CV_ENUM_CLASS_ENT(FrameProcedureOptions, MarkedInline),
229 CV_ENUM_CLASS_ENT(FrameProcedureOptions, HasStructuredExceptionHandling),
230 CV_ENUM_CLASS_ENT(FrameProcedureOptions, Naked),
231 CV_ENUM_CLASS_ENT(FrameProcedureOptions, SecurityChecks),
232 CV_ENUM_CLASS_ENT(FrameProcedureOptions, AsynchronousExceptionHandling),
233 CV_ENUM_CLASS_ENT(FrameProcedureOptions, NoStackOrderingForSecurityChecks),
234 CV_ENUM_CLASS_ENT(FrameProcedureOptions, Inlined),
235 CV_ENUM_CLASS_ENT(FrameProcedureOptions, StrictSecurityChecks),
236 CV_ENUM_CLASS_ENT(FrameProcedureOptions, SafeBuffers),
237 CV_ENUM_CLASS_ENT(FrameProcedureOptions, ProfileGuidedOptimization),
238 CV_ENUM_CLASS_ENT(FrameProcedureOptions, ValidProfileCounts),
239 CV_ENUM_CLASS_ENT(FrameProcedureOptions, OptimizedForSpeed),
240 CV_ENUM_CLASS_ENT(FrameProcedureOptions, GuardCfg),
241 CV_ENUM_CLASS_ENT(FrameProcedureOptions, GuardCfw),
242};
243
Zachary Turner9f054d42016-05-25 00:12:40 +0000244static const EnumEntry<uint16_t> ExportSymFlags[] = {
245 CV_ENUM_CLASS_ENT(ExportFlags, IsConstant),
246 CV_ENUM_CLASS_ENT(ExportFlags, IsData),
247 CV_ENUM_CLASS_ENT(ExportFlags, IsPrivate),
248 CV_ENUM_CLASS_ENT(ExportFlags, HasNoName),
249 CV_ENUM_CLASS_ENT(ExportFlags, HasExplicitOrdinal),
250 CV_ENUM_CLASS_ENT(ExportFlags, IsForwarder),
251};
252
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000253static const EnumEntry<uint8_t> ThunkOrdinalNames[] = {
254 CV_ENUM_CLASS_ENT(ThunkOrdinal, Standard),
255 CV_ENUM_CLASS_ENT(ThunkOrdinal, ThisAdjustor),
256 CV_ENUM_CLASS_ENT(ThunkOrdinal, Vcall),
257 CV_ENUM_CLASS_ENT(ThunkOrdinal, Pcode),
258 CV_ENUM_CLASS_ENT(ThunkOrdinal, UnknownLoad),
259 CV_ENUM_CLASS_ENT(ThunkOrdinal, TrampIncremental),
260 CV_ENUM_CLASS_ENT(ThunkOrdinal, BranchIsland),
261};
262
263static const EnumEntry<uint16_t> TrampolineNames[] = {
264 CV_ENUM_CLASS_ENT(TrampolineType, TrampIncremental),
265 CV_ENUM_CLASS_ENT(TrampolineType, BranchIsland),
266};
267
Zachary Turneraaad5742016-05-23 23:41:13 +0000268/// Use this private dumper implementation to keep implementation details about
269/// the visitor out of SymbolDumper.h.
270class CVSymbolDumperImpl : public CVSymbolVisitor<CVSymbolDumperImpl> {
271public:
Zachary Turner3e78e2d2016-05-24 00:06:04 +0000272 CVSymbolDumperImpl(CVTypeDumper &CVTD, SymbolDumpDelegate *ObjDelegate,
273 ScopedPrinter &W, bool PrintRecordBytes)
274 : CVSymbolVisitor(ObjDelegate), CVTD(CVTD), ObjDelegate(ObjDelegate),
275 W(W), PrintRecordBytes(PrintRecordBytes), InFunctionScope(false) {}
Zachary Turneraaad5742016-05-23 23:41:13 +0000276
277/// CVSymbolVisitor overrides.
278#define SYMBOL_RECORD(EnumName, EnumVal, Name) \
279 void visit##Name(SymbolKind Kind, Name &Record);
280#define SYMBOL_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName)
281#include "llvm/DebugInfo/CodeView/CVSymbolTypes.def"
282
283 void visitSymbolBegin(SymbolKind Kind, ArrayRef<uint8_t> Data);
284 void visitSymbolEnd(SymbolKind Kind, ArrayRef<uint8_t> OriginalSymData);
285 void visitUnknownSymbol(SymbolKind Kind, ArrayRef<uint8_t> Data);
286
287private:
288 void printLocalVariableAddrRange(const LocalVariableAddrRange &Range,
289 uint32_t RelocationOffset);
290 void printLocalVariableAddrGap(ArrayRef<LocalVariableAddrGap> Gaps);
291
Zachary Turneraaad5742016-05-23 23:41:13 +0000292 CVTypeDumper &CVTD;
293 SymbolDumpDelegate *ObjDelegate;
294 ScopedPrinter &W;
295
296 bool PrintRecordBytes;
297 bool InFunctionScope;
298};
299}
300
301void CVSymbolDumperImpl::printLocalVariableAddrRange(
302 const LocalVariableAddrRange &Range, uint32_t RelocationOffset) {
303 DictScope S(W, "LocalVariableAddrRange");
304 if (ObjDelegate)
305 ObjDelegate->printRelocatedField("OffsetStart", RelocationOffset,
306 Range.OffsetStart);
307 W.printHex("ISectStart", Range.ISectStart);
308 W.printHex("Range", Range.Range);
309}
310
311void CVSymbolDumperImpl::printLocalVariableAddrGap(
312 ArrayRef<LocalVariableAddrGap> Gaps) {
313 for (auto &Gap : Gaps) {
314 ListScope S(W, "LocalVariableAddrGap");
315 W.printHex("GapStartOffset", Gap.GapStartOffset);
316 W.printHex("Range", Gap.Range);
317 }
318}
319
320void CVSymbolDumperImpl::visitSymbolBegin(SymbolKind Kind,
321 ArrayRef<uint8_t> Data) {}
322
323void CVSymbolDumperImpl::visitSymbolEnd(SymbolKind Kind,
324 ArrayRef<uint8_t> OriginalSymData) {
325 if (PrintRecordBytes && ObjDelegate)
326 ObjDelegate->printBinaryBlockWithRelocs("SymData", OriginalSymData);
327}
328
329void CVSymbolDumperImpl::visitBlockSym(SymbolKind Kind, BlockSym &Block) {
330 DictScope S(W, "BlockStart");
331
332 StringRef LinkageName;
333 W.printHex("PtrParent", Block.Header.PtrParent);
334 W.printHex("PtrEnd", Block.Header.PtrEnd);
335 W.printHex("CodeSize", Block.Header.CodeSize);
336 if (ObjDelegate) {
337 ObjDelegate->printRelocatedField("CodeOffset", Block.getRelocationOffset(),
338 Block.Header.CodeOffset, &LinkageName);
339 }
340 W.printHex("Segment", Block.Header.Segment);
341 W.printString("BlockName", Block.Name);
342 W.printString("LinkageName", LinkageName);
343}
344
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000345void CVSymbolDumperImpl::visitThunk32Sym(SymbolKind Kind, Thunk32Sym &Thunk) {
346 DictScope S(W, "Thunk32");
347 W.printNumber("Parent", Thunk.Header.Parent);
348 W.printNumber("End", Thunk.Header.End);
349 W.printNumber("Next", Thunk.Header.Next);
350 W.printNumber("Off", Thunk.Header.Off);
351 W.printNumber("Seg", Thunk.Header.Seg);
352 W.printNumber("Len", Thunk.Header.Len);
353 W.printEnum("Ordinal", Thunk.Header.Ord, makeArrayRef(ThunkOrdinalNames));
354}
355
356void CVSymbolDumperImpl::visitTrampolineSym(SymbolKind Kind,
357 TrampolineSym &Tramp) {
358 DictScope S(W, "Trampoline");
359 W.printEnum("Type", Tramp.Header.Type, makeArrayRef(TrampolineNames));
360 W.printNumber("Size", Tramp.Header.Size);
361 W.printNumber("ThunkOff", Tramp.Header.ThunkOff);
362 W.printNumber("TargetOff", Tramp.Header.TargetOff);
363 W.printNumber("ThunkSection", Tramp.Header.ThunkSection);
364 W.printNumber("TargetSection", Tramp.Header.TargetSection);
365}
366
367void CVSymbolDumperImpl::visitSectionSym(SymbolKind Kind, SectionSym &Section) {
368 DictScope S(W, "Section");
369 W.printNumber("SectionNumber", Section.Header.SectionNumber);
370 W.printNumber("Alignment", Section.Header.Alignment);
371 W.printNumber("Reserved", Section.Header.Reserved);
372 W.printNumber("Rva", Section.Header.Rva);
373 W.printNumber("Length", Section.Header.Length);
374 W.printHex("Characteristics", Section.Header.Characteristics);
375 W.printString("Name", Section.Name);
376}
377
378void CVSymbolDumperImpl::visitCoffGroupSym(SymbolKind Kind,
379 CoffGroupSym &CoffGroup) {
380 DictScope S(W, "COFF Group");
381 W.printNumber("Size", CoffGroup.Header.Size);
382 W.printHex("Characteristics", CoffGroup.Header.Characteristics);
383 W.printNumber("Offset", CoffGroup.Header.Offset);
384 W.printNumber("Segment", CoffGroup.Header.Segment);
385 W.printString("Name", CoffGroup.Name);
386}
387
Zachary Turneraaad5742016-05-23 23:41:13 +0000388void CVSymbolDumperImpl::visitBPRelativeSym(SymbolKind Kind,
389 BPRelativeSym &BPRel) {
390 DictScope S(W, "BPRelativeSym");
391
392 W.printNumber("Offset", BPRel.Header.Offset);
393 CVTD.printTypeIndex("Type", BPRel.Header.Type);
394 W.printString("VarName", BPRel.Name);
395}
396
397void CVSymbolDumperImpl::visitBuildInfoSym(SymbolKind Kind,
398 BuildInfoSym &BuildInfo) {
399 DictScope S(W, "BuildInfo");
400
401 W.printNumber("BuildId", BuildInfo.Header.BuildId);
402}
403
404void CVSymbolDumperImpl::visitCallSiteInfoSym(SymbolKind Kind,
405 CallSiteInfoSym &CallSiteInfo) {
406 DictScope S(W, "CallSiteInfo");
407
408 StringRef LinkageName;
409 if (ObjDelegate) {
410 ObjDelegate->printRelocatedField(
411 "CodeOffset", CallSiteInfo.getRelocationOffset(),
412 CallSiteInfo.Header.CodeOffset, &LinkageName);
413 }
414 W.printHex("Segment", CallSiteInfo.Header.Segment);
415 W.printHex("Reserved", CallSiteInfo.Header.Reserved);
416 CVTD.printTypeIndex("Type", CallSiteInfo.Header.Type);
417 if (!LinkageName.empty())
418 W.printString("LinkageName", LinkageName);
419}
420
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000421void CVSymbolDumperImpl::visitEnvBlockSym(SymbolKind Kind,
422 EnvBlockSym &EnvBlock) {
423 DictScope S(W, "EnvBlock");
424
425 W.printNumber("Reserved", EnvBlock.Header.Reserved);
426 ListScope L(W, "Entries");
427 for (auto Entry : EnvBlock.Fields) {
428 W.printString(Entry);
429 }
430}
431
432void CVSymbolDumperImpl::visitFileStaticSym(SymbolKind Kind,
433 FileStaticSym &FileStatic) {
434 DictScope S(W, "FileStatic");
435 W.printNumber("Index", FileStatic.Header.Index);
436 W.printNumber("ModFilenameOffset", FileStatic.Header.ModFilenameOffset);
437 W.printFlags("Flags", uint16_t(FileStatic.Header.Flags),
438 makeArrayRef(LocalFlags));
439 W.printString("Name", FileStatic.Name);
440}
441
Zachary Turner9f054d42016-05-25 00:12:40 +0000442void CVSymbolDumperImpl::visitExportSym(SymbolKind Kind, ExportSym &Export) {
443 DictScope S(W, "Export");
444 W.printNumber("Ordinal", Export.Header.Ordinal);
445 W.printFlags("Flags", Export.Header.Flags, makeArrayRef(ExportSymFlags));
446 W.printString("Name", Export.Name);
447}
448
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000449void CVSymbolDumperImpl::visitCompile2Sym(SymbolKind Kind,
450 Compile2Sym &Compile2) {
451 DictScope S(W, "CompilerFlags2");
452
453 W.printEnum("Language", Compile2.Header.getLanguage(),
454 makeArrayRef(SourceLanguages));
455 W.printFlags("Flags", Compile2.Header.flags & ~0xff,
456 makeArrayRef(CompileSym2FlagNames));
457 W.printEnum("Machine", unsigned(Compile2.Header.Machine),
458 makeArrayRef(CPUTypeNames));
459 std::string FrontendVersion;
460 {
461 raw_string_ostream Out(FrontendVersion);
462 Out << Compile2.Header.VersionFrontendMajor << '.'
463 << Compile2.Header.VersionFrontendMinor << '.'
464 << Compile2.Header.VersionFrontendBuild;
465 }
466 std::string BackendVersion;
467 {
468 raw_string_ostream Out(BackendVersion);
469 Out << Compile2.Header.VersionBackendMajor << '.'
470 << Compile2.Header.VersionBackendMinor << '.'
471 << Compile2.Header.VersionBackendBuild;
472 }
473 W.printString("FrontendVersion", FrontendVersion);
474 W.printString("BackendVersion", BackendVersion);
475 W.printString("VersionName", Compile2.Version);
476}
477
Zachary Turneraaad5742016-05-23 23:41:13 +0000478void CVSymbolDumperImpl::visitCompile3Sym(SymbolKind Kind,
479 Compile3Sym &Compile3) {
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000480 DictScope S(W, "CompilerFlags3");
Zachary Turneraaad5742016-05-23 23:41:13 +0000481
482 W.printEnum("Language", Compile3.Header.getLanguage(),
483 makeArrayRef(SourceLanguages));
484 W.printFlags("Flags", Compile3.Header.flags & ~0xff,
485 makeArrayRef(CompileSym3FlagNames));
486 W.printEnum("Machine", unsigned(Compile3.Header.Machine),
487 makeArrayRef(CPUTypeNames));
488 std::string FrontendVersion;
489 {
490 raw_string_ostream Out(FrontendVersion);
491 Out << Compile3.Header.VersionFrontendMajor << '.'
492 << Compile3.Header.VersionFrontendMinor << '.'
493 << Compile3.Header.VersionFrontendBuild << '.'
494 << Compile3.Header.VersionFrontendQFE;
495 }
496 std::string BackendVersion;
497 {
498 raw_string_ostream Out(BackendVersion);
499 Out << Compile3.Header.VersionBackendMajor << '.'
500 << Compile3.Header.VersionBackendMinor << '.'
501 << Compile3.Header.VersionBackendBuild << '.'
502 << Compile3.Header.VersionBackendQFE;
503 }
504 W.printString("FrontendVersion", FrontendVersion);
505 W.printString("BackendVersion", BackendVersion);
506 W.printString("VersionName", Compile3.Version);
507}
508
509void CVSymbolDumperImpl::visitConstantSym(SymbolKind Kind,
510 ConstantSym &Constant) {
511 DictScope S(W, "Constant");
512
513 CVTD.printTypeIndex("Type", Constant.Header.Type);
514 W.printNumber("Value", Constant.Value);
515 W.printString("Name", Constant.Name);
516}
517
518void CVSymbolDumperImpl::visitDataSym(SymbolKind Kind, DataSym &Data) {
519 DictScope S(W, "DataSym");
520
521 StringRef LinkageName;
522 if (ObjDelegate) {
523 ObjDelegate->printRelocatedField("DataOffset", Data.getRelocationOffset(),
524 Data.Header.DataOffset, &LinkageName);
525 }
526 CVTD.printTypeIndex("Type", Data.Header.Type);
527 W.printString("DisplayName", Data.Name);
528 if (!LinkageName.empty())
529 W.printString("LinkageName", LinkageName);
530}
531
532void CVSymbolDumperImpl::visitDefRangeFramePointerRelFullScopeSym(
533 SymbolKind Kind,
534 DefRangeFramePointerRelFullScopeSym &DefRangeFramePointerRelFullScope) {
535 DictScope S(W, "DefRangeFramePointerRelFullScope");
536 W.printNumber("Offset", DefRangeFramePointerRelFullScope.Header.Offset);
537}
538
539void CVSymbolDumperImpl::visitDefRangeFramePointerRelSym(
540 SymbolKind Kind, DefRangeFramePointerRelSym &DefRangeFramePointerRel) {
541 DictScope S(W, "DefRangeFramePointerRel");
542
543 W.printNumber("Offset", DefRangeFramePointerRel.Header.Offset);
544 printLocalVariableAddrRange(DefRangeFramePointerRel.Header.Range,
545 DefRangeFramePointerRel.getRelocationOffset());
546 printLocalVariableAddrGap(DefRangeFramePointerRel.Gaps);
547}
548
549void CVSymbolDumperImpl::visitDefRangeRegisterRelSym(
550 SymbolKind Kind, DefRangeRegisterRelSym &DefRangeRegisterRel) {
551 DictScope S(W, "DefRangeRegisterRel");
552
553 W.printNumber("BaseRegister", DefRangeRegisterRel.Header.BaseRegister);
554 W.printBoolean("HasSpilledUDTMember",
555 DefRangeRegisterRel.hasSpilledUDTMember());
556 W.printNumber("OffsetInParent", DefRangeRegisterRel.offsetInParent());
557 W.printNumber("BasePointerOffset",
558 DefRangeRegisterRel.Header.BasePointerOffset);
559 printLocalVariableAddrRange(DefRangeRegisterRel.Header.Range,
560 DefRangeRegisterRel.getRelocationOffset());
561 printLocalVariableAddrGap(DefRangeRegisterRel.Gaps);
562}
563
564void CVSymbolDumperImpl::visitDefRangeRegisterSym(
565 SymbolKind Kind, DefRangeRegisterSym &DefRangeRegister) {
566 DictScope S(W, "DefRangeRegister");
567
568 W.printNumber("Register", DefRangeRegister.Header.Register);
569 W.printNumber("MayHaveNoName", DefRangeRegister.Header.MayHaveNoName);
570 printLocalVariableAddrRange(DefRangeRegister.Header.Range,
571 DefRangeRegister.getRelocationOffset());
572 printLocalVariableAddrGap(DefRangeRegister.Gaps);
573}
574
575void CVSymbolDumperImpl::visitDefRangeSubfieldRegisterSym(
576 SymbolKind Kind, DefRangeSubfieldRegisterSym &DefRangeSubfieldRegister) {
577 DictScope S(W, "DefRangeSubfieldRegister");
578
579 W.printNumber("Register", DefRangeSubfieldRegister.Header.Register);
580 W.printNumber("MayHaveNoName", DefRangeSubfieldRegister.Header.MayHaveNoName);
581 W.printNumber("OffsetInParent",
582 DefRangeSubfieldRegister.Header.OffsetInParent);
583 printLocalVariableAddrRange(DefRangeSubfieldRegister.Header.Range,
584 DefRangeSubfieldRegister.getRelocationOffset());
585 printLocalVariableAddrGap(DefRangeSubfieldRegister.Gaps);
586}
587
588void CVSymbolDumperImpl::visitDefRangeSubfieldSym(
589 SymbolKind Kind, DefRangeSubfieldSym &DefRangeSubfield) {
590 DictScope S(W, "DefRangeSubfield");
591
592 if (ObjDelegate) {
593 StringRef StringTable = ObjDelegate->getStringTable();
594 if (!StringTable.empty()) {
595 W.printString("Program",
596 StringTable.drop_front(DefRangeSubfield.Header.Program)
597 .split('\0')
598 .first);
599 }
600 }
601 W.printNumber("OffsetInParent", DefRangeSubfield.Header.OffsetInParent);
602 printLocalVariableAddrRange(DefRangeSubfield.Header.Range,
603 DefRangeSubfield.getRelocationOffset());
604 printLocalVariableAddrGap(DefRangeSubfield.Gaps);
605}
606
607void CVSymbolDumperImpl::visitDefRangeSym(SymbolKind Kind,
608 DefRangeSym &DefRange) {
609 DictScope S(W, "DefRange");
610
611 if (ObjDelegate) {
612 StringRef StringTable = ObjDelegate->getStringTable();
David Majnemerb3433102016-05-28 19:45:56 +0000613 auto ProgramStringTableOffset = DefRange.Header.Program;
614 if (ProgramStringTableOffset >= StringTable.size())
615 return parseError();
616 StringRef Program =
617 StringTable.drop_front(ProgramStringTableOffset).split('\0').first;
618 W.printString("Program", Program);
Zachary Turneraaad5742016-05-23 23:41:13 +0000619 }
620 printLocalVariableAddrRange(DefRange.Header.Range,
621 DefRange.getRelocationOffset());
622 printLocalVariableAddrGap(DefRange.Gaps);
623}
624
625void CVSymbolDumperImpl::visitFrameCookieSym(SymbolKind Kind,
626 FrameCookieSym &FrameCookie) {
627 DictScope S(W, "FrameCookie");
628
629 StringRef LinkageName;
630 if (ObjDelegate) {
631 ObjDelegate->printRelocatedField(
632 "CodeOffset", FrameCookie.getRelocationOffset(),
633 FrameCookie.Header.CodeOffset, &LinkageName);
634 }
635 W.printHex("Register", FrameCookie.Header.Register);
636 W.printEnum("CookieKind", uint16_t(FrameCookie.Header.CookieKind),
637 makeArrayRef(FrameCookieKinds));
638}
639
640void CVSymbolDumperImpl::visitFrameProcSym(SymbolKind Kind,
641 FrameProcSym &FrameProc) {
642 DictScope S(W, "FrameProc");
643
644 W.printHex("TotalFrameBytes", FrameProc.Header.TotalFrameBytes);
645 W.printHex("PaddingFrameBytes", FrameProc.Header.PaddingFrameBytes);
646 W.printHex("OffsetToPadding", FrameProc.Header.OffsetToPadding);
647 W.printHex("BytesOfCalleeSavedRegisters",
648 FrameProc.Header.BytesOfCalleeSavedRegisters);
649 W.printHex("OffsetOfExceptionHandler",
650 FrameProc.Header.OffsetOfExceptionHandler);
651 W.printHex("SectionIdOfExceptionHandler",
652 FrameProc.Header.SectionIdOfExceptionHandler);
653 W.printFlags("Flags", FrameProc.Header.Flags,
654 makeArrayRef(FrameProcSymFlags));
655}
656
657void CVSymbolDumperImpl::visitHeapAllocationSiteSym(
658 SymbolKind Kind, HeapAllocationSiteSym &HeapAllocSite) {
659 DictScope S(W, "HeapAllocationSite");
660
661 StringRef LinkageName;
662 if (ObjDelegate) {
663 ObjDelegate->printRelocatedField(
664 "CodeOffset", HeapAllocSite.getRelocationOffset(),
665 HeapAllocSite.Header.CodeOffset, &LinkageName);
666 }
667 W.printHex("Segment", HeapAllocSite.Header.Segment);
668 W.printHex("CallInstructionSize", HeapAllocSite.Header.CallInstructionSize);
669 CVTD.printTypeIndex("Type", HeapAllocSite.Header.Type);
670 if (!LinkageName.empty())
671 W.printString("LinkageName", LinkageName);
672}
673
674void CVSymbolDumperImpl::visitInlineSiteSym(SymbolKind Kind,
675 InlineSiteSym &InlineSite) {
676 DictScope S(W, "InlineSite");
677
678 W.printHex("PtrParent", InlineSite.Header.PtrParent);
679 W.printHex("PtrEnd", InlineSite.Header.PtrEnd);
680 CVTD.printTypeIndex("Inlinee", InlineSite.Header.Inlinee);
681
682 ListScope BinaryAnnotations(W, "BinaryAnnotations");
683 for (auto &Annotation : InlineSite.annotations()) {
684 switch (Annotation.OpCode) {
685 case BinaryAnnotationsOpCode::Invalid:
686 return parseError();
687 case BinaryAnnotationsOpCode::CodeOffset:
688 case BinaryAnnotationsOpCode::ChangeCodeOffset:
689 case BinaryAnnotationsOpCode::ChangeCodeLength:
690 W.printHex(Annotation.Name, Annotation.U1);
691 break;
692 case BinaryAnnotationsOpCode::ChangeCodeOffsetBase:
693 case BinaryAnnotationsOpCode::ChangeLineEndDelta:
694 case BinaryAnnotationsOpCode::ChangeRangeKind:
695 case BinaryAnnotationsOpCode::ChangeColumnStart:
696 case BinaryAnnotationsOpCode::ChangeColumnEnd:
697 W.printNumber(Annotation.Name, Annotation.U1);
698 break;
699 case BinaryAnnotationsOpCode::ChangeLineOffset:
700 case BinaryAnnotationsOpCode::ChangeColumnEndDelta:
701 W.printNumber(Annotation.Name, Annotation.S1);
702 break;
703 case BinaryAnnotationsOpCode::ChangeFile:
704 if (ObjDelegate) {
705 W.printHex("ChangeFile",
706 ObjDelegate->getFileNameForFileOffset(Annotation.U1),
707 Annotation.U1);
708 } else {
709 W.printHex("ChangeFile", Annotation.U1);
710 }
711
712 break;
713 case BinaryAnnotationsOpCode::ChangeCodeOffsetAndLineOffset: {
714 W.startLine() << "ChangeCodeOffsetAndLineOffset: {CodeOffset: "
715 << W.hex(Annotation.U1) << ", LineOffset: " << Annotation.S1
716 << "}\n";
717 break;
718 }
719 case BinaryAnnotationsOpCode::ChangeCodeLengthAndCodeOffset: {
720 W.startLine() << "ChangeCodeLengthAndCodeOffset: {CodeOffset: "
721 << W.hex(Annotation.U2)
722 << ", Length: " << W.hex(Annotation.U1) << "}\n";
723 break;
724 }
725 }
726 }
727}
728
Zachary Turner4caa1bf2016-05-24 22:58:46 +0000729void CVSymbolDumperImpl::visitRegisterSym(SymbolKind Kind,
730 RegisterSym &Register) {
731 DictScope S(W, "RegisterSym");
732 W.printNumber("Type", Register.Header.Index);
733 W.printEnum("Seg", uint16_t(Register.Header.Register),
734 makeArrayRef(RegisterNames));
735 W.printString("Name", Register.Name);
736}
737
Zachary Turner9e33e6f2016-05-24 18:55:14 +0000738void CVSymbolDumperImpl::visitPublicSym32(SymbolKind Kind,
739 PublicSym32 &Public) {
740 DictScope S(W, "PublicSym");
741 W.printNumber("Type", Public.Header.Index);
742 W.printNumber("Seg", Public.Header.Seg);
743 W.printNumber("Off", Public.Header.Off);
744 W.printString("Name", Public.Name);
745}
746
747void CVSymbolDumperImpl::visitProcRefSym(SymbolKind Kind, ProcRefSym &ProcRef) {
748 DictScope S(W, "ProcRef");
749 W.printNumber("SumName", ProcRef.Header.SumName);
750 W.printNumber("SymOffset", ProcRef.Header.SymOffset);
751 W.printNumber("Mod", ProcRef.Header.Mod);
752 W.printString("Name", ProcRef.Name);
753}
754
Zachary Turneraaad5742016-05-23 23:41:13 +0000755void CVSymbolDumperImpl::visitLabelSym(SymbolKind Kind, LabelSym &Label) {
756 DictScope S(W, "Label");
757
758 StringRef LinkageName;
759 if (ObjDelegate) {
760 ObjDelegate->printRelocatedField("CodeOffset", Label.getRelocationOffset(),
761 Label.Header.CodeOffset, &LinkageName);
762 }
763 W.printHex("Segment", Label.Header.Segment);
764 W.printHex("Flags", Label.Header.Flags);
765 W.printFlags("Flags", Label.Header.Flags, makeArrayRef(ProcSymFlagNames));
766 W.printString("DisplayName", Label.Name);
767 if (!LinkageName.empty())
768 W.printString("LinkageName", LinkageName);
769}
770
771void CVSymbolDumperImpl::visitLocalSym(SymbolKind Kind, LocalSym &Local) {
772 DictScope S(W, "Local");
773
774 CVTD.printTypeIndex("Type", Local.Header.Type);
775 W.printFlags("Flags", uint16_t(Local.Header.Flags), makeArrayRef(LocalFlags));
776 W.printString("VarName", Local.Name);
777}
778
779void CVSymbolDumperImpl::visitObjNameSym(SymbolKind Kind, ObjNameSym &ObjName) {
780 DictScope S(W, "ObjectName");
781
782 W.printHex("Signature", ObjName.Header.Signature);
783 W.printString("ObjectName", ObjName.Name);
784}
785
786void CVSymbolDumperImpl::visitProcSym(SymbolKind Kind, ProcSym &Proc) {
787 DictScope S(W, "ProcStart");
788
789 if (InFunctionScope)
790 return parseError();
791
792 InFunctionScope = true;
793
794 StringRef LinkageName;
795 W.printHex("PtrParent", Proc.Header.PtrParent);
796 W.printHex("PtrEnd", Proc.Header.PtrEnd);
797 W.printHex("PtrNext", Proc.Header.PtrNext);
798 W.printHex("CodeSize", Proc.Header.CodeSize);
799 W.printHex("DbgStart", Proc.Header.DbgStart);
800 W.printHex("DbgEnd", Proc.Header.DbgEnd);
801 CVTD.printTypeIndex("FunctionType", Proc.Header.FunctionType);
802 if (ObjDelegate) {
803 ObjDelegate->printRelocatedField("CodeOffset", Proc.getRelocationOffset(),
804 Proc.Header.CodeOffset, &LinkageName);
805 }
806 W.printHex("Segment", Proc.Header.Segment);
807 W.printFlags("Flags", static_cast<uint8_t>(Proc.Header.Flags),
808 makeArrayRef(ProcSymFlagNames));
809 W.printString("DisplayName", Proc.Name);
810 if (!LinkageName.empty())
811 W.printString("LinkageName", LinkageName);
812}
813
814void CVSymbolDumperImpl::visitScopeEndSym(SymbolKind Kind,
815 ScopeEndSym &ScopeEnd) {
816 if (Kind == SymbolKind::S_END)
Zachary Turnercac29ae2016-05-24 17:30:25 +0000817 DictScope S(W, "BlockEnd");
Zachary Turneraaad5742016-05-23 23:41:13 +0000818 else if (Kind == SymbolKind::S_PROC_ID_END)
Zachary Turnercac29ae2016-05-24 17:30:25 +0000819 DictScope S(W, "ProcEnd");
Zachary Turneraaad5742016-05-23 23:41:13 +0000820 else if (Kind == SymbolKind::S_INLINESITE_END)
821 DictScope S(W, "InlineSiteEnd");
822
823 InFunctionScope = false;
824}
825
826void CVSymbolDumperImpl::visitCallerSym(SymbolKind Kind, CallerSym &Caller) {
827 ListScope S(W, Kind == S_CALLEES ? "Callees" : "Callers");
828 for (auto FuncID : Caller.Indices)
829 CVTD.printTypeIndex("FuncID", FuncID);
830}
831
832void CVSymbolDumperImpl::visitRegRelativeSym(SymbolKind Kind,
833 RegRelativeSym &RegRel) {
834 DictScope S(W, "RegRelativeSym");
835
836 W.printHex("Offset", RegRel.Header.Offset);
837 CVTD.printTypeIndex("Type", RegRel.Header.Type);
838 W.printHex("Register", RegRel.Header.Register);
839 W.printString("VarName", RegRel.Name);
840}
841
842void CVSymbolDumperImpl::visitThreadLocalDataSym(SymbolKind Kind,
843 ThreadLocalDataSym &Data) {
844 DictScope S(W, "ThreadLocalDataSym");
845
846 StringRef LinkageName;
847 if (ObjDelegate) {
848 ObjDelegate->printRelocatedField("DataOffset", Data.getRelocationOffset(),
849 Data.Header.DataOffset, &LinkageName);
850 }
851 CVTD.printTypeIndex("Type", Data.Header.Type);
852 W.printString("DisplayName", Data.Name);
853 if (!LinkageName.empty())
854 W.printString("LinkageName", LinkageName);
855}
856
857void CVSymbolDumperImpl::visitUDTSym(SymbolKind Kind, UDTSym &UDT) {
858 DictScope S(W, "UDT");
859 CVTD.printTypeIndex("Type", UDT.Header.Type);
860 W.printString("UDTName", UDT.Name);
861}
862
863void CVSymbolDumperImpl::visitUnknownSymbol(SymbolKind Kind,
864 ArrayRef<uint8_t> Data) {
865 DictScope S(W, "UnknownSym");
Zachary Turner00d847b2016-05-24 17:44:29 +0000866 W.printEnum("Kind", uint16_t(Kind), makeArrayRef(SymbolTypeNames));
867 W.printNumber("Length", uint32_t(Data.size()));
Zachary Turneraaad5742016-05-23 23:41:13 +0000868}
869
Zachary Turner1de49c92016-05-27 18:47:20 +0000870bool CVSymbolDumper::dump(const CVRecord<SymbolKind> &Record) {
Zachary Turner3e78e2d2016-05-24 00:06:04 +0000871 CVSymbolDumperImpl Dumper(CVTD, ObjDelegate.get(), W, PrintRecordBytes);
Zachary Turneraaad5742016-05-23 23:41:13 +0000872 Dumper.visitSymbolRecord(Record);
873 return !Dumper.hadError();
874}
875
Zachary Turner0d43c1c2016-05-28 05:21:57 +0000876bool CVSymbolDumper::dump(const CVSymbolArray &Symbols) {
Zachary Turner3e78e2d2016-05-24 00:06:04 +0000877 CVSymbolDumperImpl Dumper(CVTD, ObjDelegate.get(), W, PrintRecordBytes);
Zachary Turner0d43c1c2016-05-28 05:21:57 +0000878 Dumper.visitSymbolStream(Symbols);
Zachary Turneraaad5742016-05-23 23:41:13 +0000879 return !Dumper.hadError();
880}