LLVM 20.0.0git
LVCodeViewVisitor.cpp
Go to the documentation of this file.
1//===-- LVCodeViewVisitor.cpp ---------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This implements the LVCodeViewVisitor class.
10//
11//===----------------------------------------------------------------------===//
12
29#include "llvm/Object/COFF.h"
30#include "llvm/Support/Error.h"
33
34using namespace llvm;
35using namespace llvm::codeview;
36using namespace llvm::object;
37using namespace llvm::pdb;
38using namespace llvm::logicalview;
39
40#define DEBUG_TYPE "CodeViewUtilities"
41
42namespace llvm {
43namespace logicalview {
44
46 // Dealing with a MSVC generated PDB, we encountered a type index with the
47 // value of: 0x0280xxxx where xxxx=0000.
48 //
49 // There is some documentation about type indices:
50 // https://llvm.org/docs/PDB/TpiStream.html
51 //
52 // A type index is a 32-bit integer that uniquely identifies a type inside
53 // of an object file’s .debug$T section or a PDB file’s TPI or IPI stream.
54 // The value of the type index for the first type record from the TPI stream
55 // is given by the TypeIndexBegin member of the TPI Stream Header although
56 // in practice this value is always equal to 0x1000 (4096).
57 //
58 // Any type index with a high bit set is considered to come from the IPI
59 // stream, although this appears to be more of a hack, and LLVM does not
60 // generate type indices of this nature. They can, however, be observed in
61 // Microsoft PDBs occasionally, so one should be prepared to handle them.
62 // Note that having the high bit set is not a necessary condition to
63 // determine whether a type index comes from the IPI stream, it is only
64 // sufficient.
66 { dbgs() << "Index before: " << HexNumber(TI.getIndex()) << "\n"; });
67 TI.setIndex(TI.getIndex() & 0x0000ffff);
69 { dbgs() << "Index after: " << HexNumber(TI.getIndex()) << "\n"; });
70 return TI;
71}
72
74#define CV_TYPE(enum, val) {#enum, enum},
75#include "llvm/DebugInfo/CodeView/CodeViewTypes.def"
76};
77
78// Return the type name pointed by the type index. It uses the kind to query
79// the associated name for the record type.
81 if (TI.isSimple())
82 return {};
83
84 StringRef RecordName;
85 CVType CVReference = Types.getType(TI);
86 auto GetName = [&](auto Record) {
88 const_cast<CVType &>(CVReference), Record))
89 consumeError(std::move(Err));
90 else
91 RecordName = Record.getName();
92 };
93
94 TypeRecordKind RK = static_cast<TypeRecordKind>(CVReference.kind());
95 if (RK == TypeRecordKind::Class || RK == TypeRecordKind::Struct)
96 GetName(ClassRecord(RK));
97 else if (RK == TypeRecordKind::Union)
98 GetName(UnionRecord(RK));
99 else if (RK == TypeRecordKind::Enum)
100 GetName(EnumRecord(RK));
101
102 return RecordName;
103}
104
105} // namespace logicalview
106} // namespace llvm
107
108#undef DEBUG_TYPE
109#define DEBUG_TYPE "CodeViewDataVisitor"
110
111namespace llvm {
112namespace logicalview {
113
114// Keeps the type indexes with line information.
115using LVLineRecords = std::vector<TypeIndex>;
116
117namespace {
118
119class LVTypeRecords {
120 LVShared *Shared = nullptr;
121
122 // Logical elements associated to their CodeView Type Index.
123 using RecordEntry = std::pair<TypeLeafKind, LVElement *>;
124 using RecordTable = std::map<TypeIndex, RecordEntry>;
125 RecordTable RecordFromTypes;
126 RecordTable RecordFromIds;
127
128 using NameTable = std::map<StringRef, TypeIndex>;
129 NameTable NameFromTypes;
130 NameTable NameFromIds;
131
132public:
133 LVTypeRecords(LVShared *Shared) : Shared(Shared) {}
134
135 void add(uint32_t StreamIdx, TypeIndex TI, TypeLeafKind Kind,
136 LVElement *Element = nullptr);
137 void add(uint32_t StreamIdx, TypeIndex TI, StringRef Name);
138 LVElement *find(uint32_t StreamIdx, TypeIndex TI, bool Create = true);
140};
141
142class LVForwardReferences {
143 // Forward reference and its definitions (Name as key).
144 using ForwardEntry = std::pair<TypeIndex, TypeIndex>;
145 using ForwardTypeNames = std::map<StringRef, ForwardEntry>;
146 ForwardTypeNames ForwardTypesNames;
147
148 // Forward reference and its definition (TypeIndex as key).
149 using ForwardType = std::map<TypeIndex, TypeIndex>;
150 ForwardType ForwardTypes;
151
152 // Forward types and its references.
153 void add(TypeIndex TIForward, TypeIndex TIReference) {
154 ForwardTypes.emplace(TIForward, TIReference);
155 }
156
157 void add(StringRef Name, TypeIndex TIForward) {
158 if (ForwardTypesNames.find(Name) == ForwardTypesNames.end()) {
159 ForwardTypesNames.emplace(
160 std::piecewise_construct, std::forward_as_tuple(Name),
161 std::forward_as_tuple(TIForward, TypeIndex::None()));
162 } else {
163 // Update a recorded definition with its reference.
164 ForwardTypesNames[Name].first = TIForward;
165 add(TIForward, ForwardTypesNames[Name].second);
166 }
167 }
168
169 // Update a previously recorded forward reference with its definition.
170 void update(StringRef Name, TypeIndex TIReference) {
171 auto It = ForwardTypesNames.find(Name);
172 if (It != ForwardTypesNames.end()) {
173 // Update the recorded forward reference with its definition.
174 It->second.second = TIReference;
175 add(It->second.first, TIReference);
176 } else {
177 // We have not seen the forward reference. Insert the definition.
178 ForwardTypesNames.emplace(
179 std::piecewise_construct, std::forward_as_tuple(Name),
180 std::forward_as_tuple(TypeIndex::None(), TIReference));
181 }
182 }
183
184public:
185 LVForwardReferences() = default;
186
187 void record(bool IsForwardRef, StringRef Name, TypeIndex TI) {
188 // We are expecting for the forward references to be first. But that
189 // is not always the case. A name must be recorded regardless of the
190 // order in which the forward reference appears.
191 (IsForwardRef) ? add(Name, TI) : update(Name, TI);
192 }
193
194 TypeIndex find(TypeIndex TIForward) {
195 auto It = ForwardTypes.find(TIForward);
196 return It != ForwardTypes.end() ? It->second : TypeIndex::None();
197 }
198
200 auto It = ForwardTypesNames.find(Name);
201 return It != ForwardTypesNames.end() ? It->second.second
202 : TypeIndex::None();
203 }
204
205 // If the given TI corresponds to a reference, return the reference.
206 // Otherwise return the given TI.
207 TypeIndex remap(TypeIndex TI) {
208 TypeIndex Forward = find(TI);
209 return Forward.isNoneType() ? TI : Forward;
210 }
211};
212
213// Namespace deduction.
214class LVNamespaceDeduction {
215 LVShared *Shared = nullptr;
216
217 using Names = std::map<StringRef, LVScope *>;
218 Names NamespaceNames;
219
220 using LookupSet = std::set<StringRef>;
221 LookupSet DeducedScopes;
222 LookupSet UnresolvedScopes;
223 LookupSet IdentifiedNamespaces;
224
225 void add(StringRef Name, LVScope *Namespace) {
226 if (NamespaceNames.find(Name) == NamespaceNames.end())
227 NamespaceNames.emplace(Name, Namespace);
228 }
229
230public:
231 LVNamespaceDeduction(LVShared *Shared) : Shared(Shared) {}
232
233 void init();
234 void add(StringRef String);
235 LVScope *get(LVStringRefs Components);
236 LVScope *get(StringRef Name, bool CheckScope = true);
237
238 // Find the logical namespace for the 'Name' component.
240 auto It = NamespaceNames.find(Name);
241 LVScope *Namespace = It != NamespaceNames.end() ? It->second : nullptr;
242 return Namespace;
243 }
244
245 // For the given lexical components, return a tuple with the first entry
246 // being the outermost namespace and the second entry being the first
247 // non-namespace.
248 LVLexicalIndex find(LVStringRefs Components) {
249 if (Components.empty())
250 return {};
251
252 LVStringRefs::size_type FirstNamespace = 0;
253 LVStringRefs::size_type FirstNonNamespace;
254 for (LVStringRefs::size_type Index = 0; Index < Components.size();
255 ++Index) {
256 FirstNonNamespace = Index;
257 LookupSet::iterator Iter = IdentifiedNamespaces.find(Components[Index]);
258 if (Iter == IdentifiedNamespaces.end())
259 // The component is not a namespace name.
260 break;
261 }
262 return std::make_tuple(FirstNamespace, FirstNonNamespace);
263 }
264};
265
266// Strings.
267class LVStringRecords {
268 using StringEntry = std::tuple<uint32_t, std::string, LVScopeCompileUnit *>;
269 using StringIds = std::map<TypeIndex, StringEntry>;
270 StringIds Strings;
271
272public:
273 LVStringRecords() = default;
274
275 void add(TypeIndex TI, StringRef String) {
276 static uint32_t Index = 0;
277 if (Strings.find(TI) == Strings.end())
278 Strings.emplace(
279 std::piecewise_construct, std::forward_as_tuple(TI),
280 std::forward_as_tuple(++Index, std::string(String), nullptr));
281 }
282
284 StringIds::iterator Iter = Strings.find(TI);
285 return Iter != Strings.end() ? std::get<1>(Iter->second) : StringRef{};
286 }
287
288 uint32_t findIndex(TypeIndex TI) {
289 StringIds::iterator Iter = Strings.find(TI);
290 return Iter != Strings.end() ? std::get<0>(Iter->second) : 0;
291 }
292
293 // Move strings representing the filenames to the compile unit.
294 void addFilenames();
295 void addFilenames(LVScopeCompileUnit *Scope);
296};
297} // namespace
298
299using LVTypeKinds = std::set<TypeLeafKind>;
300using LVSymbolKinds = std::set<SymbolKind>;
301
302// The following data keeps forward information, type records, names for
303// namespace deduction, strings records, line records.
304// It is shared by the type visitor, symbol visitor and logical visitor and
305// it is independent from the CodeViewReader.
306struct LVShared {
309 LVForwardReferences ForwardReferences;
311 LVNamespaceDeduction NamespaceDeduction;
312 LVStringRecords StringRecords;
313 LVTypeRecords TypeRecords;
314
315 // In order to determine which types and/or symbols records should be handled
316 // by the reader, we record record kinds seen by the type and symbol visitors.
317 // At the end of the scopes creation, the '--internal=tag' option will allow
318 // to print the unique record ids collected.
321
324 TypeRecords(this) {}
325 ~LVShared() = default;
326};
327} // namespace logicalview
328} // namespace llvm
329
330void LVTypeRecords::add(uint32_t StreamIdx, TypeIndex TI, TypeLeafKind Kind,
331 LVElement *Element) {
332 RecordTable &Target =
333 (StreamIdx == StreamTPI) ? RecordFromTypes : RecordFromIds;
334 Target.emplace(std::piecewise_construct, std::forward_as_tuple(TI),
335 std::forward_as_tuple(Kind, Element));
336}
337
338void LVTypeRecords::add(uint32_t StreamIdx, TypeIndex TI, StringRef Name) {
339 NameTable &Target = (StreamIdx == StreamTPI) ? NameFromTypes : NameFromIds;
340 Target.emplace(Name, TI);
341}
342
343LVElement *LVTypeRecords::find(uint32_t StreamIdx, TypeIndex TI, bool Create) {
344 RecordTable &Target =
345 (StreamIdx == StreamTPI) ? RecordFromTypes : RecordFromIds;
346
347 LVElement *Element = nullptr;
348 RecordTable::iterator Iter = Target.find(TI);
349 if (Iter != Target.end()) {
350 Element = Iter->second.second;
351 if (Element || !Create)
352 return Element;
353
354 // Create the logical element if not found.
355 Element = Shared->Visitor->createElement(Iter->second.first);
356 if (Element) {
357 Element->setOffset(TI.getIndex());
358 Element->setOffsetFromTypeIndex();
359 Target[TI].second = Element;
360 }
361 }
362 return Element;
363}
364
365TypeIndex LVTypeRecords::find(uint32_t StreamIdx, StringRef Name) {
366 NameTable &Target = (StreamIdx == StreamTPI) ? NameFromTypes : NameFromIds;
367 NameTable::iterator Iter = Target.find(Name);
368 return Iter != Target.end() ? Iter->second : TypeIndex::None();
369}
370
371void LVStringRecords::addFilenames() {
372 for (StringIds::const_reference Entry : Strings) {
373 StringRef Name = std::get<1>(Entry.second);
374 LVScopeCompileUnit *Scope = std::get<2>(Entry.second);
375 Scope->addFilename(transformPath(Name));
376 }
377 Strings.clear();
378}
379
380void LVStringRecords::addFilenames(LVScopeCompileUnit *Scope) {
381 for (StringIds::reference Entry : Strings)
382 if (!std::get<2>(Entry.second))
383 std::get<2>(Entry.second) = Scope;
384}
385
386void LVNamespaceDeduction::add(StringRef String) {
387 StringRef InnerComponent;
388 StringRef OuterComponent;
389 std::tie(OuterComponent, InnerComponent) = getInnerComponent(String);
390 DeducedScopes.insert(InnerComponent);
391 if (OuterComponent.size())
392 UnresolvedScopes.insert(OuterComponent);
393}
394
395void LVNamespaceDeduction::init() {
396 // We have 2 sets of names:
397 // - deduced scopes (class, structure, union and enum) and
398 // - unresolved scopes, that can represent namespaces or any deduced.
399 // Before creating the namespaces, we have to traverse the unresolved
400 // and remove any references to already deduced scopes.
401 LVStringRefs Components;
402 for (const StringRef &Unresolved : UnresolvedScopes) {
403 Components = getAllLexicalComponents(Unresolved);
404 for (const StringRef &Component : Components) {
405 LookupSet::iterator Iter = DeducedScopes.find(Component);
406 if (Iter == DeducedScopes.end())
407 IdentifiedNamespaces.insert(Component);
408 }
409 }
410
411 LLVM_DEBUG({
412 auto Print = [&](LookupSet &Container, const char *Title) {
413 auto Header = [&]() {
414 dbgs() << formatv("\n{0}\n", fmt_repeat('=', 72));
415 dbgs() << formatv("{0}\n", Title);
416 dbgs() << formatv("{0}\n", fmt_repeat('=', 72));
417 };
418 Header();
419 for (const StringRef &Item : Container)
420 dbgs() << formatv("'{0}'\n", Item.str().c_str());
421 };
422
423 Print(DeducedScopes, "Deducted Scopes");
424 Print(UnresolvedScopes, "Unresolved Scopes");
425 Print(IdentifiedNamespaces, "Namespaces");
426 });
427}
428
429LVScope *LVNamespaceDeduction::get(LVStringRefs Components) {
430 LLVM_DEBUG({
431 for (const StringRef &Component : Components)
432 dbgs() << formatv("'{0}'\n", Component.str().c_str());
433 });
434
435 if (Components.empty())
436 return nullptr;
437
438 // Update the namespaces relationship.
439 LVScope *Namespace = nullptr;
440 LVScope *Parent = Shared->Reader->getCompileUnit();
441 for (const StringRef &Component : Components) {
442 // Check if we have seen the namespace.
443 Namespace = find(Component);
444 if (!Namespace) {
445 // We have identified namespaces that are generated by MSVC. Mark them
446 // as 'system' so they will be excluded from the logical view.
447 Namespace = Shared->Reader->createScopeNamespace();
448 Namespace->setTag(dwarf::DW_TAG_namespace);
449 Namespace->setName(Component);
450 Parent->addElement(Namespace);
451 getReader().isSystemEntry(Namespace);
452 add(Component, Namespace);
453 }
454 Parent = Namespace;
455 }
456 return Parent;
457}
458
459LVScope *LVNamespaceDeduction::get(StringRef ScopedName, bool CheckScope) {
460 LVStringRefs Components = getAllLexicalComponents(ScopedName);
461 if (CheckScope)
462 llvm::erase_if(Components, [&](StringRef Component) {
463 LookupSet::iterator Iter = IdentifiedNamespaces.find(Component);
464 return Iter == IdentifiedNamespaces.end();
465 });
466
468 { dbgs() << formatv("ScopedName: '{0}'\n", ScopedName.str().c_str()); });
469
470 return get(Components);
471}
472
473#undef DEBUG_TYPE
474#define DEBUG_TYPE "CodeViewTypeVisitor"
475
476//===----------------------------------------------------------------------===//
477// TypeRecord traversal.
478//===----------------------------------------------------------------------===//
479void LVTypeVisitor::printTypeIndex(StringRef FieldName, TypeIndex TI,
480 uint32_t StreamIdx) const {
481 codeview::printTypeIndex(W, FieldName, TI,
482 StreamIdx == StreamTPI ? Types : Ids);
483}
484
487}
488
490 LLVM_DEBUG({
491 W.getOStream() << formatTypeLeafKind(Record.kind());
492 W.getOStream() << " (" << HexNumber(TI.getIndex()) << ")\n";
493 });
494
495 if (options().getInternalTag())
496 Shared->TypeKinds.insert(Record.kind());
497
498 // The collected type records, will be use to create the logical elements
499 // during the symbols traversal when a type is referenced.
500 CurrentTypeIndex = TI;
501 Shared->TypeRecords.add(StreamIdx, TI, Record.kind());
502 return Error::success();
503}
504
506 LLVM_DEBUG({ W.printNumber("Length", uint32_t(Record.content().size())); });
507 return Error::success();
508}
509
511 LLVM_DEBUG({
513 W.getOStream() << " {\n";
514 W.indent();
515 });
516 return Error::success();
517}
518
520 LLVM_DEBUG({
521 W.unindent();
522 W.startLine() << "}\n";
523 });
524 return Error::success();
525}
526
528 LLVM_DEBUG({ W.printHex("UnknownMember", unsigned(Record.Kind)); });
529 return Error::success();
530}
531
532// LF_BUILDINFO (TPI)/(IPI)
534 // All the args are references into the TPI/IPI stream.
535 LLVM_DEBUG({
536 W.printNumber("NumArgs", static_cast<uint32_t>(Args.getArgs().size()));
537 ListScope Arguments(W, "Arguments");
538 for (TypeIndex Arg : Args.getArgs())
539 printTypeIndex("ArgType", Arg, StreamIPI);
540 });
541
542 // Only add the strings that hold information about filenames. They will be
543 // used to complete the line/file information for the logical elements.
544 // There are other strings holding information about namespaces.
545 TypeIndex TI;
547
548 // Absolute CWD path
549 TI = Args.getArgs()[BuildInfoRecord::BuildInfoArg::CurrentDirectory];
550 String = Ids.getTypeName(TI);
551 if (!String.empty())
552 Shared->StringRecords.add(TI, String);
553
554 // Get the compile unit name.
555 TI = Args.getArgs()[BuildInfoRecord::BuildInfoArg::SourceFile];
556 String = Ids.getTypeName(TI);
557 if (!String.empty())
558 Shared->StringRecords.add(TI, String);
559 LogicalVisitor->setCompileUnitName(std::string(String));
560
561 return Error::success();
562}
563
564// LF_CLASS, LF_STRUCTURE, LF_INTERFACE (TPI)
566 LLVM_DEBUG({
567 printTypeIndex("TypeIndex", CurrentTypeIndex, StreamTPI);
568 printTypeIndex("FieldListType", Class.getFieldList(), StreamTPI);
569 W.printString("Name", Class.getName());
570 });
571
572 // Collect class name for scope deduction.
573 Shared->NamespaceDeduction.add(Class.getName());
574 Shared->ForwardReferences.record(Class.isForwardRef(), Class.getName(),
575 CurrentTypeIndex);
576
577 // Collect class name for contained scopes deduction.
578 Shared->TypeRecords.add(StreamIdx, CurrentTypeIndex, Class.getName());
579 return Error::success();
580}
581
582// LF_ENUM (TPI)
584 LLVM_DEBUG({
585 printTypeIndex("TypeIndex", CurrentTypeIndex, StreamTPI);
586 printTypeIndex("FieldListType", Enum.getFieldList(), StreamTPI);
587 W.printString("Name", Enum.getName());
588 });
589
590 // Collect enum name for scope deduction.
591 Shared->NamespaceDeduction.add(Enum.getName());
592 return Error::success();
593}
594
595// LF_FUNC_ID (TPI)/(IPI)
597 LLVM_DEBUG({
598 printTypeIndex("TypeIndex", CurrentTypeIndex, StreamTPI);
599 printTypeIndex("Type", Func.getFunctionType(), StreamTPI);
600 printTypeIndex("Parent", Func.getParentScope(), StreamTPI);
601 W.printString("Name", Func.getName());
602 });
603
604 // Collect function name for scope deduction.
605 Shared->NamespaceDeduction.add(Func.getName());
606 return Error::success();
607}
608
609// LF_PROCEDURE (TPI)
611 LLVM_DEBUG({
612 printTypeIndex("TypeIndex", CurrentTypeIndex, StreamTPI);
613 printTypeIndex("ReturnType", Proc.getReturnType(), StreamTPI);
614 W.printNumber("NumParameters", Proc.getParameterCount());
615 printTypeIndex("ArgListType", Proc.getArgumentList(), StreamTPI);
616 });
617
618 // Collect procedure information as they can be referenced by typedefs.
619 Shared->TypeRecords.add(StreamTPI, CurrentTypeIndex, {});
620 return Error::success();
621}
622
623// LF_STRING_ID (TPI)/(IPI)
625 // No additional references are needed.
626 LLVM_DEBUG({
627 printTypeIndex("Id", String.getId(), StreamIPI);
628 W.printString("StringData", String.getString());
629 });
630 return Error::success();
631}
632
633// LF_UDT_SRC_LINE (TPI)/(IPI)
636 // UDT and SourceFile are references into the TPI/IPI stream.
637 LLVM_DEBUG({
638 printTypeIndex("UDT", Line.getUDT(), StreamIPI);
639 printTypeIndex("SourceFile", Line.getSourceFile(), StreamIPI);
640 W.printNumber("LineNumber", Line.getLineNumber());
641 });
642
643 Shared->LineRecords.push_back(CurrentTypeIndex);
644 return Error::success();
645}
646
647// LF_UNION (TPI)
649 LLVM_DEBUG({
650 W.printNumber("MemberCount", Union.getMemberCount());
651 printTypeIndex("FieldList", Union.getFieldList(), StreamTPI);
652 W.printNumber("SizeOf", Union.getSize());
653 W.printString("Name", Union.getName());
654 if (Union.hasUniqueName())
655 W.printString("UniqueName", Union.getUniqueName());
656 });
657
658 // Collect union name for scope deduction.
659 Shared->NamespaceDeduction.add(Union.getName());
660 Shared->ForwardReferences.record(Union.isForwardRef(), Union.getName(),
661 CurrentTypeIndex);
662
663 // Collect class name for contained scopes deduction.
664 Shared->TypeRecords.add(StreamIdx, CurrentTypeIndex, Union.getName());
665 return Error::success();
666}
667
668#undef DEBUG_TYPE
669#define DEBUG_TYPE "CodeViewSymbolVisitor"
670
671//===----------------------------------------------------------------------===//
672// SymbolRecord traversal.
673//===----------------------------------------------------------------------===//
675 uint32_t RelocOffset,
677 StringRef *RelocSym) {
678 Reader->printRelocatedField(Label, CoffSection, RelocOffset, Offset,
679 RelocSym);
680}
681
684 StringRef *RelocSym) {
685 Reader->getLinkageName(CoffSection, RelocOffset, Offset, RelocSym);
686}
687
690 Expected<StringRef> Name = Reader->getFileNameForFileOffset(FileOffset);
691 if (!Name) {
692 consumeError(Name.takeError());
693 return {};
694 }
695 return *Name;
696}
697
699 return Reader->CVStringTable;
700}
701
702void LVSymbolVisitor::printLocalVariableAddrRange(
703 const LocalVariableAddrRange &Range, uint32_t RelocationOffset) {
704 DictScope S(W, "LocalVariableAddrRange");
705 if (ObjDelegate)
706 ObjDelegate->printRelocatedField("OffsetStart", RelocationOffset,
707 Range.OffsetStart);
708 W.printHex("ISectStart", Range.ISectStart);
709 W.printHex("Range", Range.Range);
710}
711
712void LVSymbolVisitor::printLocalVariableAddrGap(
714 for (const LocalVariableAddrGap &Gap : Gaps) {
715 ListScope S(W, "LocalVariableAddrGap");
716 W.printHex("GapStartOffset", Gap.GapStartOffset);
717 W.printHex("Range", Gap.Range);
718 }
719}
720
721void LVSymbolVisitor::printTypeIndex(StringRef FieldName, TypeIndex TI) const {
722 codeview::printTypeIndex(W, FieldName, TI, Types);
723}
724
726 return visitSymbolBegin(Record, 0);
727}
728
730 SymbolKind Kind = Record.kind();
731 LLVM_DEBUG({
732 W.printNumber("Offset", Offset);
733 W.printEnum("Begin Kind", unsigned(Kind), getSymbolTypeNames());
734 });
735
736 if (options().getInternalTag())
737 Shared->SymbolKinds.insert(Kind);
738
739 LogicalVisitor->CurrentElement = LogicalVisitor->createElement(Kind);
740 if (!LogicalVisitor->CurrentElement) {
741 LLVM_DEBUG({
742 // We have an unsupported Symbol or Type Record.
743 // W.printEnum("Kind ignored", unsigned(Kind), getSymbolTypeNames());
744 });
745 return Error::success();
746 }
747
748 // Offset carried by the traversal routines when dealing with streams.
749 CurrentOffset = Offset;
750 IsCompileUnit = false;
751 if (!LogicalVisitor->CurrentElement->getOffsetFromTypeIndex())
752 LogicalVisitor->CurrentElement->setOffset(Offset);
753 if (symbolOpensScope(Kind) || (IsCompileUnit = symbolIsCompileUnit(Kind))) {
754 assert(LogicalVisitor->CurrentScope && "Invalid scope!");
755 LogicalVisitor->addElement(LogicalVisitor->CurrentScope, IsCompileUnit);
756 } else {
757 if (LogicalVisitor->CurrentSymbol)
758 LogicalVisitor->addElement(LogicalVisitor->CurrentSymbol);
759 if (LogicalVisitor->CurrentType)
760 LogicalVisitor->addElement(LogicalVisitor->CurrentType);
761 }
762
763 return Error::success();
764}
765
767 SymbolKind Kind = Record.kind();
769 { W.printEnum("End Kind", unsigned(Kind), getSymbolTypeNames()); });
770
771 if (symbolEndsScope(Kind)) {
772 LogicalVisitor->popScope();
773 }
774
775 return Error::success();
776}
777
779 LLVM_DEBUG({ W.printNumber("Length", Record.length()); });
780 return Error::success();
781}
782
783// S_BLOCK32
785 LLVM_DEBUG({
786 W.printHex("CodeSize", Block.CodeSize);
787 W.printHex("Segment", Block.Segment);
788 W.printString("BlockName", Block.Name);
789 });
790
791 if (LVScope *Scope = LogicalVisitor->CurrentScope) {
793 if (ObjDelegate)
794 ObjDelegate->getLinkageName(Block.getRelocationOffset(), Block.CodeOffset,
795 &LinkageName);
796 Scope->setLinkageName(LinkageName);
797
798 if (options().getGeneralCollectRanges()) {
799 // Record converted segment::offset addressing for this scope.
800 LVAddress Addendum = Reader->getSymbolTableAddress(LinkageName);
801 LVAddress LowPC =
802 Reader->linearAddress(Block.Segment, Block.CodeOffset, Addendum);
803 LVAddress HighPC = LowPC + Block.CodeSize - 1;
804 Scope->addObject(LowPC, HighPC);
805 }
806 }
807
808 return Error::success();
809}
810
811// S_BPREL32
814 LLVM_DEBUG({
815 printTypeIndex("Type", Local.Type);
816 W.printNumber("Offset", Local.Offset);
817 W.printString("VarName", Local.Name);
818 });
819
820 if (LVSymbol *Symbol = LogicalVisitor->CurrentSymbol) {
821 Symbol->setName(Local.Name);
822 // From the MS_Symbol_Type.pdf documentation (S_BPREL32):
823 // This symbol specifies symbols that are allocated on the stack for a
824 // procedure. For C and C++, these include the actual function parameters
825 // and the local non-static variables of functions.
826 // However, the offset for 'this' comes as a negative value.
827
828 // Symbol was created as 'variable'; determine its real kind.
829 Symbol->resetIsVariable();
830
831 if (Local.Name == "this") {
832 Symbol->setIsParameter();
833 Symbol->setIsArtificial();
834 } else {
835 // Determine symbol kind.
836 bool(Local.Offset > 0) ? Symbol->setIsParameter()
837 : Symbol->setIsVariable();
838 }
839
840 // Update correct debug information tag.
841 if (Symbol->getIsParameter())
842 Symbol->setTag(dwarf::DW_TAG_formal_parameter);
843
844 LVElement *Element = LogicalVisitor->getElement(StreamTPI, Local.Type);
845 if (Element && Element->getIsScoped()) {
846 // We have a local type. Find its parent function.
847 LVScope *Parent = Symbol->getFunctionParent();
848 // The element representing the type has been already finalized. If
849 // the type is an aggregate type, its members have been already added.
850 // As the type is local, its level will be changed.
851
852 // FIXME: Currently the algorithm used to scope lambda functions is
853 // incorrect. Before we allocate the type at this scope, check if is
854 // already allocated in other scope.
855 if (!Element->getParentScope()) {
856 Parent->addElement(Element);
857 Element->updateLevel(Parent);
858 }
859 }
860 Symbol->setType(Element);
861 }
862
863 return Error::success();
864}
865
866// S_REGREL32
869 LLVM_DEBUG({
870 printTypeIndex("Type", Local.Type);
871 W.printNumber("Offset", Local.Offset);
872 W.printString("VarName", Local.Name);
873 });
874
875 if (LVSymbol *Symbol = LogicalVisitor->CurrentSymbol) {
876 Symbol->setName(Local.Name);
877
878 // Symbol was created as 'variable'; determine its real kind.
879 Symbol->resetIsVariable();
880
881 // Check for the 'this' symbol.
882 if (Local.Name == "this") {
883 Symbol->setIsArtificial();
884 Symbol->setIsParameter();
885 } else {
886 // Determine symbol kind.
887 determineSymbolKind(Symbol, Local.Register);
888 }
889
890 // Update correct debug information tag.
891 if (Symbol->getIsParameter())
892 Symbol->setTag(dwarf::DW_TAG_formal_parameter);
893
894 LVElement *Element = LogicalVisitor->getElement(StreamTPI, Local.Type);
895 if (Element && Element->getIsScoped()) {
896 // We have a local type. Find its parent function.
897 LVScope *Parent = Symbol->getFunctionParent();
898 // The element representing the type has been already finalized. If
899 // the type is an aggregate type, its members have been already added.
900 // As the type is local, its level will be changed.
901
902 // FIXME: Currently the algorithm used to scope lambda functions is
903 // incorrect. Before we allocate the type at this scope, check if is
904 // already allocated in other scope.
905 if (!Element->getParentScope()) {
906 Parent->addElement(Element);
907 Element->updateLevel(Parent);
908 }
909 }
910 Symbol->setType(Element);
911 }
912
913 return Error::success();
914}
915
916// S_BUILDINFO
918 BuildInfoSym &BuildInfo) {
919 LLVM_DEBUG({ printTypeIndex("BuildId", BuildInfo.BuildId); });
920
921 CVType CVBuildType = Ids.getType(BuildInfo.BuildId);
922 if (Error Err = LogicalVisitor->finishVisitation(
923 CVBuildType, BuildInfo.BuildId, Reader->getCompileUnit()))
924 return Err;
925
926 return Error::success();
927}
928
929// S_COMPILE2
931 Compile2Sym &Compile2) {
932 LLVM_DEBUG({
933 W.printEnum("Language", uint8_t(Compile2.getLanguage()),
935 W.printFlags("Flags", uint32_t(Compile2.getFlags()),
937 W.printEnum("Machine", unsigned(Compile2.Machine), getCPUTypeNames());
938 W.printString("VersionName", Compile2.Version);
939 });
940
941 // MSVC generates the following sequence for a CodeView module:
942 // S_OBJNAME --> Set 'CurrentObjectName'.
943 // S_COMPILE2 --> Set the compile unit name using 'CurrentObjectName'.
944 // ...
945 // S_BUILDINFO --> Extract the source name.
946 //
947 // Clang generates the following sequence for a CodeView module:
948 // S_COMPILE2 --> Set the compile unit name to empty string.
949 // ...
950 // S_BUILDINFO --> Extract the source name.
951 //
952 // For both toolchains, update the compile unit name from S_BUILDINFO.
953 if (LVScope *Scope = LogicalVisitor->CurrentScope) {
954 // The name of the CU, was extracted from the 'BuildInfo' subsection.
955 Reader->setCompileUnitCPUType(Compile2.Machine);
956 Scope->setName(CurrentObjectName);
957 if (options().getAttributeProducer())
958 Scope->setProducer(Compile2.Version);
959 getReader().isSystemEntry(Scope, CurrentObjectName);
960
961 // The line records in CodeView are recorded per Module ID. Update
962 // the relationship between the current CU and the Module ID.
963 Reader->addModule(Scope);
964
965 // Updated the collected strings with their associated compile unit.
966 Shared->StringRecords.addFilenames(Reader->getCompileUnit());
967 }
968
969 // Clear any previous ObjectName.
970 CurrentObjectName = "";
971 return Error::success();
972}
973
974// S_COMPILE3
976 Compile3Sym &Compile3) {
977 LLVM_DEBUG({
978 W.printEnum("Language", uint8_t(Compile3.getLanguage()),
980 W.printFlags("Flags", uint32_t(Compile3.getFlags()),
982 W.printEnum("Machine", unsigned(Compile3.Machine), getCPUTypeNames());
983 W.printString("VersionName", Compile3.Version);
984 });
985
986 // MSVC generates the following sequence for a CodeView module:
987 // S_OBJNAME --> Set 'CurrentObjectName'.
988 // S_COMPILE3 --> Set the compile unit name using 'CurrentObjectName'.
989 // ...
990 // S_BUILDINFO --> Extract the source name.
991 //
992 // Clang generates the following sequence for a CodeView module:
993 // S_COMPILE3 --> Set the compile unit name to empty string.
994 // ...
995 // S_BUILDINFO --> Extract the source name.
996 //
997 // For both toolchains, update the compile unit name from S_BUILDINFO.
998 if (LVScope *Scope = LogicalVisitor->CurrentScope) {
999 // The name of the CU, was extracted from the 'BuildInfo' subsection.
1000 Reader->setCompileUnitCPUType(Compile3.Machine);
1001 Scope->setName(CurrentObjectName);
1002 if (options().getAttributeProducer())
1003 Scope->setProducer(Compile3.Version);
1004 getReader().isSystemEntry(Scope, CurrentObjectName);
1005
1006 // The line records in CodeView are recorded per Module ID. Update
1007 // the relationship between the current CU and the Module ID.
1008 Reader->addModule(Scope);
1009
1010 // Updated the collected strings with their associated compile unit.
1011 Shared->StringRecords.addFilenames(Reader->getCompileUnit());
1012 }
1013
1014 // Clear any previous ObjectName.
1015 CurrentObjectName = "";
1016 return Error::success();
1017}
1018
1019// S_CONSTANT, S_MANCONSTANT
1022 LLVM_DEBUG({
1023 printTypeIndex("Type", Constant.Type);
1024 W.printNumber("Value", Constant.Value);
1025 W.printString("Name", Constant.Name);
1026 });
1027
1028 if (LVSymbol *Symbol = LogicalVisitor->CurrentSymbol) {
1029 Symbol->setName(Constant.Name);
1030 Symbol->setType(LogicalVisitor->getElement(StreamTPI, Constant.Type));
1031 Symbol->resetIncludeInPrint();
1032 }
1033
1034 return Error::success();
1035}
1036
1037// S_DEFRANGE_FRAMEPOINTER_REL_FULL_SCOPE
1040 DefRangeFramePointerRelFullScopeSym &DefRangeFramePointerRelFullScope) {
1041 // DefRanges don't have types, just registers and code offsets.
1042 LLVM_DEBUG({
1043 if (LocalSymbol)
1044 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1045
1046 W.printNumber("Offset", DefRangeFramePointerRelFullScope.Offset);
1047 });
1048
1049 if (LVSymbol *Symbol = LocalSymbol) {
1050 Symbol->setHasCodeViewLocation();
1051 LocalSymbol = nullptr;
1052
1053 // Add location debug location. Operands: [Offset, 0].
1054 dwarf::Attribute Attr =
1055 dwarf::Attribute(SymbolKind::S_DEFRANGE_FRAMEPOINTER_REL_FULL_SCOPE);
1056
1057 uint64_t Operand1 = DefRangeFramePointerRelFullScope.Offset;
1058 Symbol->addLocation(Attr, 0, 0, 0, 0);
1059 Symbol->addLocationOperands(LVSmall(Attr), {Operand1});
1060 }
1061
1062 return Error::success();
1063}
1064
1065// S_DEFRANGE_FRAMEPOINTER_REL
1067 CVSymbol &Record, DefRangeFramePointerRelSym &DefRangeFramePointerRel) {
1068 // DefRanges don't have types, just registers and code offsets.
1069 LLVM_DEBUG({
1070 if (LocalSymbol)
1071 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1072
1073 W.printNumber("Offset", DefRangeFramePointerRel.Hdr.Offset);
1074 printLocalVariableAddrRange(DefRangeFramePointerRel.Range,
1075 DefRangeFramePointerRel.getRelocationOffset());
1076 printLocalVariableAddrGap(DefRangeFramePointerRel.Gaps);
1077 });
1078
1079 // We are expecting the following sequence:
1080 // 128 | S_LOCAL [size = 20] `ParamBar`
1081 // ...
1082 // 148 | S_DEFRANGE_FRAMEPOINTER_REL [size = 16]
1083 if (LVSymbol *Symbol = LocalSymbol) {
1084 Symbol->setHasCodeViewLocation();
1085 LocalSymbol = nullptr;
1086
1087 // Add location debug location. Operands: [Offset, 0].
1088 dwarf::Attribute Attr =
1089 dwarf::Attribute(SymbolKind::S_DEFRANGE_FRAMEPOINTER_REL);
1090 uint64_t Operand1 = DefRangeFramePointerRel.Hdr.Offset;
1091
1092 LocalVariableAddrRange Range = DefRangeFramePointerRel.Range;
1094 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1095
1096 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1097 Symbol->addLocationOperands(LVSmall(Attr), {Operand1});
1098 }
1099
1100 return Error::success();
1101}
1102
1103// S_DEFRANGE_REGISTER_REL
1105 CVSymbol &Record, DefRangeRegisterRelSym &DefRangeRegisterRel) {
1106 // DefRanges don't have types, just registers and code offsets.
1107 LLVM_DEBUG({
1108 if (LocalSymbol)
1109 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1110
1111 W.printBoolean("HasSpilledUDTMember",
1112 DefRangeRegisterRel.hasSpilledUDTMember());
1113 W.printNumber("OffsetInParent", DefRangeRegisterRel.offsetInParent());
1114 W.printNumber("BasePointerOffset",
1115 DefRangeRegisterRel.Hdr.BasePointerOffset);
1116 printLocalVariableAddrRange(DefRangeRegisterRel.Range,
1117 DefRangeRegisterRel.getRelocationOffset());
1118 printLocalVariableAddrGap(DefRangeRegisterRel.Gaps);
1119 });
1120
1121 if (LVSymbol *Symbol = LocalSymbol) {
1122 Symbol->setHasCodeViewLocation();
1123 LocalSymbol = nullptr;
1124
1125 // Add location debug location. Operands: [Register, Offset].
1126 dwarf::Attribute Attr =
1127 dwarf::Attribute(SymbolKind::S_DEFRANGE_REGISTER_REL);
1128 uint64_t Operand1 = DefRangeRegisterRel.Hdr.Register;
1129 uint64_t Operand2 = DefRangeRegisterRel.Hdr.BasePointerOffset;
1130
1131 LocalVariableAddrRange Range = DefRangeRegisterRel.Range;
1133 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1134
1135 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1136 Symbol->addLocationOperands(LVSmall(Attr), {Operand1, Operand2});
1137 }
1138
1139 return Error::success();
1140}
1141
1142// S_DEFRANGE_REGISTER
1144 DefRangeRegisterSym &DefRangeRegister) {
1145 // DefRanges don't have types, just registers and code offsets.
1146 LLVM_DEBUG({
1147 if (LocalSymbol)
1148 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1149
1150 W.printEnum("Register", uint16_t(DefRangeRegister.Hdr.Register),
1152 W.printNumber("MayHaveNoName", DefRangeRegister.Hdr.MayHaveNoName);
1153 printLocalVariableAddrRange(DefRangeRegister.Range,
1154 DefRangeRegister.getRelocationOffset());
1155 printLocalVariableAddrGap(DefRangeRegister.Gaps);
1156 });
1157
1158 if (LVSymbol *Symbol = LocalSymbol) {
1159 Symbol->setHasCodeViewLocation();
1160 LocalSymbol = nullptr;
1161
1162 // Add location debug location. Operands: [Register, 0].
1163 dwarf::Attribute Attr = dwarf::Attribute(SymbolKind::S_DEFRANGE_REGISTER);
1164 uint64_t Operand1 = DefRangeRegister.Hdr.Register;
1165
1166 LocalVariableAddrRange Range = DefRangeRegister.Range;
1168 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1169
1170 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1171 Symbol->addLocationOperands(LVSmall(Attr), {Operand1});
1172 }
1173
1174 return Error::success();
1175}
1176
1177// S_DEFRANGE_SUBFIELD_REGISTER
1179 CVSymbol &Record, DefRangeSubfieldRegisterSym &DefRangeSubfieldRegister) {
1180 // DefRanges don't have types, just registers and code offsets.
1181 LLVM_DEBUG({
1182 if (LocalSymbol)
1183 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1184
1185 W.printEnum("Register", uint16_t(DefRangeSubfieldRegister.Hdr.Register),
1187 W.printNumber("MayHaveNoName", DefRangeSubfieldRegister.Hdr.MayHaveNoName);
1188 W.printNumber("OffsetInParent",
1189 DefRangeSubfieldRegister.Hdr.OffsetInParent);
1190 printLocalVariableAddrRange(DefRangeSubfieldRegister.Range,
1191 DefRangeSubfieldRegister.getRelocationOffset());
1192 printLocalVariableAddrGap(DefRangeSubfieldRegister.Gaps);
1193 });
1194
1195 if (LVSymbol *Symbol = LocalSymbol) {
1196 Symbol->setHasCodeViewLocation();
1197 LocalSymbol = nullptr;
1198
1199 // Add location debug location. Operands: [Register, 0].
1200 dwarf::Attribute Attr =
1201 dwarf::Attribute(SymbolKind::S_DEFRANGE_SUBFIELD_REGISTER);
1202 uint64_t Operand1 = DefRangeSubfieldRegister.Hdr.Register;
1203
1204 LocalVariableAddrRange Range = DefRangeSubfieldRegister.Range;
1206 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1207
1208 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1209 Symbol->addLocationOperands(LVSmall(Attr), {Operand1});
1210 }
1211
1212 return Error::success();
1213}
1214
1215// S_DEFRANGE_SUBFIELD
1217 DefRangeSubfieldSym &DefRangeSubfield) {
1218 // DefRanges don't have types, just registers and code offsets.
1219 LLVM_DEBUG({
1220 if (LocalSymbol)
1221 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1222
1223 if (ObjDelegate) {
1224 DebugStringTableSubsectionRef Strings = ObjDelegate->getStringTable();
1225 auto ExpectedProgram = Strings.getString(DefRangeSubfield.Program);
1226 if (!ExpectedProgram) {
1227 consumeError(ExpectedProgram.takeError());
1228 return llvm::make_error<CodeViewError>(
1229 "String table offset outside of bounds of String Table!");
1230 }
1231 W.printString("Program", *ExpectedProgram);
1232 }
1233 W.printNumber("OffsetInParent", DefRangeSubfield.OffsetInParent);
1234 printLocalVariableAddrRange(DefRangeSubfield.Range,
1235 DefRangeSubfield.getRelocationOffset());
1236 printLocalVariableAddrGap(DefRangeSubfield.Gaps);
1237 });
1238
1239 if (LVSymbol *Symbol = LocalSymbol) {
1240 Symbol->setHasCodeViewLocation();
1241 LocalSymbol = nullptr;
1242
1243 // Add location debug location. Operands: [Program, 0].
1244 dwarf::Attribute Attr = dwarf::Attribute(SymbolKind::S_DEFRANGE_SUBFIELD);
1245 uint64_t Operand1 = DefRangeSubfield.Program;
1246
1247 LocalVariableAddrRange Range = DefRangeSubfield.Range;
1249 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1250
1251 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1252 Symbol->addLocationOperands(LVSmall(Attr), {Operand1, /*Operand2=*/0});
1253 }
1254
1255 return Error::success();
1256}
1257
1258// S_DEFRANGE
1260 DefRangeSym &DefRange) {
1261 // DefRanges don't have types, just registers and code offsets.
1262 LLVM_DEBUG({
1263 if (LocalSymbol)
1264 W.getOStream() << formatv("Symbol: {0}, ", LocalSymbol->getName());
1265
1266 if (ObjDelegate) {
1267 DebugStringTableSubsectionRef Strings = ObjDelegate->getStringTable();
1268 auto ExpectedProgram = Strings.getString(DefRange.Program);
1269 if (!ExpectedProgram) {
1270 consumeError(ExpectedProgram.takeError());
1271 return llvm::make_error<CodeViewError>(
1272 "String table offset outside of bounds of String Table!");
1273 }
1274 W.printString("Program", *ExpectedProgram);
1275 }
1276 printLocalVariableAddrRange(DefRange.Range, DefRange.getRelocationOffset());
1277 printLocalVariableAddrGap(DefRange.Gaps);
1278 });
1279
1280 if (LVSymbol *Symbol = LocalSymbol) {
1281 Symbol->setHasCodeViewLocation();
1282 LocalSymbol = nullptr;
1283
1284 // Add location debug location. Operands: [Program, 0].
1285 dwarf::Attribute Attr = dwarf::Attribute(SymbolKind::S_DEFRANGE);
1286 uint64_t Operand1 = DefRange.Program;
1287
1290 Reader->linearAddress(Range.ISectStart, Range.OffsetStart);
1291
1292 Symbol->addLocation(Attr, Address, Address + Range.Range, 0, 0);
1293 Symbol->addLocationOperands(LVSmall(Attr), {Operand1, /*Operand2=*/0});
1294 }
1295
1296 return Error::success();
1297}
1298
1299// S_FRAMEPROC
1301 FrameProcSym &FrameProc) {
1302 if (LVScope *Function = LogicalVisitor->getReaderScope()) {
1303 // S_FRAMEPROC contains extra information for the function described
1304 // by any of the previous generated records:
1305 // S_GPROC32, S_LPROC32, S_LPROC32_ID, S_GPROC32_ID.
1306
1307 // The generated sequence is:
1308 // S_GPROC32_ID ...
1309 // S_FRAMEPROC ...
1310
1311 // Collect additional inline flags for the current scope function.
1312 FrameProcedureOptions Flags = FrameProc.Flags;
1313 if (FrameProcedureOptions::MarkedInline ==
1314 (Flags & FrameProcedureOptions::MarkedInline))
1316 if (FrameProcedureOptions::Inlined ==
1317 (Flags & FrameProcedureOptions::Inlined))
1318 Function->setInlineCode(dwarf::DW_INL_inlined);
1319
1320 // To determine the symbol kind for any symbol declared in that function,
1321 // we can access the S_FRAMEPROC for the parent scope function. It contains
1322 // information about the local fp and param fp registers and compare with
1323 // the register in the S_REGREL32 to get a match.
1325 LocalFrameRegister = FrameProc.getLocalFramePtrReg(CPU);
1326 ParamFrameRegister = FrameProc.getParamFramePtrReg(CPU);
1327 }
1328
1329 return Error::success();
1330}
1331
1332// S_GDATA32, S_LDATA32, S_LMANDATA, S_GMANDATA
1334 LLVM_DEBUG({
1335 printTypeIndex("Type", Data.Type);
1336 W.printString("DisplayName", Data.Name);
1337 });
1338
1339 if (LVSymbol *Symbol = LogicalVisitor->CurrentSymbol) {
1341 if (ObjDelegate)
1342 ObjDelegate->getLinkageName(Data.getRelocationOffset(), Data.DataOffset,
1343 &LinkageName);
1344
1345 Symbol->setName(Data.Name);
1346 Symbol->setLinkageName(LinkageName);
1347
1348 // The MSVC generates local data as initialization for aggregates. It
1349 // contains the address for an initialization function.
1350 // The symbols contains the '$initializer$' pattern. Allow them only if
1351 // the '--internal=system' option is given.
1352 // 0 | S_LDATA32 `Struct$initializer$`
1353 // type = 0x1040 (void ()*)
1354 if (getReader().isSystemEntry(Symbol) && !options().getAttributeSystem()) {
1355 Symbol->resetIncludeInPrint();
1356 return Error::success();
1357 }
1358
1359 if (LVScope *Namespace = Shared->NamespaceDeduction.get(Data.Name)) {
1360 // The variable is already at different scope. In order to reflect
1361 // the correct parent, move it to the namespace.
1362 if (Symbol->getParentScope()->removeElement(Symbol))
1363 Namespace->addElement(Symbol);
1364 }
1365
1366 Symbol->setType(LogicalVisitor->getElement(StreamTPI, Data.Type));
1367 if (Record.kind() == SymbolKind::S_GDATA32)
1368 Symbol->setIsExternal();
1369 }
1370
1371 return Error::success();
1372}
1373
1374// S_INLINESITE
1377 LLVM_DEBUG({ printTypeIndex("Inlinee", InlineSite.Inlinee); });
1378
1379 if (LVScope *InlinedFunction = LogicalVisitor->CurrentScope) {
1380 LVScope *AbstractFunction = Reader->createScopeFunction();
1381 AbstractFunction->setIsSubprogram();
1382 AbstractFunction->setTag(dwarf::DW_TAG_subprogram);
1383 AbstractFunction->setInlineCode(dwarf::DW_INL_inlined);
1384 AbstractFunction->setIsInlinedAbstract();
1385 InlinedFunction->setReference(AbstractFunction);
1386
1387 LogicalVisitor->startProcessArgumentList();
1388 // 'Inlinee' is a Type ID.
1389 CVType CVFunctionType = Ids.getType(InlineSite.Inlinee);
1390 if (Error Err = LogicalVisitor->finishVisitation(
1391 CVFunctionType, InlineSite.Inlinee, AbstractFunction))
1392 return Err;
1393 LogicalVisitor->stopProcessArgumentList();
1394
1395 // For inlined functions set the linkage name to be the same as
1396 // the name. It used to find their lines and ranges.
1397 StringRef Name = AbstractFunction->getName();
1398 InlinedFunction->setName(Name);
1399 InlinedFunction->setLinkageName(Name);
1400
1401 // Process annotation bytes to calculate code and line offsets.
1402 if (Error Err = LogicalVisitor->inlineSiteAnnotation(
1403 AbstractFunction, InlinedFunction, InlineSite))
1404 return Err;
1405 }
1406
1407 return Error::success();
1408}
1409
1410// S_LOCAL
1412 LLVM_DEBUG({
1413 printTypeIndex("Type", Local.Type);
1414 W.printFlags("Flags", uint16_t(Local.Flags), getLocalFlagNames());
1415 W.printString("VarName", Local.Name);
1416 });
1417
1418 if (LVSymbol *Symbol = LogicalVisitor->CurrentSymbol) {
1419 Symbol->setName(Local.Name);
1420
1421 // Symbol was created as 'variable'; determine its real kind.
1422 Symbol->resetIsVariable();
1423
1424 // Be sure the 'this' symbol is marked as 'compiler generated'.
1425 if (bool(Local.Flags & LocalSymFlags::IsCompilerGenerated) ||
1426 Local.Name == "this") {
1427 Symbol->setIsArtificial();
1428 Symbol->setIsParameter();
1429 } else {
1430 bool(Local.Flags & LocalSymFlags::IsParameter) ? Symbol->setIsParameter()
1431 : Symbol->setIsVariable();
1432 }
1433
1434 // Update correct debug information tag.
1435 if (Symbol->getIsParameter())
1436 Symbol->setTag(dwarf::DW_TAG_formal_parameter);
1437
1438 LVElement *Element = LogicalVisitor->getElement(StreamTPI, Local.Type);
1439 if (Element && Element->getIsScoped()) {
1440 // We have a local type. Find its parent function.
1441 LVScope *Parent = Symbol->getFunctionParent();
1442 // The element representing the type has been already finalized. If
1443 // the type is an aggregate type, its members have been already added.
1444 // As the type is local, its level will be changed.
1445 Parent->addElement(Element);
1446 Element->updateLevel(Parent);
1447 }
1448 Symbol->setType(Element);
1449
1450 // The CodeView records (S_DEFFRAME_*) describing debug location for
1451 // this symbol, do not have any direct reference to it. Those records
1452 // are emitted after this symbol. Record the current symbol.
1453 LocalSymbol = Symbol;
1454 }
1455
1456 return Error::success();
1457}
1458
1459// S_OBJNAME
1461 LLVM_DEBUG({
1462 W.printHex("Signature", ObjName.Signature);
1463 W.printString("ObjectName", ObjName.Name);
1464 });
1465
1466 CurrentObjectName = ObjName.Name;
1467 return Error::success();
1468}
1469
1470// S_GPROC32, S_LPROC32, S_LPROC32_ID, S_GPROC32_ID
1472 if (InFunctionScope)
1473 return llvm::make_error<CodeViewError>("Visiting a ProcSym while inside "
1474 "function scope!");
1475
1476 InFunctionScope = true;
1477
1478 LLVM_DEBUG({
1479 printTypeIndex("FunctionType", Proc.FunctionType);
1480 W.printHex("Segment", Proc.Segment);
1481 W.printFlags("Flags", static_cast<uint8_t>(Proc.Flags),
1483 W.printString("DisplayName", Proc.Name);
1484 });
1485
1486 // Clang and Microsoft generated different debug information records:
1487 // For functions definitions:
1488 // Clang: S_GPROC32 -> LF_FUNC_ID -> LF_PROCEDURE
1489 // Microsoft: S_GPROC32 -> LF_PROCEDURE
1490
1491 // For member function definition:
1492 // Clang: S_GPROC32 -> LF_MFUNC_ID -> LF_MFUNCTION
1493 // Microsoft: S_GPROC32 -> LF_MFUNCTION
1494 // In order to support both sequences, if we found LF_FUNCTION_ID, just
1495 // get the TypeIndex for LF_PROCEDURE.
1496
1497 // For the given test case, we have the sequence:
1498 // namespace NSP_local {
1499 // void foo_local() {
1500 // }
1501 // }
1502 //
1503 // 0x1000 | LF_STRING_ID String: NSP_local
1504 // 0x1002 | LF_PROCEDURE
1505 // return type = 0x0003 (void), # args = 0, param list = 0x1001
1506 // calling conv = cdecl, options = None
1507 // 0x1003 | LF_FUNC_ID
1508 // name = foo_local, type = 0x1002, parent scope = 0x1000
1509 // 0 | S_GPROC32_ID `NSP_local::foo_local`
1510 // type = `0x1003 (foo_local)`
1511 // 0x1004 | LF_STRING_ID String: suite
1512 // 0x1005 | LF_STRING_ID String: suite_local.cpp
1513 //
1514 // The LF_STRING_ID can hold different information:
1515 // 0x1000 - The enclosing namespace.
1516 // 0x1004 - The compile unit directory name.
1517 // 0x1005 - The compile unit name.
1518 //
1519 // Before deducting its scope, we need to evaluate its type and create any
1520 // associated namespaces.
1521 if (LVScope *Function = LogicalVisitor->CurrentScope) {
1523 if (ObjDelegate)
1524 ObjDelegate->getLinkageName(Proc.getRelocationOffset(), Proc.CodeOffset,
1525 &LinkageName);
1526
1527 // The line table can be accessed using the linkage name.
1529 Function->setName(Proc.Name);
1530 Function->setLinkageName(LinkageName);
1531
1532 if (options().getGeneralCollectRanges()) {
1533 // Record converted segment::offset addressing for this scope.
1534 LVAddress Addendum = Reader->getSymbolTableAddress(LinkageName);
1535 LVAddress LowPC =
1536 Reader->linearAddress(Proc.Segment, Proc.CodeOffset, Addendum);
1537 LVAddress HighPC = LowPC + Proc.CodeSize - 1;
1538 Function->addObject(LowPC, HighPC);
1539
1540 // If the scope is a function, add it to the public names.
1541 if ((options().getAttributePublics() || options().getPrintAnyLine()) &&
1542 !Function->getIsInlinedFunction())
1543 Reader->getCompileUnit()->addPublicName(Function, LowPC, HighPC);
1544 }
1545
1546 if (Function->getIsSystem() && !options().getAttributeSystem()) {
1547 Function->resetIncludeInPrint();
1548 return Error::success();
1549 }
1550
1551 TypeIndex TIFunctionType = Proc.FunctionType;
1552 if (TIFunctionType.isSimple())
1553 Function->setType(LogicalVisitor->getElement(StreamTPI, TIFunctionType));
1554 else {
1555 // We have to detect the correct stream, using the lexical parent
1556 // name, as there is not other obvious way to get the stream.
1557 // Normal function: LF_FUNC_ID (TPI)/(IPI)
1558 // LF_PROCEDURE (TPI)
1559 // Lambda function: LF_MFUNCTION (TPI)
1560 // Member function: LF_MFUNC_ID (TPI)/(IPI)
1561
1562 StringRef OuterComponent;
1563 std::tie(OuterComponent, std::ignore) = getInnerComponent(Proc.Name);
1564 TypeIndex TI = Shared->ForwardReferences.find(OuterComponent);
1565
1566 std::optional<CVType> CVFunctionType;
1567 auto GetRecordType = [&]() -> bool {
1568 CVFunctionType = Ids.tryGetType(TIFunctionType);
1569 if (!CVFunctionType)
1570 return false;
1571
1572 if (TI.isNoneType())
1573 // Normal function.
1574 if (CVFunctionType->kind() == LF_FUNC_ID)
1575 return true;
1576
1577 // Member function.
1578 return (CVFunctionType->kind() == LF_MFUNC_ID);
1579 };
1580
1581 // We can have a LF_FUNC_ID, LF_PROCEDURE or LF_MFUNCTION.
1582 if (!GetRecordType()) {
1583 CVFunctionType = Types.tryGetType(TIFunctionType);
1584 if (!CVFunctionType)
1585 return llvm::make_error<CodeViewError>("Invalid type index");
1586 }
1587
1588 if (Error Err = LogicalVisitor->finishVisitation(
1589 *CVFunctionType, TIFunctionType, Function))
1590 return Err;
1591 }
1592
1593 if (Record.kind() == SymbolKind::S_GPROC32 ||
1594 Record.kind() == SymbolKind::S_GPROC32_ID)
1595 Function->setIsExternal();
1596
1597 // We don't have a way to see if the symbol is compiler generated. Use
1598 // the linkage name, to detect `scalar deleting destructor' functions.
1599 std::string DemangledSymbol = demangle(LinkageName);
1600 if (DemangledSymbol.find("scalar deleting dtor") != std::string::npos) {
1601 Function->setIsArtificial();
1602 } else {
1603 // Clang generates global ctor and dtor names containing the substrings:
1604 // 'dynamic initializer for' and 'dynamic atexit destructor for'.
1605 if (DemangledSymbol.find("dynamic atexit destructor for") !=
1606 std::string::npos)
1607 Function->setIsArtificial();
1608 }
1609 }
1610
1611 return Error::success();
1612}
1613
1614// S_END
1616 ScopeEndSym &ScopeEnd) {
1617 InFunctionScope = false;
1618 return Error::success();
1619}
1620
1621// S_THUNK32
1623 if (InFunctionScope)
1624 return llvm::make_error<CodeViewError>("Visiting a Thunk32Sym while inside "
1625 "function scope!");
1626
1627 InFunctionScope = true;
1628
1629 LLVM_DEBUG({
1630 W.printHex("Segment", Thunk.Segment);
1631 W.printString("Name", Thunk.Name);
1632 });
1633
1634 if (LVScope *Function = LogicalVisitor->CurrentScope)
1635 Function->setName(Thunk.Name);
1636
1637 return Error::success();
1638}
1639
1640// S_UDT, S_COBOLUDT
1642 LLVM_DEBUG({
1643 printTypeIndex("Type", UDT.Type);
1644 W.printString("UDTName", UDT.Name);
1645 });
1646
1647 if (LVType *Type = LogicalVisitor->CurrentType) {
1648 if (LVScope *Namespace = Shared->NamespaceDeduction.get(UDT.Name)) {
1649 if (Type->getParentScope()->removeElement(Type))
1650 Namespace->addElement(Type);
1651 }
1652
1653 Type->setName(UDT.Name);
1654
1655 // We have to determine if the typedef is a real C/C++ definition or is
1656 // the S_UDT record that describe all the user defined types.
1657 // 0 | S_UDT `Name` original type = 0x1009
1658 // 0x1009 | LF_STRUCTURE `Name`
1659 // Ignore type definitions for RTTI types:
1660 // _s__RTTIBaseClassArray, _s__RTTIBaseClassDescriptor,
1661 // _s__RTTICompleteObjectLocator, _s__RTTIClassHierarchyDescriptor.
1663 Type->resetIncludeInPrint();
1664 else {
1665 StringRef RecordName = getRecordName(Types, UDT.Type);
1666 if (UDT.Name == RecordName)
1667 Type->resetIncludeInPrint();
1668 Type->setType(LogicalVisitor->getElement(StreamTPI, UDT.Type));
1669 }
1670 }
1671
1672 return Error::success();
1673}
1674
1675// S_UNAMESPACE
1677 UsingNamespaceSym &UN) {
1678 LLVM_DEBUG({ W.printString("Namespace", UN.Name); });
1679 return Error::success();
1680}
1681
1682// S_ARMSWITCHTABLE
1684 JumpTableSym &JumpTable) {
1685 LLVM_DEBUG({
1686 W.printHex("BaseOffset", JumpTable.BaseOffset);
1687 W.printNumber("BaseSegment", JumpTable.BaseSegment);
1688 W.printFlags("SwitchType", static_cast<uint16_t>(JumpTable.SwitchType),
1690 W.printHex("BranchOffset", JumpTable.BranchOffset);
1691 W.printHex("TableOffset", JumpTable.TableOffset);
1692 W.printNumber("BranchSegment", JumpTable.BranchSegment);
1693 W.printNumber("TableSegment", JumpTable.TableSegment);
1694 W.printNumber("EntriesCount", JumpTable.EntriesCount);
1695 });
1696 return Error::success();
1697}
1698
1699// S_CALLERS, S_CALLEES, S_INLINEES
1701 LLVM_DEBUG({
1702 llvm::StringRef FieldName;
1703 switch (Caller.getKind()) {
1704 case SymbolRecordKind::CallerSym:
1705 FieldName = "Callee";
1706 break;
1707 case SymbolRecordKind::CalleeSym:
1708 FieldName = "Caller";
1709 break;
1710 case SymbolRecordKind::InlineesSym:
1711 FieldName = "Inlinee";
1712 break;
1713 default:
1714 return llvm::make_error<CodeViewError>(
1715 "Unknown CV Record type for a CallerSym object!");
1716 }
1717 for (auto FuncID : Caller.Indices) {
1718 printTypeIndex(FieldName, FuncID);
1719 }
1720 });
1721 return Error::success();
1722}
1723
1724#undef DEBUG_TYPE
1725#define DEBUG_TYPE "CodeViewLogicalVisitor"
1726
1727//===----------------------------------------------------------------------===//
1728// Logical visitor.
1729//===----------------------------------------------------------------------===//
1731 InputFile &Input)
1732 : Reader(Reader), W(W), Input(Input) {
1733 // The LogicalVisitor connects the CodeViewReader with the visitors that
1734 // traverse the types, symbols, etc. Do any initialization that is needed.
1735 Shared = std::make_shared<LVShared>(Reader, this);
1736}
1737
1739 uint32_t StreamIdx) {
1740 codeview::printTypeIndex(W, FieldName, TI,
1741 StreamIdx == StreamTPI ? types() : ids());
1742}
1743
1745 LVElement *Element, uint32_t StreamIdx) {
1746 W.getOStream() << "\n";
1747 W.startLine() << formatTypeLeafKind(Record.kind());
1748 W.getOStream() << " (" << HexNumber(TI.getIndex()) << ")";
1749 W.getOStream() << " {\n";
1750 W.indent();
1751 W.printEnum("TypeLeafKind", unsigned(Record.kind()), ArrayRef(LeafTypeNames));
1752 printTypeIndex("TI", TI, StreamIdx);
1753 W.startLine() << "Element: " << HexNumber(Element->getOffset()) << " "
1754 << Element->getName() << "\n";
1755}
1756
1758 W.unindent();
1759 W.startLine() << "}\n";
1760}
1761
1763 LVElement *Element,
1764 uint32_t StreamIdx) {
1765 W.getOStream() << "\n";
1766 W.startLine() << formatTypeLeafKind(Record.Kind);
1767 W.getOStream() << " (" << HexNumber(TI.getIndex()) << ")";
1768 W.getOStream() << " {\n";
1769 W.indent();
1770 W.printEnum("TypeLeafKind", unsigned(Record.Kind), ArrayRef(LeafTypeNames));
1771 printTypeIndex("TI", TI, StreamIdx);
1772 W.startLine() << "Element: " << HexNumber(Element->getOffset()) << " "
1773 << Element->getName() << "\n";
1774}
1775
1777 W.unindent();
1778 W.startLine() << "}\n";
1779}
1780
1782 LLVM_DEBUG({
1783 printTypeIndex("\nTI", TI, StreamTPI);
1784 W.printNumber("Length", uint32_t(Record.content().size()));
1785 });
1786 return Error::success();
1787}
1788
1789// LF_ARGLIST (TPI)
1791 TypeIndex TI, LVElement *Element) {
1792 ArrayRef<TypeIndex> Indices = Args.getIndices();
1793 uint32_t Size = Indices.size();
1794 LLVM_DEBUG({
1795 printTypeBegin(Record, TI, Element, StreamTPI);
1796 W.printNumber("NumArgs", Size);
1797 ListScope Arguments(W, "Arguments");
1798 for (uint32_t I = 0; I < Size; ++I)
1799 printTypeIndex("ArgType", Indices[I], StreamTPI);
1801 });
1802
1803 LVScope *Function = static_cast<LVScope *>(Element);
1804 for (uint32_t Index = 0; Index < Size; ++Index) {
1805 TypeIndex ParameterType = Indices[Index];
1806 createParameter(ParameterType, StringRef(), Function);
1807 }
1808
1809 return Error::success();
1810}
1811
1812// LF_ARRAY (TPI)
1814 TypeIndex TI, LVElement *Element) {
1815 LLVM_DEBUG({
1816 printTypeBegin(Record, TI, Element, StreamTPI);
1817 printTypeIndex("ElementType", AT.getElementType(), StreamTPI);
1818 printTypeIndex("IndexType", AT.getIndexType(), StreamTPI);
1819 W.printNumber("SizeOf", AT.getSize());
1820 W.printString("Name", AT.getName());
1822 });
1823
1824 if (Element->getIsFinalized())
1825 return Error::success();
1826 Element->setIsFinalized();
1827
1828 LVScopeArray *Array = static_cast<LVScopeArray *>(Element);
1829 if (!Array)
1830 return Error::success();
1831
1832 Reader->getCompileUnit()->addElement(Array);
1833 TypeIndex TIElementType = AT.getElementType();
1834
1835 LVType *PrevSubrange = nullptr;
1837
1838 // As the logical view is modeled on DWARF, for each dimension we have to
1839 // create a DW_TAG_subrange_type, with dimension size.
1840 // The subrange type can be: unsigned __int32 or unsigned __int64.
1841 auto AddSubrangeType = [&](ArrayRecord &AR) {
1842 LVType *Subrange = Reader->createTypeSubrange();
1843 Subrange->setTag(dwarf::DW_TAG_subrange_type);
1844 Subrange->setType(getElement(StreamTPI, AR.getIndexType()));
1845 Subrange->setCount(AR.getSize());
1846 Subrange->setOffset(
1847 TIElementType.isSimple()
1848 ? (uint32_t)(TypeLeafKind)TIElementType.getSimpleKind()
1849 : TIElementType.getIndex());
1850 Array->addElement(Subrange);
1851
1852 if (PrevSubrange)
1853 if (int64_t Count = Subrange->getCount())
1854 PrevSubrange->setCount(PrevSubrange->getCount() / Count);
1855 PrevSubrange = Subrange;
1856 };
1857
1858 // Preserve the original TypeIndex; it would be updated in the case of:
1859 // - The array type contains qualifiers.
1860 // - In multidimensional arrays, the last LF_ARRAY entry contains the type.
1861 TypeIndex TIArrayType;
1862
1863 // For each dimension in the array, there is a LF_ARRAY entry. The last
1864 // entry contains the array type, which can be a LF_MODIFIER in the case
1865 // of the type being modified by a qualifier (const, etc).
1866 ArrayRecord AR(AT);
1867 CVType CVEntry = Record;
1868 while (CVEntry.kind() == LF_ARRAY) {
1869 // Create the subrange information, required by the logical view. Once
1870 // the array has been processed, the dimension sizes will updated, as
1871 // the sizes are a progression. For instance:
1872 // sizeof(int) = 4
1873 // int Array[2]; Sizes: 8 Dim: 8 / 4 -> [2]
1874 // int Array[2][3]; Sizes: 24, 12 Dim: 24 / 12 -> [2]
1875 // Dim: 12 / 4 -> [3]
1876 // int Array[2][3][4]; sizes: 96, 48, 16 Dim: 96 / 48 -> [2]
1877 // Dim: 48 / 16 -> [3]
1878 // Dim: 16 / 4 -> [4]
1879 AddSubrangeType(AR);
1880 TIArrayType = TIElementType;
1881
1882 // The current ElementType can be a modifier, in which case we need to
1883 // get the type being modified.
1884 // If TypeIndex is not a simple type, check if we have a qualified type.
1885 if (!TIElementType.isSimple()) {
1886 CVType CVElementType = Types.getType(TIElementType);
1887 if (CVElementType.kind() == LF_MODIFIER) {
1888 LVElement *QualifiedType =
1889 Shared->TypeRecords.find(StreamTPI, TIElementType);
1890 if (Error Err =
1891 finishVisitation(CVElementType, TIElementType, QualifiedType))
1892 return Err;
1893 // Get the TypeIndex of the type that the LF_MODIFIER modifies.
1894 TIElementType = getModifiedType(CVElementType);
1895 }
1896 }
1897 // Ends the traversal, as we have reached a simple type (int, char, etc).
1898 if (TIElementType.isSimple())
1899 break;
1900
1901 // Read next dimension linked entry, if any.
1902 CVEntry = Types.getType(TIElementType);
1904 const_cast<CVType &>(CVEntry), AR)) {
1905 consumeError(std::move(Err));
1906 break;
1907 }
1908 TIElementType = AR.getElementType();
1909 // NOTE: The typeindex has a value of: 0x0280.0000
1910 getTrueType(TIElementType);
1911 }
1912
1913 Array->setName(AT.getName());
1914 TIArrayType = Shared->ForwardReferences.remap(TIArrayType);
1915 Array->setType(getElement(StreamTPI, TIArrayType));
1916
1917 if (PrevSubrange)
1918 // In the case of an aggregate type (class, struct, union, interface),
1919 // get the aggregate size. As the original record is pointing to its
1920 // reference, we have to update it.
1921 if (uint64_t Size =
1922 isAggregate(CVEntry)
1923 ? getSizeInBytesForTypeRecord(Types.getType(TIArrayType))
1924 : getSizeInBytesForTypeIndex(TIElementType))
1925 PrevSubrange->setCount(PrevSubrange->getCount() / Size);
1926
1927 return Error::success();
1928}
1929
1930// LF_BITFIELD (TPI)
1932 TypeIndex TI, LVElement *Element) {
1933 LLVM_DEBUG({
1934 printTypeBegin(Record, TI, Element, StreamTPI);
1935 printTypeIndex("Type", TI, StreamTPI);
1936 W.printNumber("BitSize", BF.getBitSize());
1937 W.printNumber("BitOffset", BF.getBitOffset());
1939 });
1940
1941 Element->setType(getElement(StreamTPI, BF.getType()));
1942 Element->setBitSize(BF.getBitSize());
1943 return Error::success();
1944}
1945
1946// LF_BUILDINFO (TPI)/(IPI)
1948 TypeIndex TI, LVElement *Element) {
1949 LLVM_DEBUG({
1950 printTypeBegin(Record, TI, Element, StreamIPI);
1951 W.printNumber("NumArgs", static_cast<uint32_t>(BI.getArgs().size()));
1952 ListScope Arguments(W, "Arguments");
1953 for (TypeIndex Arg : BI.getArgs())
1954 printTypeIndex("ArgType", Arg, StreamIPI);
1956 });
1957
1958 // The given 'Element' refers to the current compilation unit.
1959 // All the args are references into the TPI/IPI stream.
1960 TypeIndex TIName = BI.getArgs()[BuildInfoRecord::BuildInfoArg::SourceFile];
1961 std::string Name = std::string(ids().getTypeName(TIName));
1962
1963 // There are cases where LF_BUILDINFO fields are empty.
1964 if (!Name.empty())
1965 Element->setName(Name);
1966
1967 return Error::success();
1968}
1969
1970// LF_CLASS, LF_STRUCTURE, LF_INTERFACE (TPI)
1972 TypeIndex TI, LVElement *Element) {
1973 LLVM_DEBUG({
1974 printTypeBegin(Record, TI, Element, StreamTPI);
1975 W.printNumber("MemberCount", Class.getMemberCount());
1976 printTypeIndex("FieldList", Class.getFieldList(), StreamTPI);
1977 printTypeIndex("DerivedFrom", Class.getDerivationList(), StreamTPI);
1978 printTypeIndex("VShape", Class.getVTableShape(), StreamTPI);
1979 W.printNumber("SizeOf", Class.getSize());
1980 W.printString("Name", Class.getName());
1981 if (Class.hasUniqueName())
1982 W.printString("UniqueName", Class.getUniqueName());
1984 });
1985
1986 if (Element->getIsFinalized())
1987 return Error::success();
1988 Element->setIsFinalized();
1989
1990 LVScopeAggregate *Scope = static_cast<LVScopeAggregate *>(Element);
1991 if (!Scope)
1992 return Error::success();
1993
1994 Scope->setName(Class.getName());
1995 if (Class.hasUniqueName())
1996 Scope->setLinkageName(Class.getUniqueName());
1997
1998 if (Class.isNested()) {
1999 Scope->setIsNested();
2000 createParents(Class.getName(), Scope);
2001 }
2002
2003 if (Class.isScoped())
2004 Scope->setIsScoped();
2005
2006 // Nested types will be added to their parents at creation. The forward
2007 // references are only processed to finish the referenced element creation.
2008 if (!(Class.isNested() || Class.isScoped())) {
2009 if (LVScope *Namespace = Shared->NamespaceDeduction.get(Class.getName()))
2010 Namespace->addElement(Scope);
2011 else
2012 Reader->getCompileUnit()->addElement(Scope);
2013 }
2014
2016 TypeIndex TIFieldList = Class.getFieldList();
2017 if (TIFieldList.isNoneType()) {
2018 TypeIndex ForwardType = Shared->ForwardReferences.find(Class.getName());
2019 if (!ForwardType.isNoneType()) {
2020 CVType CVReference = Types.getType(ForwardType);
2021 TypeRecordKind RK = static_cast<TypeRecordKind>(CVReference.kind());
2022 ClassRecord ReferenceRecord(RK);
2024 const_cast<CVType &>(CVReference), ReferenceRecord))
2025 return Err;
2026 TIFieldList = ReferenceRecord.getFieldList();
2027 }
2028 }
2029
2030 if (!TIFieldList.isNoneType()) {
2031 // Pass down the TypeIndex 'TI' for the aggregate containing the field list.
2032 CVType CVFieldList = Types.getType(TIFieldList);
2033 if (Error Err = finishVisitation(CVFieldList, TI, Scope))
2034 return Err;
2035 }
2036
2037 return Error::success();
2038}
2039
2040// LF_ENUM (TPI)
2042 TypeIndex TI, LVElement *Element) {
2043 LLVM_DEBUG({
2044 printTypeBegin(Record, TI, Element, StreamTPI);
2045 W.printNumber("NumEnumerators", Enum.getMemberCount());
2046 printTypeIndex("UnderlyingType", Enum.getUnderlyingType(), StreamTPI);
2047 printTypeIndex("FieldListType", Enum.getFieldList(), StreamTPI);
2048 W.printString("Name", Enum.getName());
2050 });
2051
2052 LVScopeEnumeration *Scope = static_cast<LVScopeEnumeration *>(Element);
2053 if (!Scope)
2054 return Error::success();
2055
2056 if (Scope->getIsFinalized())
2057 return Error::success();
2058 Scope->setIsFinalized();
2059
2060 // Set the name, as in the case of nested, it would determine the relation
2061 // to any potential parent, via the LF_NESTTYPE record.
2062 Scope->setName(Enum.getName());
2063 if (Enum.hasUniqueName())
2064 Scope->setLinkageName(Enum.getUniqueName());
2065
2066 Scope->setType(getElement(StreamTPI, Enum.getUnderlyingType()));
2067
2068 if (Enum.isNested()) {
2069 Scope->setIsNested();
2070 createParents(Enum.getName(), Scope);
2071 }
2072
2073 if (Enum.isScoped()) {
2074 Scope->setIsScoped();
2075 Scope->setIsEnumClass();
2076 }
2077
2078 // Nested types will be added to their parents at creation.
2079 if (!(Enum.isNested() || Enum.isScoped())) {
2080 if (LVScope *Namespace = Shared->NamespaceDeduction.get(Enum.getName()))
2081 Namespace->addElement(Scope);
2082 else
2083 Reader->getCompileUnit()->addElement(Scope);
2084 }
2085
2086 TypeIndex TIFieldList = Enum.getFieldList();
2087 if (!TIFieldList.isNoneType()) {
2089 CVType CVFieldList = Types.getType(TIFieldList);
2090 if (Error Err = finishVisitation(CVFieldList, TIFieldList, Scope))
2091 return Err;
2092 }
2093
2094 return Error::success();
2095}
2096
2097// LF_FIELDLIST (TPI)
2100 TypeIndex TI, LVElement *Element) {
2101 LLVM_DEBUG({
2102 printTypeBegin(Record, TI, Element, StreamTPI);
2104 });
2105
2106 if (Error Err = visitFieldListMemberStream(TI, Element, FieldList.Data))
2107 return Err;
2108
2109 return Error::success();
2110}
2111
2112// LF_FUNC_ID (TPI)/(IPI)
2114 TypeIndex TI, LVElement *Element) {
2115 // ParentScope and FunctionType are references into the TPI stream.
2116 LLVM_DEBUG({
2117 printTypeBegin(Record, TI, Element, StreamIPI);
2118 printTypeIndex("ParentScope", Func.getParentScope(), StreamTPI);
2119 printTypeIndex("FunctionType", Func.getFunctionType(), StreamTPI);
2120 W.printString("Name", Func.getName());
2122 });
2123
2124 // The TypeIndex (LF_PROCEDURE) returned by 'getFunctionType' is the
2125 // function propotype, we need to use the function definition.
2126 if (LVScope *FunctionDcl = static_cast<LVScope *>(Element)) {
2127 // For inlined functions, the inlined instance has been already processed
2128 // (all its information is contained in the Symbols section).
2129 // 'Element' points to the created 'abstract' (out-of-line) function.
2130 // Use the parent scope information to allocate it to the correct scope.
2132 TypeIndex TIParent = Func.getParentScope();
2133 if (FunctionDcl->getIsInlinedAbstract()) {
2134 FunctionDcl->setName(Func.getName());
2135 if (TIParent.isNoneType())
2136 Reader->getCompileUnit()->addElement(FunctionDcl);
2137 }
2138
2139 if (!TIParent.isNoneType()) {
2140 CVType CVParentScope = ids().getType(TIParent);
2141 if (Error Err = finishVisitation(CVParentScope, TIParent, FunctionDcl))
2142 return Err;
2143 }
2144
2145 TypeIndex TIFunctionType = Func.getFunctionType();
2146 CVType CVFunctionType = Types.getType(TIFunctionType);
2147 if (Error Err =
2148 finishVisitation(CVFunctionType, TIFunctionType, FunctionDcl))
2149 return Err;
2150
2151 FunctionDcl->setIsFinalized();
2152 }
2153
2154 return Error::success();
2155}
2156
2157// LF_LABEL (TPI)
2159 TypeIndex TI, LVElement *Element) {
2160 LLVM_DEBUG({
2161 printTypeBegin(Record, TI, Element, StreamTPI);
2163 });
2164 return Error::success();
2165}
2166
2167// LF_MFUNC_ID (TPI)/(IPI)
2169 TypeIndex TI, LVElement *Element) {
2170 // ClassType and FunctionType are references into the TPI stream.
2171 LLVM_DEBUG({
2172 printTypeBegin(Record, TI, Element, StreamIPI);
2173 printTypeIndex("ClassType", Id.getClassType(), StreamTPI);
2174 printTypeIndex("FunctionType", Id.getFunctionType(), StreamTPI);
2175 W.printString("Name", Id.getName());
2177 });
2178
2179 LVScope *FunctionDcl = static_cast<LVScope *>(Element);
2180 if (FunctionDcl->getIsInlinedAbstract()) {
2181 // For inlined functions, the inlined instance has been already processed
2182 // (all its information is contained in the Symbols section).
2183 // 'Element' points to the created 'abstract' (out-of-line) function.
2184 // Use the parent scope information to allocate it to the correct scope.
2185 if (LVScope *Class = static_cast<LVScope *>(
2186 Shared->TypeRecords.find(StreamTPI, Id.getClassType())))
2187 Class->addElement(FunctionDcl);
2188 }
2189
2190 TypeIndex TIFunctionType = Id.getFunctionType();
2191 CVType CVFunction = types().getType(TIFunctionType);
2192 if (Error Err = finishVisitation(CVFunction, TIFunctionType, Element))
2193 return Err;
2194
2195 return Error::success();
2196}
2197
2198// LF_MFUNCTION (TPI)
2201 LVElement *Element) {
2202 LLVM_DEBUG({
2203 printTypeBegin(Record, TI, Element, StreamTPI);
2204 printTypeIndex("ReturnType", MF.getReturnType(), StreamTPI);
2205 printTypeIndex("ClassType", MF.getClassType(), StreamTPI);
2206 printTypeIndex("ThisType", MF.getThisType(), StreamTPI);
2207 W.printNumber("NumParameters", MF.getParameterCount());
2208 printTypeIndex("ArgListType", MF.getArgumentList(), StreamTPI);
2209 W.printNumber("ThisAdjustment", MF.getThisPointerAdjustment());
2211 });
2212
2213 if (LVScope *MemberFunction = static_cast<LVScope *>(Element)) {
2215
2216 MemberFunction->setIsFinalized();
2217 MemberFunction->setType(getElement(StreamTPI, MF.getReturnType()));
2218 MemberFunction->setOffset(TI.getIndex());
2219 MemberFunction->setOffsetFromTypeIndex();
2220
2221 if (ProcessArgumentList) {
2222 ProcessArgumentList = false;
2223
2224 if (!MemberFunction->getIsStatic()) {
2225 LVElement *ThisPointer = getElement(StreamTPI, MF.getThisType());
2226 // When creating the 'this' pointer, check if it points to a reference.
2227 ThisPointer->setType(Class);
2228 LVSymbol *This =
2229 createParameter(ThisPointer, StringRef(), MemberFunction);
2230 This->setIsArtificial();
2231 }
2232
2233 // Create formal parameters.
2235 CVType CVArguments = Types.getType(MF.getArgumentList());
2236 if (Error Err = finishVisitation(CVArguments, MF.getArgumentList(),
2237 MemberFunction))
2238 return Err;
2239 }
2240 }
2241
2242 return Error::success();
2243}
2244
2245// LF_METHODLIST (TPI)
2247 MethodOverloadListRecord &Overloads,
2248 TypeIndex TI, LVElement *Element) {
2249 LLVM_DEBUG({
2250 printTypeBegin(Record, TI, Element, StreamTPI);
2252 });
2253
2254 for (OneMethodRecord &Method : Overloads.Methods) {
2256 Record.Kind = LF_METHOD;
2257 Method.Name = OverloadedMethodName;
2258 if (Error Err = visitKnownMember(Record, Method, TI, Element))
2259 return Err;
2260 }
2261
2262 return Error::success();
2263}
2264
2265// LF_MODIFIER (TPI)
2267 TypeIndex TI, LVElement *Element) {
2268 LLVM_DEBUG({
2269 printTypeBegin(Record, TI, Element, StreamTPI);
2270 printTypeIndex("ModifiedType", Mod.getModifiedType(), StreamTPI);
2272 });
2273
2274 // Create the modified type, which will be attached to the type(s) that
2275 // contains the modifiers.
2276 LVElement *ModifiedType = getElement(StreamTPI, Mod.getModifiedType());
2277
2278 // At this point the types recording the qualifiers do not have a
2279 // scope parent. They must be assigned to the current compile unit.
2281
2282 // The incoming element does not have a defined kind. Use the given
2283 // modifiers to complete its type. A type can have more than one modifier;
2284 // in that case, we have to create an extra type to have the other modifier.
2285 LVType *LastLink = static_cast<LVType *>(Element);
2286 if (!LastLink->getParentScope())
2287 CompileUnit->addElement(LastLink);
2288
2289 bool SeenModifier = false;
2290 uint16_t Mods = static_cast<uint16_t>(Mod.getModifiers());
2291 if (Mods & uint16_t(ModifierOptions::Const)) {
2292 SeenModifier = true;
2293 LastLink->setTag(dwarf::DW_TAG_const_type);
2294 LastLink->setIsConst();
2295 LastLink->setName("const");
2296 }
2297 if (Mods & uint16_t(ModifierOptions::Volatile)) {
2298 if (SeenModifier) {
2299 LVType *Volatile = Reader->createType();
2300 Volatile->setIsModifier();
2301 LastLink->setType(Volatile);
2302 LastLink = Volatile;
2303 CompileUnit->addElement(LastLink);
2304 }
2305 LastLink->setTag(dwarf::DW_TAG_volatile_type);
2306 LastLink->setIsVolatile();
2307 LastLink->setName("volatile");
2308 }
2309 if (Mods & uint16_t(ModifierOptions::Unaligned)) {
2310 if (SeenModifier) {
2311 LVType *Unaligned = Reader->createType();
2312 Unaligned->setIsModifier();
2313 LastLink->setType(Unaligned);
2314 LastLink = Unaligned;
2315 CompileUnit->addElement(LastLink);
2316 }
2318 LastLink->setIsUnaligned();
2319 LastLink->setName("unaligned");
2320 }
2321
2322 LastLink->setType(ModifiedType);
2323 return Error::success();
2324}
2325
2326// LF_POINTER (TPI)
2328 TypeIndex TI, LVElement *Element) {
2329 LLVM_DEBUG({
2330 printTypeBegin(Record, TI, Element, StreamTPI);
2331 printTypeIndex("PointeeType", Ptr.getReferentType(), StreamTPI);
2332 W.printNumber("IsFlat", Ptr.isFlat());
2333 W.printNumber("IsConst", Ptr.isConst());
2334 W.printNumber("IsVolatile", Ptr.isVolatile());
2335 W.printNumber("IsUnaligned", Ptr.isUnaligned());
2336 W.printNumber("IsRestrict", Ptr.isRestrict());
2337 W.printNumber("IsThisPtr&", Ptr.isLValueReferenceThisPtr());
2338 W.printNumber("IsThisPtr&&", Ptr.isRValueReferenceThisPtr());
2339 W.printNumber("SizeOf", Ptr.getSize());
2340
2341 if (Ptr.isPointerToMember()) {
2342 const MemberPointerInfo &MI = Ptr.getMemberInfo();
2343 printTypeIndex("ClassType", MI.getContainingType(), StreamTPI);
2344 }
2346 });
2347
2348 // Find the pointed-to type.
2349 LVType *Pointer = static_cast<LVType *>(Element);
2350 LVElement *Pointee = nullptr;
2351
2352 PointerMode Mode = Ptr.getMode();
2353 Pointee = Ptr.isPointerToMember()
2354 ? Shared->TypeRecords.find(StreamTPI, Ptr.getReferentType())
2355 : getElement(StreamTPI, Ptr.getReferentType());
2356
2357 // At this point the types recording the qualifiers do not have a
2358 // scope parent. They must be assigned to the current compile unit.
2360
2361 // Order for the different modifiers:
2362 // <restrict> <pointer, Reference, ValueReference> <const, volatile>
2363 // Const and volatile already processed.
2364 bool SeenModifier = false;
2365 LVType *LastLink = Pointer;
2366 if (!LastLink->getParentScope())
2367 CompileUnit->addElement(LastLink);
2368
2369 if (Ptr.isRestrict()) {
2370 SeenModifier = true;
2371 LVType *Restrict = Reader->createType();
2372 Restrict->setTag(dwarf::DW_TAG_restrict_type);
2373 Restrict->setIsRestrict();
2374 Restrict->setName("restrict");
2375 LastLink->setType(Restrict);
2376 LastLink = Restrict;
2377 CompileUnit->addElement(LastLink);
2378 }
2379 if (Mode == PointerMode::LValueReference) {
2380 if (SeenModifier) {
2381 LVType *LReference = Reader->createType();
2382 LReference->setIsModifier();
2383 LastLink->setType(LReference);
2384 LastLink = LReference;
2385 CompileUnit->addElement(LastLink);
2386 }
2387 LastLink->setTag(dwarf::DW_TAG_reference_type);
2388 LastLink->setIsReference();
2389 LastLink->setName("&");
2390 }
2391 if (Mode == PointerMode::RValueReference) {
2392 if (SeenModifier) {
2393 LVType *RReference = Reader->createType();
2394 RReference->setIsModifier();
2395 LastLink->setType(RReference);
2396 LastLink = RReference;
2397 CompileUnit->addElement(LastLink);
2398 }
2399 LastLink->setTag(dwarf::DW_TAG_rvalue_reference_type);
2400 LastLink->setIsRvalueReference();
2401 LastLink->setName("&&");
2402 }
2403
2404 // When creating the pointer, check if it points to a reference.
2405 LastLink->setType(Pointee);
2406 return Error::success();
2407}
2408
2409// LF_PROCEDURE (TPI)
2411 TypeIndex TI, LVElement *Element) {
2412 LLVM_DEBUG({
2413 printTypeBegin(Record, TI, Element, StreamTPI);
2414 printTypeIndex("ReturnType", Proc.getReturnType(), StreamTPI);
2415 W.printNumber("NumParameters", Proc.getParameterCount());
2416 printTypeIndex("ArgListType", Proc.getArgumentList(), StreamTPI);
2418 });
2419
2420 // There is no need to traverse the argument list, as the CodeView format
2421 // declares the parameters as a 'S_LOCAL' symbol tagged as parameter.
2422 // Only process parameters when dealing with inline functions.
2423 if (LVScope *FunctionDcl = static_cast<LVScope *>(Element)) {
2424 FunctionDcl->setType(getElement(StreamTPI, Proc.getReturnType()));
2425
2426 if (ProcessArgumentList) {
2427 ProcessArgumentList = false;
2428 // Create formal parameters.
2430 CVType CVArguments = Types.getType(Proc.getArgumentList());
2431 if (Error Err = finishVisitation(CVArguments, Proc.getArgumentList(),
2432 FunctionDcl))
2433 return Err;
2434 }
2435 }
2436
2437 return Error::success();
2438}
2439
2440// LF_UNION (TPI)
2442 TypeIndex TI, LVElement *Element) {
2443 LLVM_DEBUG({
2444 printTypeBegin(Record, TI, Element, StreamTPI);
2445 W.printNumber("MemberCount", Union.getMemberCount());
2446 printTypeIndex("FieldList", Union.getFieldList(), StreamTPI);
2447 W.printNumber("SizeOf", Union.getSize());
2448 W.printString("Name", Union.getName());
2449 if (Union.hasUniqueName())
2450 W.printString("UniqueName", Union.getUniqueName());
2452 });
2453
2454 LVScopeAggregate *Scope = static_cast<LVScopeAggregate *>(Element);
2455 if (!Scope)
2456 return Error::success();
2457
2458 if (Scope->getIsFinalized())
2459 return Error::success();
2460 Scope->setIsFinalized();
2461
2462 Scope->setName(Union.getName());
2463 if (Union.hasUniqueName())
2464 Scope->setLinkageName(Union.getUniqueName());
2465
2466 if (Union.isNested()) {
2467 Scope->setIsNested();
2468 createParents(Union.getName(), Scope);
2469 } else {
2470 if (LVScope *Namespace = Shared->NamespaceDeduction.get(Union.getName()))
2471 Namespace->addElement(Scope);
2472 else
2473 Reader->getCompileUnit()->addElement(Scope);
2474 }
2475
2476 if (!Union.getFieldList().isNoneType()) {
2478 // Pass down the TypeIndex 'TI' for the aggregate containing the field list.
2479 CVType CVFieldList = Types.getType(Union.getFieldList());
2480 if (Error Err = finishVisitation(CVFieldList, TI, Scope))
2481 return Err;
2482 }
2483
2484 return Error::success();
2485}
2486
2487// LF_TYPESERVER2 (TPI)
2489 TypeIndex TI, LVElement *Element) {
2490 LLVM_DEBUG({
2491 printTypeBegin(Record, TI, Element, StreamTPI);
2492 W.printString("Guid", formatv("{0}", TS.getGuid()).str());
2493 W.printNumber("Age", TS.getAge());
2494 W.printString("Name", TS.getName());
2496 });
2497 return Error::success();
2498}
2499
2500// LF_VFTABLE (TPI)
2502 TypeIndex TI, LVElement *Element) {
2503 LLVM_DEBUG({
2504 printTypeBegin(Record, TI, Element, StreamTPI);
2505 printTypeIndex("CompleteClass", VFT.getCompleteClass(), StreamTPI);
2506 printTypeIndex("OverriddenVFTable", VFT.getOverriddenVTable(), StreamTPI);
2507 W.printHex("VFPtrOffset", VFT.getVFPtrOffset());
2508 W.printString("VFTableName", VFT.getName());
2509 for (const StringRef &N : VFT.getMethodNames())
2510 W.printString("MethodName", N);
2512 });
2513 return Error::success();
2514}
2515
2516// LF_VTSHAPE (TPI)
2518 VFTableShapeRecord &Shape,
2519 TypeIndex TI, LVElement *Element) {
2520 LLVM_DEBUG({
2521 printTypeBegin(Record, TI, Element, StreamTPI);
2522 W.printNumber("VFEntryCount", Shape.getEntryCount());
2524 });
2525 return Error::success();
2526}
2527
2528// LF_SUBSTR_LIST (TPI)/(IPI)
2530 StringListRecord &Strings,
2531 TypeIndex TI, LVElement *Element) {
2532 // All the indices are references into the TPI/IPI stream.
2533 LLVM_DEBUG({
2534 printTypeBegin(Record, TI, Element, StreamIPI);
2535 ArrayRef<TypeIndex> Indices = Strings.getIndices();
2536 uint32_t Size = Indices.size();
2537 W.printNumber("NumStrings", Size);
2538 ListScope Arguments(W, "Strings");
2539 for (uint32_t I = 0; I < Size; ++I)
2540 printTypeIndex("String", Indices[I], StreamIPI);
2542 });
2543 return Error::success();
2544}
2545
2546// LF_STRING_ID (TPI)/(IPI)
2548 TypeIndex TI, LVElement *Element) {
2549 // All args are references into the TPI/IPI stream.
2550 LLVM_DEBUG({
2551 printTypeIndex("\nTI", TI, StreamIPI);
2552 printTypeIndex("Id", String.getId(), StreamIPI);
2553 W.printString("StringData", String.getString());
2554 });
2555
2556 if (LVScope *Namespace = Shared->NamespaceDeduction.get(
2557 String.getString(), /*CheckScope=*/false)) {
2558 // The function is already at different scope. In order to reflect
2559 // the correct parent, move it to the namespace.
2560 if (LVScope *Scope = Element->getParentScope())
2561 Scope->removeElement(Element);
2562 Namespace->addElement(Element);
2563 }
2564
2565 return Error::success();
2566}
2567
2568// LF_UDT_SRC_LINE (TPI)/(IPI)
2570 UdtSourceLineRecord &SourceLine,
2571 TypeIndex TI, LVElement *Element) {
2572 // All args are references into the TPI/IPI stream.
2573 LLVM_DEBUG({
2574 printTypeIndex("\nTI", TI, StreamIPI);
2575 printTypeIndex("UDT", SourceLine.getUDT(), StreamIPI);
2576 printTypeIndex("SourceFile", SourceLine.getSourceFile(), StreamIPI);
2577 W.printNumber("LineNumber", SourceLine.getLineNumber());
2578 });
2579 return Error::success();
2580}
2581
2582// LF_UDT_MOD_SRC_LINE (TPI)/(IPI)
2584 UdtModSourceLineRecord &ModSourceLine,
2585 TypeIndex TI, LVElement *Element) {
2586 // All args are references into the TPI/IPI stream.
2587 LLVM_DEBUG({
2588 printTypeBegin(Record, TI, Element, StreamIPI);
2589 printTypeIndex("\nTI", TI, StreamIPI);
2590 printTypeIndex("UDT", ModSourceLine.getUDT(), StreamIPI);
2591 printTypeIndex("SourceFile", ModSourceLine.getSourceFile(), StreamIPI);
2592 W.printNumber("LineNumber", ModSourceLine.getLineNumber());
2593 W.printNumber("Module", ModSourceLine.getModule());
2595 });
2596 return Error::success();
2597}
2598
2599// LF_PRECOMP (TPI)
2601 TypeIndex TI, LVElement *Element) {
2602 LLVM_DEBUG({
2603 printTypeBegin(Record, TI, Element, StreamTPI);
2604 W.printHex("StartIndex", Precomp.getStartTypeIndex());
2605 W.printHex("Count", Precomp.getTypesCount());
2606 W.printHex("Signature", Precomp.getSignature());
2607 W.printString("PrecompFile", Precomp.getPrecompFilePath());
2609 });
2610 return Error::success();
2611}
2612
2613// LF_ENDPRECOMP (TPI)
2615 EndPrecompRecord &EndPrecomp,
2616 TypeIndex TI, LVElement *Element) {
2617 LLVM_DEBUG({
2618 printTypeBegin(Record, TI, Element, StreamTPI);
2619 W.printHex("Signature", EndPrecomp.getSignature());
2621 });
2622 return Error::success();
2623}
2624
2626 TypeIndex TI) {
2627 LLVM_DEBUG({ W.printHex("UnknownMember", unsigned(Record.Kind)); });
2628 return Error::success();
2629}
2630
2631// LF_BCLASS, LF_BINTERFACE
2634 LVElement *Element) {
2635 LLVM_DEBUG({
2636 printMemberBegin(Record, TI, Element, StreamTPI);
2637 printTypeIndex("BaseType", Base.getBaseType(), StreamTPI);
2638 W.printHex("BaseOffset", Base.getBaseOffset());
2640 });
2641
2642 createElement(Record.Kind);
2643 if (LVSymbol *Symbol = CurrentSymbol) {
2644 LVElement *BaseClass = getElement(StreamTPI, Base.getBaseType());
2645 Symbol->setName(BaseClass->getName());
2646 Symbol->setType(BaseClass);
2647 Symbol->setAccessibilityCode(Base.getAccess());
2648 static_cast<LVScope *>(Element)->addElement(Symbol);
2649 }
2650
2651 return Error::success();
2652}
2653
2654// LF_MEMBER
2657 LVElement *Element) {
2658 LLVM_DEBUG({
2659 printMemberBegin(Record, TI, Element, StreamTPI);
2660 printTypeIndex("Type", Field.getType(), StreamTPI);
2661 W.printHex("FieldOffset", Field.getFieldOffset());
2662 W.printString("Name", Field.getName());
2664 });
2665
2666 // Create the data member.
2667 createDataMember(Record, static_cast<LVScope *>(Element), Field.getName(),
2668 Field.getType(), Field.getAccess());
2669 return Error::success();
2670}
2671
2672// LF_ENUMERATE
2675 LVElement *Element) {
2676 LLVM_DEBUG({
2677 printMemberBegin(Record, TI, Element, StreamTPI);
2678 W.printNumber("EnumValue", Enum.getValue());
2679 W.printString("Name", Enum.getName());
2681 });
2682
2683 createElement(Record.Kind);
2684 if (LVType *Type = CurrentType) {
2685 Type->setName(Enum.getName());
2687 Enum.getValue().toString(Value, 16, true, true);
2688 Type->setValue(Value);
2689 static_cast<LVScope *>(Element)->addElement(CurrentType);
2690 }
2691
2692 return Error::success();
2693}
2694
2695// LF_INDEX
2698 TypeIndex TI, LVElement *Element) {
2699 LLVM_DEBUG({
2700 printMemberBegin(Record, TI, Element, StreamTPI);
2701 printTypeIndex("ContinuationIndex", Cont.getContinuationIndex(), StreamTPI);
2703 });
2704 return Error::success();
2705}
2706
2707// LF_NESTTYPE
2710 LVElement *Element) {
2711 LLVM_DEBUG({
2712 printMemberBegin(Record, TI, Element, StreamTPI);
2713 printTypeIndex("Type", Nested.getNestedType(), StreamTPI);
2714 W.printString("Name", Nested.getName());
2716 });
2717
2718 if (LVElement *Typedef = createElement(SymbolKind::S_UDT)) {
2719 Typedef->setName(Nested.getName());
2720 LVElement *NestedType = getElement(StreamTPI, Nested.getNestedType());
2721 Typedef->setType(NestedType);
2722 LVScope *Scope = static_cast<LVScope *>(Element);
2723 Scope->addElement(Typedef);
2724
2725 if (NestedType && NestedType->getIsNested()) {
2726 // 'Element' is an aggregate type that may contains this nested type
2727 // definition. Used their scoped names, to decide on their relationship.
2728 StringRef RecordName = getRecordName(types(), TI);
2729
2730 StringRef NestedTypeName = NestedType->getName();
2731 if (NestedTypeName.size() && RecordName.size()) {
2732 StringRef OuterComponent;
2733 std::tie(OuterComponent, std::ignore) =
2734 getInnerComponent(NestedTypeName);
2735 // We have an already created nested type. Add it to the current scope
2736 // and update all its children if any.
2737 if (OuterComponent.size() && OuterComponent == RecordName) {
2738 if (!NestedType->getIsScopedAlready()) {
2739 Scope->addElement(NestedType);
2740 NestedType->setIsScopedAlready();
2741 NestedType->updateLevel(Scope);
2742 }
2743 Typedef->resetIncludeInPrint();
2744 }
2745 }
2746 }
2747 }
2748
2749 return Error::success();
2750}
2751
2752// LF_ONEMETHOD
2754 OneMethodRecord &Method, TypeIndex TI,
2755 LVElement *Element) {
2756 LLVM_DEBUG({
2757 printMemberBegin(Record, TI, Element, StreamTPI);
2758 printTypeIndex("Type", Method.getType(), StreamTPI);
2759 // If virtual, then read the vftable offset.
2760 if (Method.isIntroducingVirtual())
2761 W.printHex("VFTableOffset", Method.getVFTableOffset());
2762 W.printString("Name", Method.getName());
2764 });
2765
2766 // All the LF_ONEMETHOD objects share the same type description.
2767 // We have to create a scope object for each one and get the required
2768 // information from the LF_MFUNCTION object.
2769 ProcessArgumentList = true;
2770 if (LVElement *MemberFunction = createElement(TypeLeafKind::LF_ONEMETHOD)) {
2771 MemberFunction->setIsFinalized();
2772 static_cast<LVScope *>(Element)->addElement(MemberFunction);
2773
2774 MemberFunction->setName(Method.getName());
2775 MemberFunction->setAccessibilityCode(Method.getAccess());
2776
2777 MethodKind Kind = Method.getMethodKind();
2778 if (Kind == MethodKind::Static)
2779 MemberFunction->setIsStatic();
2780 MemberFunction->setVirtualityCode(Kind);
2781
2782 MethodOptions Flags = Method.Attrs.getFlags();
2783 if (MethodOptions::CompilerGenerated ==
2784 (Flags & MethodOptions::CompilerGenerated))
2785 MemberFunction->setIsArtificial();
2786
2788 CVType CVMethodType = Types.getType(Method.getType());
2789 if (Error Err =
2790 finishVisitation(CVMethodType, Method.getType(), MemberFunction))
2791 return Err;
2792 }
2793 ProcessArgumentList = false;
2794
2795 return Error::success();
2796}
2797
2798// LF_METHOD
2800 OverloadedMethodRecord &Method,
2801 TypeIndex TI, LVElement *Element) {
2802 LLVM_DEBUG({
2803 printMemberBegin(Record, TI, Element, StreamTPI);
2804 W.printHex("MethodCount", Method.getNumOverloads());
2805 printTypeIndex("MethodListIndex", Method.getMethodList(), StreamTPI);
2806 W.printString("Name", Method.getName());
2808 });
2809
2810 // Record the overloaded method name, which will be used during the
2811 // traversal of the method list.
2813 OverloadedMethodName = Method.getName();
2814 CVType CVMethods = Types.getType(Method.getMethodList());
2815 if (Error Err = finishVisitation(CVMethods, Method.getMethodList(), Element))
2816 return Err;
2817
2818 return Error::success();
2819}
2820
2821// LF_STMEMBER
2824 TypeIndex TI, LVElement *Element) {
2825 LLVM_DEBUG({
2826 printMemberBegin(Record, TI, Element, StreamTPI);
2827 printTypeIndex("Type", Field.getType(), StreamTPI);
2828 W.printString("Name", Field.getName());
2830 });
2831
2832 // Create the data member.
2833 createDataMember(Record, static_cast<LVScope *>(Element), Field.getName(),
2834 Field.getType(), Field.getAccess());
2835 return Error::success();
2836}
2837
2838// LF_VFUNCTAB
2840 VFPtrRecord &VFTable, TypeIndex TI,
2841 LVElement *Element) {
2842 LLVM_DEBUG({
2843 printMemberBegin(Record, TI, Element, StreamTPI);
2844 printTypeIndex("Type", VFTable.getType(), StreamTPI);
2846 });
2847 return Error::success();
2848}
2849
2850// LF_VBCLASS, LF_IVBCLASS
2853 TypeIndex TI, LVElement *Element) {
2854 LLVM_DEBUG({
2855 printMemberBegin(Record, TI, Element, StreamTPI);
2856 printTypeIndex("BaseType", Base.getBaseType(), StreamTPI);
2857 printTypeIndex("VBPtrType", Base.getVBPtrType(), StreamTPI);
2858 W.printHex("VBPtrOffset", Base.getVBPtrOffset());
2859 W.printHex("VBTableIndex", Base.getVTableIndex());
2861 });
2862
2863 createElement(Record.Kind);
2864 if (LVSymbol *Symbol = CurrentSymbol) {
2865 LVElement *BaseClass = getElement(StreamTPI, Base.getBaseType());
2866 Symbol->setName(BaseClass->getName());
2867 Symbol->setType(BaseClass);
2868 Symbol->setAccessibilityCode(Base.getAccess());
2869 Symbol->setVirtualityCode(MethodKind::Virtual);
2870 static_cast<LVScope *>(Element)->addElement(Symbol);
2871 }
2872
2873 return Error::success();
2874}
2875
2877 TypeVisitorCallbacks &Callbacks,
2878 TypeIndex TI, LVElement *Element) {
2879 if (Error Err = Callbacks.visitMemberBegin(Record))
2880 return Err;
2881
2882 switch (Record.Kind) {
2883 default:
2884 if (Error Err = Callbacks.visitUnknownMember(Record))
2885 return Err;
2886 break;
2887#define MEMBER_RECORD(EnumName, EnumVal, Name) \
2888 case EnumName: { \
2889 if (Error Err = \
2890 visitKnownMember<Name##Record>(Record, Callbacks, TI, Element)) \
2891 return Err; \
2892 break; \
2893 }
2894#define MEMBER_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName) \
2895 MEMBER_RECORD(EnumVal, EnumVal, AliasName)
2896#define TYPE_RECORD(EnumName, EnumVal, Name)
2897#define TYPE_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName)
2898#include "llvm/DebugInfo/CodeView/CodeViewTypes.def"
2899 }
2900
2901 if (Error Err = Callbacks.visitMemberEnd(Record))
2902 return Err;
2903
2904 return Error::success();
2905}
2906
2908 LVElement *Element) {
2909 switch (Record.kind()) {
2910 default:
2911 if (Error Err = visitUnknownType(Record, TI))
2912 return Err;
2913 break;
2914#define TYPE_RECORD(EnumName, EnumVal, Name) \
2915 case EnumName: { \
2916 if (Error Err = visitKnownRecord<Name##Record>(Record, TI, Element)) \
2917 return Err; \
2918 break; \
2919 }
2920#define TYPE_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName) \
2921 TYPE_RECORD(EnumVal, EnumVal, AliasName)
2922#define MEMBER_RECORD(EnumName, EnumVal, Name)
2923#define MEMBER_RECORD_ALIAS(EnumName, EnumVal, Name, AliasName)
2924#include "llvm/DebugInfo/CodeView/CodeViewTypes.def"
2925 }
2926
2927 return Error::success();
2928}
2929
2930// Customized version of 'FieldListVisitHelper'.
2931Error LVLogicalVisitor::visitFieldListMemberStream(
2934 BinaryStreamReader Reader(Stream);
2935 FieldListDeserializer Deserializer(Reader);
2937 Pipeline.addCallbackToPipeline(Deserializer);
2938
2939 TypeLeafKind Leaf;
2940 while (!Reader.empty()) {
2941 if (Error Err = Reader.readEnum(Leaf))
2942 return Err;
2943
2945 Record.Kind = Leaf;
2946 if (Error Err = visitMemberRecord(Record, Pipeline, TI, Element))
2947 return Err;
2948 }
2949
2950 return Error::success();
2951}
2952
2954 // The CodeView specifications does not treat S_COMPILE2 and S_COMPILE3
2955 // as symbols that open a scope. The CodeView reader, treat them in a
2956 // similar way as DWARF. As there is no a symbole S_END to close the
2957 // compile unit, we need to check for the next compile unit.
2958 if (IsCompileUnit) {
2959 if (!ScopeStack.empty())
2960 popScope();
2961 InCompileUnitScope = true;
2962 }
2963
2964 pushScope(Scope);
2965 ReaderParent->addElement(Scope);
2966}
2967
2969 ReaderScope->addElement(Symbol);
2970}
2971
2973 ReaderScope->addElement(Type);
2974}
2975
2977 CurrentScope = nullptr;
2978 CurrentSymbol = nullptr;
2979 CurrentType = nullptr;
2980
2982 CurrentType = Reader->createType();
2983 CurrentType->setIsBase();
2984 CurrentType->setTag(dwarf::DW_TAG_base_type);
2985 if (options().getAttributeBase())
2986 CurrentType->setIncludeInPrint();
2987 return CurrentType;
2988 }
2989
2990 switch (Kind) {
2991 // Types.
2992 case TypeLeafKind::LF_ENUMERATE:
2993 CurrentType = Reader->createTypeEnumerator();
2994 CurrentType->setTag(dwarf::DW_TAG_enumerator);
2995 return CurrentType;
2996 case TypeLeafKind::LF_MODIFIER:
2997 CurrentType = Reader->createType();
2998 CurrentType->setIsModifier();
2999 return CurrentType;
3000 case TypeLeafKind::LF_POINTER:
3001 CurrentType = Reader->createType();
3002 CurrentType->setIsPointer();
3003 CurrentType->setName("*");
3004 CurrentType->setTag(dwarf::DW_TAG_pointer_type);
3005 return CurrentType;
3006
3007 // Symbols.
3008 case TypeLeafKind::LF_BCLASS:
3009 case TypeLeafKind::LF_IVBCLASS:
3010 case TypeLeafKind::LF_VBCLASS:
3011 CurrentSymbol = Reader->createSymbol();
3012 CurrentSymbol->setTag(dwarf::DW_TAG_inheritance);
3013 CurrentSymbol->setIsInheritance();
3014 return CurrentSymbol;
3015 case TypeLeafKind::LF_MEMBER:
3016 case TypeLeafKind::LF_STMEMBER:
3017 CurrentSymbol = Reader->createSymbol();
3018 CurrentSymbol->setIsMember();
3019 CurrentSymbol->setTag(dwarf::DW_TAG_member);
3020 return CurrentSymbol;
3021
3022 // Scopes.
3023 case TypeLeafKind::LF_ARRAY:
3024 CurrentScope = Reader->createScopeArray();
3025 CurrentScope->setTag(dwarf::DW_TAG_array_type);
3026 return CurrentScope;
3027 case TypeLeafKind::LF_CLASS:
3028 CurrentScope = Reader->createScopeAggregate();
3029 CurrentScope->setTag(dwarf::DW_TAG_class_type);
3030 CurrentScope->setIsClass();
3031 return CurrentScope;
3032 case TypeLeafKind::LF_ENUM:
3033 CurrentScope = Reader->createScopeEnumeration();
3034 CurrentScope->setTag(dwarf::DW_TAG_enumeration_type);
3035 return CurrentScope;
3036 case TypeLeafKind::LF_METHOD:
3037 case TypeLeafKind::LF_ONEMETHOD:
3038 case TypeLeafKind::LF_PROCEDURE:
3039 CurrentScope = Reader->createScopeFunction();
3040 CurrentScope->setIsSubprogram();
3041 CurrentScope->setTag(dwarf::DW_TAG_subprogram);
3042 return CurrentScope;
3043 case TypeLeafKind::LF_STRUCTURE:
3044 CurrentScope = Reader->createScopeAggregate();
3045 CurrentScope->setIsStructure();
3046 CurrentScope->setTag(dwarf::DW_TAG_structure_type);
3047 return CurrentScope;
3048 case TypeLeafKind::LF_UNION:
3049 CurrentScope = Reader->createScopeAggregate();
3050 CurrentScope->setIsUnion();
3051 CurrentScope->setTag(dwarf::DW_TAG_union_type);
3052 return CurrentScope;
3053 default:
3054 // If '--internal=tag' and '--print=warning' are specified in the command
3055 // line, we record and print each seen 'TypeLeafKind'.
3056 break;
3057 }
3058 return nullptr;
3059}
3060
3062 CurrentScope = nullptr;
3063 CurrentSymbol = nullptr;
3064 CurrentType = nullptr;
3065 switch (Kind) {
3066 // Types.
3067 case SymbolKind::S_UDT:
3068 CurrentType = Reader->createTypeDefinition();
3069 CurrentType->setTag(dwarf::DW_TAG_typedef);
3070 return CurrentType;
3071
3072 // Symbols.
3073 case SymbolKind::S_CONSTANT:
3074 CurrentSymbol = Reader->createSymbol();
3075 CurrentSymbol->setIsConstant();
3076 CurrentSymbol->setTag(dwarf::DW_TAG_constant);
3077 return CurrentSymbol;
3078
3079 case SymbolKind::S_BPREL32:
3080 case SymbolKind::S_REGREL32:
3081 case SymbolKind::S_GDATA32:
3082 case SymbolKind::S_LDATA32:
3083 case SymbolKind::S_LOCAL:
3084 // During the symbol traversal more information is available to
3085 // determine if the symbol is a parameter or a variable. At this
3086 // stage mark it as variable.
3087 CurrentSymbol = Reader->createSymbol();
3088 CurrentSymbol->setIsVariable();
3089 CurrentSymbol->setTag(dwarf::DW_TAG_variable);
3090 return CurrentSymbol;
3091
3092 // Scopes.
3093 case SymbolKind::S_BLOCK32:
3094 CurrentScope = Reader->createScope();
3095 CurrentScope->setIsLexicalBlock();
3096 CurrentScope->setTag(dwarf::DW_TAG_lexical_block);
3097 return CurrentScope;
3098 case SymbolKind::S_COMPILE2:
3099 case SymbolKind::S_COMPILE3:
3100 CurrentScope = Reader->createScopeCompileUnit();
3101 CurrentScope->setTag(dwarf::DW_TAG_compile_unit);
3102 Reader->setCompileUnit(static_cast<LVScopeCompileUnit *>(CurrentScope));
3103 return CurrentScope;
3104 case SymbolKind::S_INLINESITE:
3105 case SymbolKind::S_INLINESITE2:
3106 CurrentScope = Reader->createScopeFunctionInlined();
3107 CurrentScope->setIsInlinedFunction();
3108 CurrentScope->setTag(dwarf::DW_TAG_inlined_subroutine);
3109 return CurrentScope;
3110 case SymbolKind::S_LPROC32:
3111 case SymbolKind::S_GPROC32:
3112 case SymbolKind::S_LPROC32_ID:
3113 case SymbolKind::S_GPROC32_ID:
3114 case SymbolKind::S_SEPCODE:
3115 case SymbolKind::S_THUNK32:
3116 CurrentScope = Reader->createScopeFunction();
3117 CurrentScope->setIsSubprogram();
3118 CurrentScope->setTag(dwarf::DW_TAG_subprogram);
3119 return CurrentScope;
3120 default:
3121 // If '--internal=tag' and '--print=warning' are specified in the command
3122 // line, we record and print each seen 'SymbolKind'.
3123 break;
3124 }
3125 return nullptr;
3126}
3127
3129 LVElement *Element = Shared->TypeRecords.find(StreamTPI, TI);
3130 if (!Element) {
3131 // We are dealing with a base type or pointer to a base type, which are
3132 // not included explicitly in the CodeView format.
3134 Element = createElement(Kind);
3135 Element->setIsFinalized();
3136 Shared->TypeRecords.add(StreamTPI, (TypeIndex)Kind, Kind, Element);
3137 Element->setOffset(Kind);
3138 return Element;
3139 }
3140 // We are dealing with a pointer to a base type.
3142 Element = createElement(Kind);
3143 Shared->TypeRecords.add(StreamTPI, TI, Kind, Element);
3144 Element->setOffset(TI.getIndex());
3145 Element->setOffsetFromTypeIndex();
3146 return Element;
3147 }
3148
3149 W.printString("** Not implemented. **");
3150 printTypeIndex("TypeIndex", TI, StreamTPI);
3151 W.printString("TypeLeafKind", formatTypeLeafKind(Kind));
3152 return nullptr;
3153 }
3154
3155 Element->setOffset(TI.getIndex());
3156 Element->setOffsetFromTypeIndex();
3157 return Element;
3158}
3159
3160void LVLogicalVisitor::createDataMember(CVMemberRecord &Record, LVScope *Parent,
3163 LLVM_DEBUG({
3164 printTypeIndex("TypeIndex", TI, StreamTPI);
3165 W.printString("TypeName", Name);
3166 });
3167
3168 createElement(Record.Kind);
3169 if (LVSymbol *Symbol = CurrentSymbol) {
3170 Symbol->setName(Name);
3171 if (TI.isNoneType() || TI.isSimple())
3172 Symbol->setType(getElement(StreamTPI, TI));
3173 else {
3175 CVType CVMemberType = Types.getType(TI);
3176 if (CVMemberType.kind() == LF_BITFIELD) {
3177 if (Error Err = finishVisitation(CVMemberType, TI, Symbol)) {
3178 consumeError(std::move(Err));
3179 return;
3180 }
3181 } else
3182 Symbol->setType(getElement(StreamTPI, TI));
3183 }
3184 Symbol->setAccessibilityCode(Access);
3185 Parent->addElement(Symbol);
3186 }
3187}
3188
3189LVSymbol *LVLogicalVisitor::createParameter(LVElement *Element, StringRef Name,
3190 LVScope *Parent) {
3191 LVSymbol *Parameter = Reader->createSymbol();
3192 Parent->addElement(Parameter);
3193 Parameter->setIsParameter();
3194 Parameter->setTag(dwarf::DW_TAG_formal_parameter);
3195 Parameter->setName(Name);
3196 Parameter->setType(Element);
3197 return Parameter;
3198}
3199
3200LVSymbol *LVLogicalVisitor::createParameter(TypeIndex TI, StringRef Name,
3201 LVScope *Parent) {
3202 return createParameter(getElement(StreamTPI, TI), Name, Parent);
3203}
3204
3205LVType *LVLogicalVisitor::createBaseType(TypeIndex TI, StringRef TypeName) {
3206 TypeLeafKind SimpleKind = (TypeLeafKind)TI.getSimpleKind();
3207 TypeIndex TIR = (TypeIndex)SimpleKind;
3208 LLVM_DEBUG({
3209 printTypeIndex("TypeIndex", TIR, StreamTPI);
3210 W.printString("TypeName", TypeName);
3211 });
3212
3213 if (LVElement *Element = Shared->TypeRecords.find(StreamTPI, TIR))
3214 return static_cast<LVType *>(Element);
3215
3216 if (createElement(TIR, SimpleKind)) {
3217 CurrentType->setName(TypeName);
3219 }
3220 return CurrentType;
3221}
3222
3223LVType *LVLogicalVisitor::createPointerType(TypeIndex TI, StringRef TypeName) {
3224 LLVM_DEBUG({
3225 printTypeIndex("TypeIndex", TI, StreamTPI);
3226 W.printString("TypeName", TypeName);
3227 });
3228
3229 if (LVElement *Element = Shared->TypeRecords.find(StreamTPI, TI))
3230 return static_cast<LVType *>(Element);
3231
3232 LVType *Pointee = createBaseType(TI, TypeName.drop_back(1));
3233 if (createElement(TI, TypeLeafKind::LF_POINTER)) {
3234 CurrentType->setIsFinalized();
3235 CurrentType->setType(Pointee);
3237 }
3238 return CurrentType;
3239}
3240
3241void LVLogicalVisitor::createParents(StringRef ScopedName, LVElement *Element) {
3242 // For the given test case:
3243 //
3244 // struct S { enum E { ... }; };
3245 // S::E V;
3246 //
3247 // 0 | S_LOCAL `V`
3248 // type=0x1004 (S::E), flags = none
3249 // 0x1004 | LF_ENUM `S::E`
3250 // options: has unique name | is nested
3251 // 0x1009 | LF_STRUCTURE `S`
3252 // options: contains nested class
3253 //
3254 // When the local 'V' is processed, its type 'E' is created. But There is
3255 // no direct reference to its parent 'S'. We use the scoped name for 'E',
3256 // to create its parents.
3257
3258 // The input scoped name must have at least parent and nested names.
3259 // Drop the last element name, as it corresponds to the nested type.
3260 LVStringRefs Components = getAllLexicalComponents(ScopedName);
3261 if (Components.size() < 2)
3262 return;
3263 Components.pop_back();
3264
3265 LVStringRefs::size_type FirstNamespace;
3266 LVStringRefs::size_type FirstAggregate;
3267 std::tie(FirstNamespace, FirstAggregate) =
3268 Shared->NamespaceDeduction.find(Components);
3269
3270 LLVM_DEBUG({
3271 W.printString("First Namespace", Components[FirstNamespace]);
3272 W.printString("First NonNamespace", Components[FirstAggregate]);
3273 });
3274
3275 // Create any referenced namespaces.
3276 if (FirstNamespace < FirstAggregate) {
3277 Shared->NamespaceDeduction.get(
3278 LVStringRefs(Components.begin() + FirstNamespace,
3279 Components.begin() + FirstAggregate));
3280 }
3281
3282 // Traverse the enclosing scopes (aggregates) and create them. In the
3283 // case of nested empty aggregates, MSVC does not emit a full record
3284 // description. It emits only the reference record.
3285 LVScope *Aggregate = nullptr;
3286 TypeIndex TIAggregate;
3287 std::string AggregateName = getScopedName(
3288 LVStringRefs(Components.begin(), Components.begin() + FirstAggregate));
3289
3290 // This traversal is executed at least once.
3291 for (LVStringRefs::size_type Index = FirstAggregate;
3292 Index < Components.size(); ++Index) {
3293 AggregateName = getScopedName(LVStringRefs(Components.begin() + Index,
3294 Components.begin() + Index + 1),
3295 AggregateName);
3296 TIAggregate = Shared->ForwardReferences.remap(
3297 Shared->TypeRecords.find(StreamTPI, AggregateName));
3298 Aggregate =
3299 TIAggregate.isNoneType()
3300 ? nullptr
3301 : static_cast<LVScope *>(getElement(StreamTPI, TIAggregate));
3302 }
3303
3304 // Workaround for cases where LF_NESTTYPE is missing for nested templates.
3305 // If we manage to get parent information from the scoped name, we can add
3306 // the nested type without relying on the LF_NESTTYPE.
3307 if (Aggregate && !Element->getIsScopedAlready()) {
3308 Aggregate->addElement(Element);
3309 Element->setIsScopedAlready();
3310 }
3311}
3312
3314 LVScope *Parent) {
3315 LLVM_DEBUG({ printTypeIndex("TypeIndex", TI, StreamTPI); });
3316 TI = Shared->ForwardReferences.remap(TI);
3317 LLVM_DEBUG({ printTypeIndex("TypeIndex Remap", TI, StreamTPI); });
3318
3319 LVElement *Element = Shared->TypeRecords.find(StreamIdx, TI);
3320 if (!Element) {
3321 if (TI.isNoneType() || TI.isSimple()) {
3322 StringRef TypeName = TypeIndex::simpleTypeName(TI);
3323 // If the name ends with "*", create 2 logical types: a pointer and a
3324 // pointee type. TypeIndex is composed of a SympleTypeMode byte followed
3325 // by a SimpleTypeKind byte. The logical pointer will be identified by
3326 // the full TypeIndex value and the pointee by the SimpleTypeKind.
3327 return (TypeName.back() == '*') ? createPointerType(TI, TypeName)
3328 : createBaseType(TI, TypeName);
3329 }
3330
3331 LLVM_DEBUG({ W.printHex("TypeIndex not implemented: ", TI.getIndex()); });
3332 return nullptr;
3333 }
3334
3335 // The element has been finalized.
3336 if (Element->getIsFinalized())
3337 return Element;
3338
3339 // Add the element in case of a given parent.
3340 if (Parent)
3341 Parent->addElement(Element);
3342
3343 // Check for a composite type.
3345 CVType CVRecord = Types.getType(TI);
3346 if (Error Err = finishVisitation(CVRecord, TI, Element)) {
3347 consumeError(std::move(Err));
3348 return nullptr;
3349 }
3350 Element->setIsFinalized();
3351 return Element;
3352}
3353
3355 // Traverse the collected LF_UDT_SRC_LINE records and add the source line
3356 // information to the logical elements.
3357 for (const TypeIndex &Entry : Shared->LineRecords) {
3358 CVType CVRecord = ids().getType(Entry);
3361 const_cast<CVType &>(CVRecord), Line))
3362 consumeError(std::move(Err));
3363 else {
3364 LLVM_DEBUG({
3365 printTypeIndex("UDT", Line.getUDT(), StreamIPI);
3366 printTypeIndex("SourceFile", Line.getSourceFile(), StreamIPI);
3367 W.printNumber("LineNumber", Line.getLineNumber());
3368 });
3369
3370 // The TypeIndex returned by 'getUDT()' must point to an already
3371 // created logical element. If no logical element is found, it means
3372 // the LF_UDT_SRC_LINE is associated with a system TypeIndex.
3373 if (LVElement *Element = Shared->TypeRecords.find(
3374 StreamTPI, Line.getUDT(), /*Create=*/false)) {
3375 Element->setLineNumber(Line.getLineNumber());
3376 Element->setFilenameIndex(
3377 Shared->StringRecords.findIndex(Line.getSourceFile()));
3378 }
3379 }
3380 }
3381}
3382
3384 // Create namespaces.
3385 Shared->NamespaceDeduction.init();
3386}
3387
3388void LVLogicalVisitor::processFiles() { Shared->StringRecords.addFilenames(); }
3389
3391 if (!options().getInternalTag())
3392 return;
3393
3394 unsigned Count = 0;
3395 auto PrintItem = [&](StringRef Name) {
3396 auto NewLine = [&]() {
3397 if (++Count == 4) {
3398 Count = 0;
3399 OS << "\n";
3400 }
3401 };
3402 OS << format("%20s", Name.str().c_str());
3403 NewLine();
3404 };
3405
3406 OS << "\nTypes:\n";
3407 for (const TypeLeafKind &Kind : Shared->TypeKinds)
3408 PrintItem(formatTypeLeafKind(Kind));
3409 Shared->TypeKinds.clear();
3410
3411 Count = 0;
3412 OS << "\nSymbols:\n";
3413 for (const SymbolKind &Kind : Shared->SymbolKinds)
3415 Shared->SymbolKinds.clear();
3416
3417 OS << "\n";
3418}
3419
3421 LVScope *InlinedFunction,
3423 // Get the parent scope to update the address ranges of the nested
3424 // scope representing the inlined function.
3425 LVAddress ParentLowPC = 0;
3426 LVScope *Parent = InlinedFunction->getParentScope();
3427 if (const LVLocations *Locations = Parent->getRanges()) {
3428 if (!Locations->empty())
3429 ParentLowPC = (*Locations->begin())->getLowerAddress();
3430 }
3431
3432 // For the given inlinesite, get the initial line number and its
3433 // source filename. Update the logical scope representing it.
3434 uint32_t LineNumber = 0;
3436 LVInlineeInfo::iterator Iter = InlineeInfo.find(InlineSite.Inlinee);
3437 if (Iter != InlineeInfo.end()) {
3438 LineNumber = Iter->second.first;
3439 Filename = Iter->second.second;
3440 AbstractFunction->setLineNumber(LineNumber);
3441 // TODO: This part needs additional work in order to set properly the
3442 // correct filename in order to detect changes between filenames.
3443 // AbstractFunction->setFilename(Filename);
3444 }
3445
3446 LLVM_DEBUG({
3447 dbgs() << "inlineSiteAnnotation\n"
3448 << "Abstract: " << AbstractFunction->getName() << "\n"
3449 << "Inlined: " << InlinedFunction->getName() << "\n"
3450 << "Parent: " << Parent->getName() << "\n"
3451 << "Low PC: " << hexValue(ParentLowPC) << "\n";
3452 });
3453
3454 // Get the source lines if requested by command line option.
3455 if (!options().getPrintLines())
3456 return Error::success();
3457
3458 // Limitation: Currently we don't track changes in the FileOffset. The
3459 // side effects are the caller that it is unable to differentiate the
3460 // source filename for the inlined code.
3461 uint64_t CodeOffset = ParentLowPC;
3462 int32_t LineOffset = LineNumber;
3463 uint32_t FileOffset = 0;
3464
3465 auto UpdateClose = [&]() { LLVM_DEBUG({ dbgs() << ("\n"); }); };
3466 auto UpdateCodeOffset = [&](uint32_t Delta) {
3467 CodeOffset += Delta;
3468 LLVM_DEBUG({
3469 dbgs() << formatv(" code 0x{0} (+0x{1})", utohexstr(CodeOffset),
3470 utohexstr(Delta));
3471 });
3472 };
3473 auto UpdateLineOffset = [&](int32_t Delta) {
3474 LineOffset += Delta;
3475 LLVM_DEBUG({
3476 char Sign = Delta > 0 ? '+' : '-';
3477 dbgs() << formatv(" line {0} ({1}{2})", LineOffset, Sign,
3478 std::abs(Delta));
3479 });
3480 };
3481 auto UpdateFileOffset = [&](int32_t Offset) {
3482 FileOffset = Offset;
3483 LLVM_DEBUG({ dbgs() << formatv(" file {0}", FileOffset); });
3484 };
3485
3487 auto CreateLine = [&]() {
3488 // Create the logical line record.
3489 LVLineDebug *Line = Reader->createLineDebug();
3490 Line->setAddress(CodeOffset);
3491 Line->setLineNumber(LineOffset);
3492 // TODO: This part needs additional work in order to set properly the
3493 // correct filename in order to detect changes between filenames.
3494 // Line->setFilename(Filename);
3495 InlineeLines.push_back(Line);
3496 };
3497
3498 bool SeenLowAddress = false;
3499 bool SeenHighAddress = false;
3500 uint64_t LowPC = 0;
3501 uint64_t HighPC = 0;
3502
3503 for (auto &Annot : InlineSite.annotations()) {
3504 LLVM_DEBUG({
3505 dbgs() << formatv(" {0}",
3506 fmt_align(toHex(Annot.Bytes), AlignStyle::Left, 9));
3507 });
3508
3509 // Use the opcode to interpret the integer values.
3510 switch (Annot.OpCode) {
3511 case BinaryAnnotationsOpCode::ChangeCodeOffset:
3512 case BinaryAnnotationsOpCode::CodeOffset:
3513 case BinaryAnnotationsOpCode::ChangeCodeLength:
3514 UpdateCodeOffset(Annot.U1);
3515 UpdateClose();
3516 if (Annot.OpCode == BinaryAnnotationsOpCode::ChangeCodeOffset) {
3517 CreateLine();
3518 LowPC = CodeOffset;
3519 SeenLowAddress = true;
3520 break;
3521 }
3522 if (Annot.OpCode == BinaryAnnotationsOpCode::ChangeCodeLength) {
3523 HighPC = CodeOffset - 1;
3524 SeenHighAddress = true;
3525 }
3526 break;
3527 case BinaryAnnotationsOpCode::ChangeCodeLengthAndCodeOffset:
3528 UpdateCodeOffset(Annot.U2);
3529 UpdateClose();
3530 break;
3531 case BinaryAnnotationsOpCode::ChangeLineOffset:
3532 case BinaryAnnotationsOpCode::ChangeCodeOffsetAndLineOffset:
3533 UpdateCodeOffset(Annot.U1);
3534 UpdateLineOffset(Annot.S1);
3535 UpdateClose();
3536 if (Annot.OpCode ==
3537 BinaryAnnotationsOpCode::ChangeCodeOffsetAndLineOffset)
3538 CreateLine();
3539 break;
3540 case BinaryAnnotationsOpCode::ChangeFile:
3541 UpdateFileOffset(Annot.U1);
3542 UpdateClose();
3543 break;
3544 default:
3545 break;
3546 }
3547 if (SeenLowAddress && SeenHighAddress) {
3548 SeenLowAddress = false;
3549 SeenHighAddress = false;
3550 InlinedFunction->addObject(LowPC, HighPC);
3551 }
3552 }
3553
3554 Reader->addInlineeLines(InlinedFunction, InlineeLines);
3555 UpdateClose();
3556
3557 return Error::success();
3558}
for(const MachineOperand &MO :llvm::drop_begin(OldMI.operands(), Desc.getNumOperands()))
AMDGPU Lower Kernel Arguments
DXIL Resource Access
#define LLVM_DEBUG(...)
Definition: Debug.h:106
std::string Name
uint64_t Size
IRTranslator LLVM IR MI
#define I(x, y, z)
Definition: MD5.cpp:58
if(PassOpts->AAPipeline)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
raw_pwrite_stream & OS
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: ArrayRef.h:41
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:168
An implementation of BinaryStream which holds its entire data set in a single contiguous buffer.
Provides read only access to a subclass of BinaryStream.
This is an important base class in LLVM.
Definition: Constant.h:42
Lightweight error class with error context and mandatory checking.
Definition: Error.h:160
static ErrorSuccess success()
Create a success value.
Definition: Error.h:337
Tagged union holding either a T or a Error.
Definition: Error.h:481
StringRef getName() const
Definition: Record.h:1730
virtual void printString(StringRef Value)
void indent(int Levels=1)
void unindent(int Levels=1)
void printEnum(StringRef Label, T Value, ArrayRef< EnumEntry< TEnum > > EnumValues)
virtual raw_ostream & getOStream()
virtual raw_ostream & startLine()
virtual void printNumber(StringRef Label, char Value)
void printHex(StringRef Label, T Value)
void printFlags(StringRef Label, T Value, ArrayRef< EnumEntry< TFlag > > Flags, TFlag EnumMask1={}, TFlag EnumMask2={}, TFlag EnumMask3={}, ArrayRef< FlagEntry > ExtraFlags={})
virtual void printBoolean(StringRef Label, bool Value)
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
Definition: SmallString.h:26
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1196
StringMapEntry - This is used to represent one value that is inserted into a StringMap.
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:51
std::string str() const
str - Get the contents as an std::string.
Definition: StringRef.h:229
constexpr size_t size() const
size - Get the string size.
Definition: StringRef.h:150
Target - Wrapper for Target specific information.
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
LLVM Value Representation.
Definition: Value.h:74
Value(Type *Ty, unsigned scid)
Definition: Value.cpp:53
void setName(const Twine &Name)
Change the name of the value.
Definition: Value.cpp:377
TypeIndex getElementType() const
Definition: TypeRecord.h:405
TypeIndex getIndexType() const
Definition: TypeRecord.h:406
uint64_t getSize() const
Definition: TypeRecord.h:407
StringRef getName() const
Definition: TypeRecord.h:408
TypeIndex getType() const
Definition: TypeRecord.h:543
uint8_t getBitOffset() const
Definition: TypeRecord.h:544
ArrayRef< TypeIndex > getArgs() const
Definition: TypeRecord.h:674
Kind kind() const
Definition: CVRecord.h:42
uint8_t getLanguage() const
Definition: SymbolRecord.h:741
uint32_t getFlags() const
Definition: SymbolRecord.h:742
CompileSym3Flags getFlags() const
Definition: SymbolRecord.h:775
SourceLanguage getLanguage() const
Definition: SymbolRecord.h:772
Represents a read-only view of a CodeView string table.
DefRangeFramePointerRelHeader Hdr
Definition: SymbolRecord.h:564
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:566
DefRangeRegisterRelHeader Hdr
Definition: SymbolRecord.h:599
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:601
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:516
LocalVariableAddrRange Range
Definition: SymbolRecord.h:515
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:540
DefRangeSubfieldRegisterHeader Hdr
Definition: SymbolRecord.h:538
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:494
LocalVariableAddrRange Range
Definition: SymbolRecord.h:493
std::vector< LocalVariableAddrGap > Gaps
Definition: SymbolRecord.h:472
uint32_t getRelocationOffset() const
Definition: SymbolRecord.h:466
LocalVariableAddrRange Range
Definition: SymbolRecord.h:471
RegisterId getLocalFramePtrReg(CPUType CPU) const
Extract the register this frame uses to refer to local variables.
Definition: SymbolRecord.h:804
RegisterId getParamFramePtrReg(CPUType CPU) const
Extract the register this frame uses to refer to parameters.
Definition: SymbolRecord.h:810
FrameProcedureOptions Flags
Definition: SymbolRecord.h:801
Provides amortized O(1) random access to a CodeView type stream.
std::optional< CVType > tryGetType(TypeIndex Index)
StringRef getTypeName(TypeIndex Index) override
LF_INDEX - Used to chain two large LF_FIELDLIST or LF_METHODLIST records together.
Definition: TypeRecord.h:914
int32_t getThisPointerAdjustment() const
Definition: TypeRecord.h:193
std::vector< OneMethodRecord > Methods
Definition: TypeRecord.h:760
int32_t getVFTableOffset() const
Definition: TypeRecord.h:736
MemberAccess getAccess() const
Definition: TypeRecord.h:735
MethodKind getMethodKind() const
Definition: TypeRecord.h:733
For method overload sets. LF_METHOD.
Definition: TypeRecord.h:764
uint32_t getSignature() const
Definition: TypeRecord.h:935
StringRef getPrecompFilePath() const
Definition: TypeRecord.h:936
uint32_t getTypesCount() const
Definition: TypeRecord.h:934
uint32_t getStartTypeIndex() const
Definition: TypeRecord.h:933
uint32_t getRelocationOffset() const
Definition: SymbolRecord.h:49
TypeIndex getReturnType() const
Definition: TypeRecord.h:157
TypeIndex getArgumentList() const
Definition: TypeRecord.h:161
uint16_t getParameterCount() const
Definition: TypeRecord.h:160
TypeIndex getFieldList() const
Definition: TypeRecord.h:453
static Error deserializeAs(CVType &CVT, T &Record)
A 32-bit type reference.
Definition: TypeIndex.h:96
static TypeIndex fromArrayIndex(uint32_t Index)
Definition: TypeIndex.h:123
SimpleTypeKind getSimpleKind() const
Definition: TypeIndex.h:136
static TypeIndex None()
Definition: TypeIndex.h:148
void setIndex(uint32_t I)
Definition: TypeIndex.h:112
static const uint32_t FirstNonSimpleIndex
Definition: TypeIndex.h:98
static StringRef simpleTypeName(TypeIndex TI)
Definition: TypeIndex.cpp:71
uint32_t getIndex() const
Definition: TypeIndex.h:111
bool isNoneType() const
Definition: TypeIndex.h:116
const GUID & getGuid() const
Definition: TypeRecord.h:585
void addCallbackToPipeline(TypeVisitorCallbacks &Callbacks)
virtual Error visitUnknownMember(CVMemberRecord &Record)
virtual Error visitMemberEnd(CVMemberRecord &Record)
virtual Error visitMemberBegin(CVMemberRecord &Record)
TypeIndex getType() const
Definition: TypeRecord.h:857
uint32_t getVFPtrOffset() const
Definition: TypeRecord.h:705
TypeIndex getOverriddenVTable() const
Definition: TypeRecord.h:704
ArrayRef< StringRef > getMethodNames() const
Definition: TypeRecord.h:708
StringRef getName() const
Definition: TypeRecord.h:706
TypeIndex getCompleteClass() const
Definition: TypeRecord.h:703
Stores all information relating to a compile unit, be it in its original instance in the object file ...
void addInlineeLines(LVScope *Scope, LVLines &Lines)
LVAddress getSymbolTableAddress(StringRef Name)
LVAddress linearAddress(uint16_t Segment, uint32_t Offset, LVAddress Addendum=0)
void addToSymbolTable(StringRef Name, LVScope *Function, LVSectionIndex SectionIndex=0)
void getLinkageName(const llvm::object::coff_section *CoffSection, uint32_t RelocOffset, uint32_t Offset, StringRef *RelocSym)
static StringRef getSymbolKindName(SymbolKind Kind)
virtual void setCount(int64_t Value)
Definition: LVElement.h:246
virtual void setBitSize(uint32_t Size)
Definition: LVElement.h:243
virtual void updateLevel(LVScope *Parent, bool Moved=false)
Definition: LVElement.cpp:266
virtual int64_t getCount() const
Definition: LVElement.h:245
void setInlineCode(uint32_t Code)
Definition: LVElement.h:278
virtual void setReference(LVElement *Element)
Definition: LVElement.h:220
void setName(StringRef ElementName) override
Definition: LVElement.cpp:95
StringRef getName() const override
Definition: LVElement.h:184
void setType(LVElement *Element=nullptr)
Definition: LVElement.h:301
void setFilenameIndex(size_t Index)
Definition: LVElement.h:234
Error visitKnownRecord(CVType &Record, ArgListRecord &Args, TypeIndex TI, LVElement *Element)
void printRecords(raw_ostream &OS) const
Error visitMemberRecord(CVMemberRecord &Record, TypeVisitorCallbacks &Callbacks, TypeIndex TI, LVElement *Element)
Error visitKnownMember(CVMemberRecord &Record, BaseClassRecord &Base, TypeIndex TI, LVElement *Element)
void printMemberEnd(CVMemberRecord &Record)
void setCompileUnitName(std::string Name)
Error inlineSiteAnnotation(LVScope *AbstractFunction, LVScope *InlinedFunction, InlineSiteSym &InlineSite)
LVLogicalVisitor(LVCodeViewReader *Reader, ScopedPrinter &W, llvm::pdb::InputFile &Input)
void printTypeIndex(StringRef FieldName, TypeIndex TI, uint32_t StreamIdx)
Error visitUnknownMember(CVMemberRecord &Record, TypeIndex TI)
Error visitUnknownType(CVType &Record, TypeIndex TI)
void addElement(LVScope *Scope, bool IsCompileUnit)
void printTypeBegin(CVType &Record, TypeIndex TI, LVElement *Element, uint32_t StreamIdx)
LVElement * getElement(uint32_t StreamIdx, TypeIndex TI, LVScope *Parent=nullptr)
void printMemberBegin(CVMemberRecord &Record, TypeIndex TI, LVElement *Element, uint32_t StreamIdx)
Error finishVisitation(CVType &Record, TypeIndex TI, LVElement *Element)
LVElement * createElement(TypeLeafKind Kind)
LVScope * getParentScope() const
Definition: LVObject.h:253
void setOffset(LVOffset DieOffset)
Definition: LVObject.h:239
LVOffset getOffset() const
Definition: LVObject.h:238
void setLineNumber(uint32_t Number)
Definition: LVObject.h:273
void setTag(dwarf::Tag Tag)
Definition: LVObject.h:231
codeview::CPUType getCompileUnitCPUType()
Definition: LVReader.h:254
void setCompileUnitCPUType(codeview::CPUType Type)
Definition: LVReader.h:251
virtual bool isSystemEntry(LVElement *Element, StringRef Name={}) const
Definition: LVReader.h:275
LVScopeCompileUnit * getCompileUnit() const
Definition: LVReader.h:246
void setCompileUnit(LVScope *Scope)
Definition: LVReader.h:247
void addPublicName(LVScope *Scope, LVAddress LowPC, LVAddress HighPC)
Definition: LVScope.h:506
void addElement(LVElement *Element)
Definition: LVScope.cpp:112
void addObject(LVLocation *Location)
Definition: LVScope.cpp:151
const LVLocations * getRanges() const
Definition: LVScope.h:206
void getLinkageName(uint32_t RelocOffset, uint32_t Offset, StringRef *RelocSym=nullptr)
void printRelocatedField(StringRef Label, uint32_t RelocOffset, uint32_t Offset, StringRef *RelocSym=nullptr)
DebugStringTableSubsectionRef getStringTable() override
StringRef getFileNameForFileOffset(uint32_t FileOffset) override
Error visitSymbolEnd(CVSymbol &Record) override
Error visitKnownRecord(CVSymbol &Record, BlockSym &Block) override
Error visitSymbolBegin(CVSymbol &Record) override
Error visitUnknownSymbol(CVSymbol &Record) override
Action to take on unknown symbols. By default, they are ignored.
Error visitMemberEnd(CVMemberRecord &Record) override
Error visitUnknownMember(CVMemberRecord &Record) override
Error visitTypeBegin(CVType &Record) override
Paired begin/end actions for all types.
Error visitMemberBegin(CVMemberRecord &Record) override
Error visitKnownRecord(CVType &Record, BuildInfoRecord &Args) override
Error visitUnknownType(CVType &Record) override
Action to take on unknown types. By default, they are ignored.
This class implements an extremely fast bulk output stream that can only output to a stream.
Definition: raw_ostream.h:52
constexpr char TypeName[]
Key for Kernel::Arg::Metadata::mTypeName.
@ Entry
Definition: COFF.h:844
PointerMode
Equivalent to CV_ptrmode_e.
Definition: CodeView.h:363
MethodKind
Part of member attribute flags. (CV_methodprop_e)
Definition: CodeView.h:280
CPUType
These values correspond to the CV_CPU_TYPE_e enumeration, and are documented here: https://msdn....
Definition: CodeView.h:76
ArrayRef< EnumEntry< uint16_t > > getJumpTableEntrySizeNames()
Definition: EnumTables.cpp:580
bool symbolEndsScope(SymbolKind Kind)
Return true if this ssymbol ends a scope.
MethodOptions
Equivalent to CV_fldattr_t bitfield.
Definition: CodeView.h:291
ArrayRef< EnumEntry< SymbolKind > > getSymbolTypeNames()
Definition: EnumTables.cpp:458
MemberAccess
Source-level access specifier. (CV_access_e)
Definition: CodeView.h:272
bool symbolOpensScope(SymbolKind Kind)
Return true if this symbol opens a scope.
TypeLeafKind
Duplicate copy of the above enum, but using the official CV names.
Definition: CodeView.h:34
ArrayRef< EnumEntry< uint16_t > > getLocalFlagNames()
Definition: EnumTables.cpp:483
ArrayRef< EnumEntry< uint16_t > > getRegisterNames(CPUType Cpu)
Definition: EnumTables.cpp:466
bool isAggregate(CVType CVT)
Given an arbitrary codeview type, determine if it is an LF_STRUCTURE, LF_CLASS, LF_INTERFACE,...
ArrayRef< EnumEntry< uint8_t > > getProcSymFlagNames()
Definition: EnumTables.cpp:479
TypeRecordKind
Distinguishes individual records in .debug$T or .debug$P section or PDB type stream.
Definition: CodeView.h:27
SymbolKind
Duplicate copy of the above enum, but using the official CV names.
Definition: CodeView.h:48
uint64_t getSizeInBytesForTypeRecord(CVType CVT)
Given an arbitrary codeview type, return the type's size in the case of aggregate (LF_STRUCTURE,...
ArrayRef< EnumEntry< unsigned > > getCPUTypeNames()
Definition: EnumTables.cpp:507
ArrayRef< EnumEntry< SourceLanguage > > getSourceLanguageNames()
Definition: EnumTables.cpp:491
uint64_t getSizeInBytesForTypeIndex(TypeIndex TI)
Given an arbitrary codeview type index, determine its size.
TypeIndex getModifiedType(const CVType &CVT)
Given a CVType which is assumed to be an LF_MODIFIER, return the TypeIndex of the type that the LF_MO...
ArrayRef< EnumEntry< uint32_t > > getCompileSym3FlagNames()
Definition: EnumTables.cpp:499
void printTypeIndex(ScopedPrinter &Printer, StringRef FieldName, TypeIndex TI, TypeCollection &Types)
Definition: TypeIndex.cpp:93
@ DW_INL_inlined
Definition: Dwarf.h:756
@ DW_INL_declared_inlined
Definition: Dwarf.h:758
Attribute
Attributes.
Definition: Dwarf.h:123
constexpr Tag DW_TAG_unaligned
Definition: LVObject.h:28
FormattedNumber hexValue(uint64_t N, unsigned Width=HEX_WIDTH, bool Upper=false)
Definition: LVSupport.h:103
LVReader & getReader()
Definition: LVReader.h:333
static TypeIndex getTrueType(TypeIndex &TI)
std::vector< StringRef > LVStringRefs
Definition: LVSupport.h:33
uint8_t LVSmall
Definition: LVObject.h:42
static StringRef getRecordName(LazyRandomTypeCollection &Types, TypeIndex TI)
std::vector< TypeIndex > LVLineRecords
LVStringRefs getAllLexicalComponents(StringRef Name)
Definition: LVSupport.cpp:138
std::string transformPath(StringRef Path)
Definition: LVSupport.cpp:31
LVLexicalComponent getInnerComponent(StringRef Name)
Definition: LVSupport.cpp:118
static const EnumEntry< TypeLeafKind > LeafTypeNames[]
std::set< SymbolKind > LVSymbolKinds
std::set< TypeLeafKind > LVTypeKinds
LVOptions & options()
Definition: LVOptions.h:445
std::string getScopedName(const LVStringRefs &Components, StringRef BaseName={})
Definition: LVSupport.cpp:151
std::tuple< LVStringRefs::size_type, LVStringRefs::size_type > LVLexicalIndex
Definition: LVSupport.h:36
std::string formatTypeLeafKind(codeview::TypeLeafKind K)
Definition: FormatUtil.cpp:115
Print(const T &, const DataFlowGraph &) -> Print< T >
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
auto find(R &&Range, const T &Val)
Provide wrappers to std::find which take ranges instead of having to pass begin/end explicitly.
Definition: STLExtras.h:1759
std::tuple< uint64_t, uint32_t > InlineSite
auto formatv(bool Validate, const char *Fmt, Ts &&...Vals)
decltype(auto) get(const PointerIntPair< PointerTy, IntBits, IntType, PtrTraits, Info > &Pair)
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition: Debug.cpp:163
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
Definition: Format.h:125
StringRef getTypeName()
We provide a function which tries to compute the (demangled) name of a type statically.
Definition: TypeName.h:63
@ Mod
The access may modify the value stored in memory.
support::detail::RepeatAdapter< T > fmt_repeat(T &&Item, size_t Count)
support::detail::AlignAdapter< T > fmt_align(T &&Item, AlignStyle Where, size_t Amount, char Fill=' ')
void erase_if(Container &C, UnaryPredicate P)
Provide a container algorithm similar to C++ Library Fundamentals v2's erase_if which is equivalent t...
Definition: STLExtras.h:2099
void consumeError(Error Err)
Consume a Error without doing anything.
Definition: Error.h:1069
std::string demangle(std::string_view MangledName)
Attempt to demangle a string using different demangling schemes.
Definition: Demangle.cpp:20
#define N
MethodOptions getFlags() const
Get the flags that are not included in access control or method properties.
Definition: TypeRecord.h:72
LVShared(LVCodeViewReader *Reader, LVLogicalVisitor *Visitor)
LVNamespaceDeduction NamespaceDeduction
LVForwardReferences ForwardReferences