LLVM: lib/DebugInfo/LogicalView/Core/LVReader.cpp Source File (original) (raw)
1
2
3
4
5
6
7
8
9
10
11
12
18#include
19
20using namespace llvm;
22
23#define DEBUG_TYPE "Reader"
24
25
26
27
29 using LVDuplicateEntry = std::tuple<LVElement *, LVScope *, LVScope *>;
30 using LVDuplicate = std::vector;
31 LVDuplicate Duplicate;
32
33 using LVIntegrity = std::map<LVElement *, LVScope *>;
35
36
38 LVIntegrity::iterator Iter = Integrity.find(Element);
40 Integrity.emplace(Element, Scope);
41 else
42
43 Duplicate.emplace_back(Element, Scope, Iter->second);
44 };
45
46
47 std::function<void(LVScope * Parent)> TraverseScope = [&](LVScope *Parent) {
48 auto Traverse = [&](const auto *Set) {
49 if (Set)
50 for (const auto &Entry : *Set)
51 AddElement(Entry, Parent);
52 };
55 AddElement(Scope, Parent);
56 TraverseScope(Scope);
57 }
58 }
62 };
63
64
65 TraverseScope(Root);
66 bool PassIntegrity = true;
67 if (Duplicate.size()) {
69 return std::get<0>(l)->getID() < std::get<0>(r)->getID();
70 });
71
72 auto PrintIndex = [](unsigned Index) {
73 if (Index)
75 else
77 };
78 auto PrintElement = [&](LVElement *Element, unsigned Index = 0) {
79 PrintIndex(Index);
80 std::string ElementName(Element->getName());
81 dbgs() << format("%15s ID=0x%08x '%s'\n", Element->kind(),
82 Element->getID(), ElementName.c_str());
83 };
84
85 std::string RootName(Root->getName());
87 dbgs() << format("Root: '%s'\nDuplicated elements: %d\n", RootName.c_str(),
88 Duplicate.size());
90
91 unsigned Index = 0;
92 for (const LVDuplicateEntry &Entry : Duplicate) {
96 std::tie(Element, First, Second) = Entry;
98 PrintElement(Element, ++Index);
99 PrintElement(First);
100 PrintElement(Second);
102 }
103 PassIntegrity = false;
104 }
105 return PassIntegrity;
106}
107
108
109
110
112
113
114
115 Location = std::string(Where);
116
117
118 size_t Pos = Location.find_last_of('/');
119 if (Location.length() != Pos + 1)
120 Location.append("/");
121
122
125 Location.c_str());
126
128}
129
131 std::string Extension, raw_ostream &OS) {
132 assert(OutputFile == nullptr && "OutputFile already set.");
133
134
136 Name.append(Extension);
137
138 if (!Location.empty())
139 Name.insert(0, Location);
140
141 std::error_code EC;
143 if (EC)
144 return EC;
145
146
147 OutputFile->keep();
148 return std::error_code();
149}
150
155 outs() << "Invalid instance reader.\n";
157}
159
160Error LVReader::createSplitFolder() {
161 if (OutputSplit) {
162
163
164 if (options().getOutputFolder().empty())
166
168 SplitFolder = options().getOutputFolder();
170
171
173 return Err;
174
175 OS << "\nSplit View Location: '" << SplitContext.getLocation() << "'\n";
176 }
177
179}
180
181
183
184
185
186 if (CompileUnits.size()) {
187
188 LVCompileUnits::const_iterator Iter =
189 std::prev(CompileUnits.lower_bound(Object->getOffset()));
190 if (Iter != CompileUnits.end())
191 return Iter->second->getFilename(Index);
192 }
193
195}
196
199 ScopesWithRanges->addEntry(Scope);
200}
201
205 ScopesWithRanges->addEntry(Scope, LowerAddress, UpperAddress);
206}
207
209
210 LVSectionRanges::iterator IterSection = SectionRanges.find(SectionIndex);
211 if (IterSection == SectionRanges.end())
212 IterSection =
213 SectionRanges.emplace(SectionIndex, std::make_unique()).first;
217}
218
224
227
228 if (().getPrintSymbols()) {
229 switch (Tag) {
230
231
232
233 case dwarf::DW_TAG_formal_parameter:
234 case dwarf::DW_TAG_unspecified_parameters:
235 case dwarf::DW_TAG_member:
236 case dwarf::DW_TAG_variable:
237 case dwarf::DW_TAG_inheritance:
238 case dwarf::DW_TAG_constant:
239 case dwarf::DW_TAG_call_site_parameter:
240 case dwarf::DW_TAG_GNU_call_site_parameter:
241 return nullptr;
242 default:
243 break;
244 }
245 }
246
247 switch (Tag) {
248
249 case dwarf::DW_TAG_base_type:
252 if (options().getAttributeBase())
255 case dwarf::DW_TAG_const_type:
260 case dwarf::DW_TAG_enumerator:
263 case dwarf::DW_TAG_imported_declaration:
267 case dwarf::DW_TAG_imported_module:
271 case dwarf::DW_TAG_pointer_type:
276 case dwarf::DW_TAG_ptr_to_member_type:
281 case dwarf::DW_TAG_reference_type:
286 case dwarf::DW_TAG_restrict_type:
291 case dwarf::DW_TAG_rvalue_reference_type:
296 case dwarf::DW_TAG_subrange_type:
299 case dwarf::DW_TAG_template_value_parameter:
303 case dwarf::DW_TAG_template_type_parameter:
307 case dwarf::DW_TAG_GNU_template_template_param:
309 CurrentType->setIsTemplateTemplateParam();
311 case dwarf::DW_TAG_typedef:
314 case dwarf::DW_TAG_unspecified_type:
318 case dwarf::DW_TAG_volatile_type:
323
324
325 case dwarf::DW_TAG_formal_parameter:
329 case dwarf::DW_TAG_unspecified_parameters:
334 case dwarf::DW_TAG_member:
338 case dwarf::DW_TAG_variable:
342 case dwarf::DW_TAG_inheritance:
346 case dwarf::DW_TAG_call_site_parameter:
347 case dwarf::DW_TAG_GNU_call_site_parameter:
351 case dwarf::DW_TAG_constant:
355
356
357 case dwarf::DW_TAG_catch_block:
361 case dwarf::DW_TAG_lexical_block:
365 case dwarf::DW_TAG_try_block:
369 case dwarf::DW_TAG_compile_unit:
370 case dwarf::DW_TAG_skeleton_unit:
374 case dwarf::DW_TAG_inlined_subroutine:
377 case dwarf::DW_TAG_namespace:
380 case dwarf::DW_TAG_template_alias:
383 case dwarf::DW_TAG_array_type:
386 case dwarf::DW_TAG_call_site:
387 case dwarf::DW_TAG_GNU_call_site:
391 case dwarf::DW_TAG_entry_point:
395 case dwarf::DW_TAG_subprogram:
399 case dwarf::DW_TAG_subroutine_type:
402 case dwarf::DW_TAG_label:
406 case dwarf::DW_TAG_class_type:
410 case dwarf::DW_TAG_structure_type:
414 case dwarf::DW_TAG_union_type:
418 case dwarf::DW_TAG_enumeration_type:
421 case dwarf::DW_TAG_GNU_formal_parameter_pack:
424 case dwarf::DW_TAG_GNU_template_parameter_pack:
427 case dwarf::DW_TAG_module:
430 default:
431
432 if (options().getInternalTag() && Tag)
434 break;
435 }
436
439 });
440
441 return nullptr;
442}
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
461
463
464
465
468
469
475
476
477
479
480
482 return Err;
483
487
488
489 Root->processRangeInformation();
490
491
492
493
494 Root->resolveElements();
495
498}
499
500
502
504
505
506 if (options().getReportExecute()) {
507
508 if (options().getReportList())
510 return Err;
511
512 if (options().getReportChildren() && ().getReportParents())
514 return Err;
515
516 if (options().getReportParents() || options().getReportView())
518 return Err;
519
521 }
522
524}
525
527 if (bool DoPrint =
528 (options().getPrintExecute() || options().getComparePrint())) {
529 if (Error Err = createSplitFolder())
530 return Err;
531
532
533 bool DoMatch = options().getSelectGenericPattern() ||
534 options().getSelectGenericKind() ||
535 options().getSelectOffsetPattern();
536 return Root->doPrint(OutputSplit, DoMatch, DoPrint, OS);
537 }
538
540}
541
543 if (Error Err = createSplitFolder())
544 return Err;
545
546 return Root->doPrintMatches(OutputSplit, OS, UseMatchedElements);
547}
548
550 OS << "LVReader\n";
552}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
AMDGPU Register Bank Select
static LVReader * CurrentReader
Definition LVReader.cpp:151
bool checkIntegrityScopesTree(LVScope *Root)
Definition LVReader.cpp:28
Lightweight error class with error context and mandatory checking.
static ErrorSuccess success()
Create a success value.
SmallString - A SmallString is just a SmallVector with methods and accessors that make it work better...
StringRef - Represent a constant reference to a string, i.e.
StringRef getName() const override
virtual const char * kind() const
LLVM_ABI void addGenericPatterns(StringSet<> &Patterns)
LLVM_ABI void updateReportOptions()
LLVM_ABI void addOffsetPatterns(const LVOffsetSet &Patterns)
void addEntry(LVScope *Scope, LVAddress LowerAddress, LVAddress UpperAddress)
The logical reader owns of all the logical elements created during the debug information parsing.
virtual void sortScopes()
LVRange * getSectionRanges(LVSectionIndex SectionIndex)
Definition LVReader.cpp:208
void print(raw_ostream &OS) const
Definition LVReader.cpp:549
std::vector< LVAddressRange > CurrentRanges
LVElement * createElement(dwarf::Tag Tag)
Definition LVReader.cpp:219
Error doLoad()
Definition LVReader.cpp:460
StringRef getFilename() const
static LVReader & getInstance()
Definition LVReader.cpp:152
LVScopeCompileUnit * CompileUnit
static void setInstance(LVReader *Reader)
Definition LVReader.cpp:158
Error doPrint()
Definition LVReader.cpp:501
void addSectionRange(LVSectionIndex SectionIndex, LVScope *Scope)
Definition LVReader.cpp:197
virtual Error printMatchedElements(bool UseMatchedElements)
Definition LVReader.cpp:542
virtual Error printScopes()
Definition LVReader.cpp:526
virtual Error createScopes()
const LVLines * getLines() const
const LVScopes * getScopes() const
const LVSymbols * getSymbols() const
const LVTypes * getTypes() const
std::string getLocation() const
LLVM_ABI Error createSplitFolder(StringRef Where)
Definition LVReader.cpp:111
LLVM_ABI std::error_code open(std::string Name, std::string Extension, raw_ostream &OS)
Definition LVReader.cpp:130
This class implements an extremely fast bulk output stream that can only output to a stream.
LLVM_ABI StringRef TagString(unsigned Tag)
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
SmallVector< LVScope *, 8 > LVScopes
LLVM_ABI std::string flattenedFilePath(StringRef Path)
LLVM_ABI std::error_code create_directories(const Twine &path, bool IgnoreExisting=true, perms Perms=owner_all|group_all)
Create all the non-existent directories in path.
LLVM_ABI std::error_code make_absolute(SmallVectorImpl< char > &path)
Make path an absolute path.
This is an optimization pass for GlobalISel generic memory operations.
void stable_sort(R &&Range)
LLVM_ABI std::error_code inconvertibleErrorCode()
The value returned by this function can be returned from convertToErrorCode for Error values where no...
LLVM_ABI raw_fd_ostream & outs()
This returns a reference to a raw_fd_ostream for standard output.
Error createStringError(std::error_code EC, char const *Fmt, const Ts &... Vals)
Create formatted StringError object.
auto formatv(bool Validate, const char *Fmt, Ts &&...Vals)
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
format_object< Ts... > format(const char *Fmt, const Ts &... Vals)
These are helper functions used to produce formatted output.
Error make_error(ArgTs &&... Args)
Make a Error instance representing failure using the given error info type.
@ First
Helpers to iterate all locations in the MemoryEffectsBase class.
support::detail::RepeatAdapter< T > fmt_repeat(T &&Item, size_t Count)