Skip to content

Commit ac3851c

Browse files
committed
Improving CodeView debug info type record's inline comments
llvm-svn: 369533
1 parent 78347c9 commit ac3851c

File tree

9 files changed

+636
-192
lines changed

9 files changed

+636
-192
lines changed

llvm/include/llvm/DebugInfo/CodeView/CodeViewRecordIO.h

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,9 @@ class CodeViewRecordStreamer {
3333
virtual void EmitIntValue(uint64_t Value, unsigned Size) = 0;
3434
virtual void EmitBinaryData(StringRef Data) = 0;
3535
virtual void AddComment(const Twine &T) = 0;
36+
virtual void AddRawComment(const Twine &T) = 0;
37+
virtual bool isVerboseAsm() = 0;
38+
virtual std::string getTypeName(TypeIndex TI) = 0;
3639
virtual ~CodeViewRecordStreamer() = default;
3740
};
3841

@@ -206,6 +209,11 @@ class CodeViewRecordIO {
206209
return 0;
207210
}
208211

212+
void emitRawComment(const Twine &T) {
213+
if (isStreaming() && Streamer->isVerboseAsm())
214+
Streamer->AddRawComment(T);
215+
}
216+
209217
private:
210218
void emitEncodedSignedInteger(const int64_t &Value,
211219
const Twine &Comment = "");
@@ -225,7 +233,7 @@ class CodeViewRecordIO {
225233
}
226234

227235
void emitComment(const Twine &Comment) {
228-
if (isStreaming()) {
236+
if (isStreaming() && Streamer->isVerboseAsm()) {
229237
Twine TComment(Comment);
230238
if (!TComment.isTriviallyEmpty())
231239
Streamer->AddComment(TComment);

llvm/include/llvm/DebugInfo/CodeView/EnumTables.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,17 @@ ArrayRef<EnumEntry<uint8_t>> getThunkOrdinalNames();
3737
ArrayRef<EnumEntry<uint16_t>> getTrampolineNames();
3838
ArrayRef<EnumEntry<COFF::SectionCharacteristics>>
3939
getImageSectionCharacteristicNames();
40+
ArrayRef<EnumEntry<uint16_t>> getClassOptionNames();
41+
ArrayRef<EnumEntry<uint8_t>> getMemberAccessNames();
42+
ArrayRef<EnumEntry<uint16_t>> getMethodOptionNames();
43+
ArrayRef<EnumEntry<uint16_t>> getMemberKindNames();
44+
ArrayRef<EnumEntry<uint8_t>> getPtrKindNames();
45+
ArrayRef<EnumEntry<uint8_t>> getPtrModeNames();
46+
ArrayRef<EnumEntry<uint16_t>> getPtrMemberRepNames();
47+
ArrayRef<EnumEntry<uint16_t>> getTypeModifierNames();
48+
ArrayRef<EnumEntry<uint8_t>> getCallingConventions();
49+
ArrayRef<EnumEntry<uint8_t>> getFunctionOptionEnum();
50+
ArrayRef<EnumEntry<uint16_t>> getLabelTypeEnum();
4051

4152
} // end namespace codeview
4253
} // end namespace llvm

llvm/lib/CodeGen/AsmPrinter/CodeViewDebug.cpp

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,8 @@ using namespace llvm::codeview;
9898
namespace {
9999
class CVMCAdapter : public CodeViewRecordStreamer {
100100
public:
101-
CVMCAdapter(MCStreamer &OS) : OS(&OS) {}
101+
CVMCAdapter(MCStreamer &OS, TypeCollection &TypeTable)
102+
: OS(&OS), TypeTable(TypeTable) {}
102103

103104
void EmitBytes(StringRef Data) { OS->EmitBytes(Data); }
104105

@@ -110,8 +111,24 @@ class CVMCAdapter : public CodeViewRecordStreamer {
110111

111112
void AddComment(const Twine &T) { OS->AddComment(T); }
112113

114+
void AddRawComment(const Twine &T) { OS->emitRawComment(T); }
115+
116+
bool isVerboseAsm() { return OS->isVerboseAsm(); }
117+
118+
std::string getTypeName(TypeIndex TI) {
119+
std::string TypeName;
120+
if (!TI.isNoneType()) {
121+
if (TI.isSimple())
122+
TypeName = TypeIndex::simpleTypeName(TI);
123+
else
124+
TypeName = TypeTable.getTypeName(TI);
125+
}
126+
return TypeName;
127+
}
128+
113129
private:
114130
MCStreamer *OS = nullptr;
131+
TypeCollection &TypeTable;
115132
};
116133
} // namespace
117134

@@ -617,13 +634,6 @@ emitNullTerminatedSymbolName(MCStreamer &OS, StringRef S,
617634
OS.EmitBytes(NullTerminatedString);
618635
}
619636

620-
static StringRef getTypeLeafName(TypeLeafKind TypeKind) {
621-
for (const EnumEntry<TypeLeafKind> &EE : getTypeLeafNames())
622-
if (EE.Value == TypeKind)
623-
return EE.Name;
624-
return "";
625-
}
626-
627637
void CodeViewDebug::emitTypeInformation() {
628638
if (TypeTable.empty())
629639
return;
@@ -640,11 +650,11 @@ void CodeViewDebug::emitTypeInformation() {
640650
}
641651

642652
TypeTableCollection Table(TypeTable.records());
653+
TypeVisitorCallbackPipeline Pipeline;
643654
SmallString<512> CommentBlock;
644655
raw_svector_ostream CommentOS(CommentBlock);
645656
std::unique_ptr<ScopedPrinter> SP;
646657
std::unique_ptr<TypeDumpVisitor> TDV;
647-
TypeVisitorCallbackPipeline Pipeline;
648658

649659
if (OS.isVerboseAsm()) {
650660
// To construct block comment describing the type record for readability.
@@ -655,7 +665,7 @@ void CodeViewDebug::emitTypeInformation() {
655665
}
656666

657667
// To emit type record using Codeview MCStreamer adapter
658-
CVMCAdapter CVMCOS(OS);
668+
CVMCAdapter CVMCOS(OS, Table);
659669
TypeRecordMapping typeMapping(CVMCOS);
660670
Pipeline.addCallbackToPipeline(typeMapping);
661671

@@ -665,16 +675,6 @@ void CodeViewDebug::emitTypeInformation() {
665675
CVType Record = Table.getType(*B);
666676

667677
CommentBlock.clear();
668-
669-
auto RecordLen = Record.length();
670-
auto RecordKind = Record.kind();
671-
if (OS.isVerboseAsm())
672-
CVMCOS.AddComment("Record length");
673-
CVMCOS.EmitIntValue(RecordLen - 2, 2);
674-
if (OS.isVerboseAsm())
675-
CVMCOS.AddComment("Record kind: " + getTypeLeafName(RecordKind));
676-
CVMCOS.EmitIntValue(RecordKind, sizeof(RecordKind));
677-
678678
Error E = codeview::visitTypeRecord(Record, *B, Pipeline);
679679

680680
if (E) {

llvm/lib/DebugInfo/CodeView/CodeViewRecordIO.cpp

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,11 @@ Error CodeViewRecordIO::mapByteVectorTail(std::vector<uint8_t> &Bytes,
126126

127127
Error CodeViewRecordIO::mapInteger(TypeIndex &TypeInd, const Twine &Comment) {
128128
if (isStreaming()) {
129-
emitComment(Comment);
129+
std::string TypeNameStr = Streamer->getTypeName(TypeInd);
130+
if (!TypeNameStr.empty())
131+
emitComment(Comment + ": " + TypeNameStr);
132+
else
133+
emitComment(Comment);
130134
Streamer->EmitIntValue(TypeInd.getIndex(), sizeof(TypeInd.getIndex()));
131135
incrStreamedLen(sizeof(TypeInd.getIndex()));
132136
} else if (isWriting()) {

llvm/lib/DebugInfo/CodeView/EnumTables.cpp

Lines changed: 166 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -300,6 +300,128 @@ static const EnumEntry<COFF::SectionCharacteristics>
300300
CV_ENUM_ENT(COFF, IMAGE_SCN_MEM_READ),
301301
CV_ENUM_ENT(COFF, IMAGE_SCN_MEM_WRITE)};
302302

303+
static const EnumEntry<uint16_t> ClassOptionNames[] = {
304+
CV_ENUM_CLASS_ENT(ClassOptions, Packed),
305+
CV_ENUM_CLASS_ENT(ClassOptions, HasConstructorOrDestructor),
306+
CV_ENUM_CLASS_ENT(ClassOptions, HasOverloadedOperator),
307+
CV_ENUM_CLASS_ENT(ClassOptions, Nested),
308+
CV_ENUM_CLASS_ENT(ClassOptions, ContainsNestedClass),
309+
CV_ENUM_CLASS_ENT(ClassOptions, HasOverloadedAssignmentOperator),
310+
CV_ENUM_CLASS_ENT(ClassOptions, HasConversionOperator),
311+
CV_ENUM_CLASS_ENT(ClassOptions, ForwardReference),
312+
CV_ENUM_CLASS_ENT(ClassOptions, Scoped),
313+
CV_ENUM_CLASS_ENT(ClassOptions, HasUniqueName),
314+
CV_ENUM_CLASS_ENT(ClassOptions, Sealed),
315+
CV_ENUM_CLASS_ENT(ClassOptions, Intrinsic),
316+
};
317+
318+
static const EnumEntry<uint8_t> MemberAccessNames[] = {
319+
CV_ENUM_CLASS_ENT(MemberAccess, None),
320+
CV_ENUM_CLASS_ENT(MemberAccess, Private),
321+
CV_ENUM_CLASS_ENT(MemberAccess, Protected),
322+
CV_ENUM_CLASS_ENT(MemberAccess, Public),
323+
};
324+
325+
static const EnumEntry<uint16_t> MethodOptionNames[] = {
326+
CV_ENUM_CLASS_ENT(MethodOptions, Pseudo),
327+
CV_ENUM_CLASS_ENT(MethodOptions, NoInherit),
328+
CV_ENUM_CLASS_ENT(MethodOptions, NoConstruct),
329+
CV_ENUM_CLASS_ENT(MethodOptions, CompilerGenerated),
330+
CV_ENUM_CLASS_ENT(MethodOptions, Sealed),
331+
};
332+
333+
static const EnumEntry<uint16_t> MemberKindNames[] = {
334+
CV_ENUM_CLASS_ENT(MethodKind, Vanilla),
335+
CV_ENUM_CLASS_ENT(MethodKind, Virtual),
336+
CV_ENUM_CLASS_ENT(MethodKind, Static),
337+
CV_ENUM_CLASS_ENT(MethodKind, Friend),
338+
CV_ENUM_CLASS_ENT(MethodKind, IntroducingVirtual),
339+
CV_ENUM_CLASS_ENT(MethodKind, PureVirtual),
340+
CV_ENUM_CLASS_ENT(MethodKind, PureIntroducingVirtual),
341+
};
342+
343+
static const EnumEntry<uint8_t> PtrKindNames[] = {
344+
CV_ENUM_CLASS_ENT(PointerKind, Near16),
345+
CV_ENUM_CLASS_ENT(PointerKind, Far16),
346+
CV_ENUM_CLASS_ENT(PointerKind, Huge16),
347+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnSegment),
348+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnValue),
349+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnSegmentValue),
350+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnAddress),
351+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnSegmentAddress),
352+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnType),
353+
CV_ENUM_CLASS_ENT(PointerKind, BasedOnSelf),
354+
CV_ENUM_CLASS_ENT(PointerKind, Near32),
355+
CV_ENUM_CLASS_ENT(PointerKind, Far32),
356+
CV_ENUM_CLASS_ENT(PointerKind, Near64),
357+
};
358+
359+
static const EnumEntry<uint8_t> PtrModeNames[] = {
360+
CV_ENUM_CLASS_ENT(PointerMode, Pointer),
361+
CV_ENUM_CLASS_ENT(PointerMode, LValueReference),
362+
CV_ENUM_CLASS_ENT(PointerMode, PointerToDataMember),
363+
CV_ENUM_CLASS_ENT(PointerMode, PointerToMemberFunction),
364+
CV_ENUM_CLASS_ENT(PointerMode, RValueReference),
365+
};
366+
367+
static const EnumEntry<uint16_t> PtrMemberRepNames[] = {
368+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, Unknown),
369+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, SingleInheritanceData),
370+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, MultipleInheritanceData),
371+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, VirtualInheritanceData),
372+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, GeneralData),
373+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, SingleInheritanceFunction),
374+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation,
375+
MultipleInheritanceFunction),
376+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation,
377+
VirtualInheritanceFunction),
378+
CV_ENUM_CLASS_ENT(PointerToMemberRepresentation, GeneralFunction),
379+
};
380+
381+
static const EnumEntry<uint16_t> TypeModifierNames[] = {
382+
CV_ENUM_CLASS_ENT(ModifierOptions, Const),
383+
CV_ENUM_CLASS_ENT(ModifierOptions, Volatile),
384+
CV_ENUM_CLASS_ENT(ModifierOptions, Unaligned),
385+
};
386+
387+
static const EnumEntry<uint8_t> CallingConventions[] = {
388+
CV_ENUM_CLASS_ENT(CallingConvention, NearC),
389+
CV_ENUM_CLASS_ENT(CallingConvention, FarC),
390+
CV_ENUM_CLASS_ENT(CallingConvention, NearPascal),
391+
CV_ENUM_CLASS_ENT(CallingConvention, FarPascal),
392+
CV_ENUM_CLASS_ENT(CallingConvention, NearFast),
393+
CV_ENUM_CLASS_ENT(CallingConvention, FarFast),
394+
CV_ENUM_CLASS_ENT(CallingConvention, NearStdCall),
395+
CV_ENUM_CLASS_ENT(CallingConvention, FarStdCall),
396+
CV_ENUM_CLASS_ENT(CallingConvention, NearSysCall),
397+
CV_ENUM_CLASS_ENT(CallingConvention, FarSysCall),
398+
CV_ENUM_CLASS_ENT(CallingConvention, ThisCall),
399+
CV_ENUM_CLASS_ENT(CallingConvention, MipsCall),
400+
CV_ENUM_CLASS_ENT(CallingConvention, Generic),
401+
CV_ENUM_CLASS_ENT(CallingConvention, AlphaCall),
402+
CV_ENUM_CLASS_ENT(CallingConvention, PpcCall),
403+
CV_ENUM_CLASS_ENT(CallingConvention, SHCall),
404+
CV_ENUM_CLASS_ENT(CallingConvention, ArmCall),
405+
CV_ENUM_CLASS_ENT(CallingConvention, AM33Call),
406+
CV_ENUM_CLASS_ENT(CallingConvention, TriCall),
407+
CV_ENUM_CLASS_ENT(CallingConvention, SH5Call),
408+
CV_ENUM_CLASS_ENT(CallingConvention, M32RCall),
409+
CV_ENUM_CLASS_ENT(CallingConvention, ClrCall),
410+
CV_ENUM_CLASS_ENT(CallingConvention, Inline),
411+
CV_ENUM_CLASS_ENT(CallingConvention, NearVector),
412+
};
413+
414+
static const EnumEntry<uint8_t> FunctionOptionEnum[] = {
415+
CV_ENUM_CLASS_ENT(FunctionOptions, CxxReturnUdt),
416+
CV_ENUM_CLASS_ENT(FunctionOptions, Constructor),
417+
CV_ENUM_CLASS_ENT(FunctionOptions, ConstructorWithVirtualBases),
418+
};
419+
420+
static const EnumEntry<uint16_t> LabelTypeEnum[] = {
421+
CV_ENUM_CLASS_ENT(LabelType, Near),
422+
CV_ENUM_CLASS_ENT(LabelType, Far),
423+
};
424+
303425
namespace llvm {
304426
namespace codeview {
305427

@@ -379,5 +501,49 @@ getImageSectionCharacteristicNames() {
379501
return makeArrayRef(ImageSectionCharacteristicNames);
380502
}
381503

504+
ArrayRef<EnumEntry<uint16_t>> getClassOptionNames() {
505+
return makeArrayRef(ClassOptionNames);
506+
}
507+
508+
ArrayRef<EnumEntry<uint8_t>> getMemberAccessNames() {
509+
return makeArrayRef(MemberAccessNames);
510+
}
511+
512+
ArrayRef<EnumEntry<uint16_t>> getMethodOptionNames() {
513+
return makeArrayRef(MethodOptionNames);
514+
}
515+
516+
ArrayRef<EnumEntry<uint16_t>> getMemberKindNames() {
517+
return makeArrayRef(MemberKindNames);
518+
}
519+
520+
ArrayRef<EnumEntry<uint8_t>> getPtrKindNames() {
521+
return makeArrayRef(PtrKindNames);
522+
}
523+
524+
ArrayRef<EnumEntry<uint8_t>> getPtrModeNames() {
525+
return makeArrayRef(PtrModeNames);
526+
}
527+
528+
ArrayRef<EnumEntry<uint16_t>> getPtrMemberRepNames() {
529+
return makeArrayRef(PtrMemberRepNames);
530+
}
531+
532+
ArrayRef<EnumEntry<uint16_t>> getTypeModifierNames() {
533+
return makeArrayRef(TypeModifierNames);
534+
}
535+
536+
ArrayRef<EnumEntry<uint8_t>> getCallingConventions() {
537+
return makeArrayRef(CallingConventions);
538+
}
539+
540+
ArrayRef<EnumEntry<uint8_t>> getFunctionOptionEnum() {
541+
return makeArrayRef(FunctionOptionEnum);
542+
}
543+
544+
ArrayRef<EnumEntry<uint16_t>> getLabelTypeEnum() {
545+
return makeArrayRef(LabelTypeEnum);
546+
}
547+
382548
} // end namespace codeview
383549
} // end namespace llvm

0 commit comments

Comments
 (0)