1 | //===-- llvm/BinaryFormat/Dwarf.cpp - Dwarf Framework ------------*- C++-*-===// |
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 file contains support for generic dwarf information. |
10 | // |
11 | //===----------------------------------------------------------------------===// |
12 | |
13 | #include "llvm/BinaryFormat/Dwarf.h" |
14 | #include "llvm/ADT/StringSwitch.h" |
15 | #include "llvm/Support/ErrorHandling.h" |
16 | #include "llvm/TargetParser/Triple.h" |
17 | |
18 | using namespace llvm; |
19 | using namespace dwarf; |
20 | |
21 | StringRef llvm::dwarf::TagString(unsigned Tag) { |
22 | switch (Tag) { |
23 | default: |
24 | return StringRef(); |
25 | #define HANDLE_DW_TAG(ID, NAME, VERSION, VENDOR, KIND) \ |
26 | case DW_TAG_##NAME: \ |
27 | return "DW_TAG_" #NAME; |
28 | #include "llvm/BinaryFormat/Dwarf.def" |
29 | } |
30 | } |
31 | |
32 | unsigned llvm::dwarf::getTag(StringRef TagString) { |
33 | return StringSwitch<unsigned>(TagString) |
34 | #define HANDLE_DW_TAG(ID, NAME, VERSION, VENDOR, KIND) \ |
35 | .Case("DW_TAG_" #NAME, DW_TAG_##NAME) |
36 | #include "llvm/BinaryFormat/Dwarf.def" |
37 | .Default(Value: DW_TAG_invalid); |
38 | } |
39 | |
40 | unsigned llvm::dwarf::TagVersion(dwarf::Tag Tag) { |
41 | switch (Tag) { |
42 | default: |
43 | return 0; |
44 | #define HANDLE_DW_TAG(ID, NAME, VERSION, VENDOR, KIND) \ |
45 | case DW_TAG_##NAME: \ |
46 | return VERSION; |
47 | #include "llvm/BinaryFormat/Dwarf.def" |
48 | } |
49 | } |
50 | |
51 | unsigned llvm::dwarf::TagVendor(dwarf::Tag Tag) { |
52 | switch (Tag) { |
53 | default: |
54 | return 0; |
55 | #define HANDLE_DW_TAG(ID, NAME, VERSION, VENDOR, KIND) \ |
56 | case DW_TAG_##NAME: \ |
57 | return DWARF_VENDOR_##VENDOR; |
58 | #include "llvm/BinaryFormat/Dwarf.def" |
59 | } |
60 | } |
61 | |
62 | StringRef llvm::dwarf::ChildrenString(unsigned Children) { |
63 | switch (Children) { |
64 | case DW_CHILDREN_no: |
65 | return "DW_CHILDREN_no" ; |
66 | case DW_CHILDREN_yes: |
67 | return "DW_CHILDREN_yes" ; |
68 | } |
69 | return StringRef(); |
70 | } |
71 | |
72 | StringRef llvm::dwarf::AttributeString(unsigned Attribute) { |
73 | switch (Attribute) { |
74 | default: |
75 | return StringRef(); |
76 | #define HANDLE_DW_AT(ID, NAME, VERSION, VENDOR) \ |
77 | case DW_AT_##NAME: \ |
78 | return "DW_AT_" #NAME; |
79 | #include "llvm/BinaryFormat/Dwarf.def" |
80 | } |
81 | } |
82 | |
83 | unsigned llvm::dwarf::AttributeVersion(dwarf::Attribute Attribute) { |
84 | switch (Attribute) { |
85 | default: |
86 | return 0; |
87 | #define HANDLE_DW_AT(ID, NAME, VERSION, VENDOR) \ |
88 | case DW_AT_##NAME: \ |
89 | return VERSION; |
90 | #include "llvm/BinaryFormat/Dwarf.def" |
91 | } |
92 | } |
93 | |
94 | unsigned llvm::dwarf::AttributeVendor(dwarf::Attribute Attribute) { |
95 | switch (Attribute) { |
96 | default: |
97 | return 0; |
98 | #define HANDLE_DW_AT(ID, NAME, VERSION, VENDOR) \ |
99 | case DW_AT_##NAME: \ |
100 | return DWARF_VENDOR_##VENDOR; |
101 | #include "llvm/BinaryFormat/Dwarf.def" |
102 | } |
103 | } |
104 | |
105 | StringRef llvm::dwarf::FormEncodingString(unsigned Encoding) { |
106 | switch (Encoding) { |
107 | default: |
108 | return StringRef(); |
109 | #define HANDLE_DW_FORM(ID, NAME, VERSION, VENDOR) \ |
110 | case DW_FORM_##NAME: \ |
111 | return "DW_FORM_" #NAME; |
112 | #include "llvm/BinaryFormat/Dwarf.def" |
113 | } |
114 | } |
115 | |
116 | unsigned llvm::dwarf::FormVersion(dwarf::Form Form) { |
117 | switch (Form) { |
118 | default: |
119 | return 0; |
120 | #define HANDLE_DW_FORM(ID, NAME, VERSION, VENDOR) \ |
121 | case DW_FORM_##NAME: \ |
122 | return VERSION; |
123 | #include "llvm/BinaryFormat/Dwarf.def" |
124 | } |
125 | } |
126 | |
127 | unsigned llvm::dwarf::FormVendor(dwarf::Form Form) { |
128 | switch (Form) { |
129 | default: |
130 | return 0; |
131 | #define HANDLE_DW_FORM(ID, NAME, VERSION, VENDOR) \ |
132 | case DW_FORM_##NAME: \ |
133 | return DWARF_VENDOR_##VENDOR; |
134 | #include "llvm/BinaryFormat/Dwarf.def" |
135 | } |
136 | } |
137 | |
138 | StringRef llvm::dwarf::OperationEncodingString(unsigned Encoding) { |
139 | switch (Encoding) { |
140 | default: |
141 | return StringRef(); |
142 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
143 | case DW_OP_##NAME: \ |
144 | return "DW_OP_" #NAME; |
145 | #include "llvm/BinaryFormat/Dwarf.def" |
146 | case DW_OP_LLVM_convert: |
147 | return "DW_OP_LLVM_convert" ; |
148 | case DW_OP_LLVM_fragment: |
149 | return "DW_OP_LLVM_fragment" ; |
150 | case DW_OP_LLVM_tag_offset: |
151 | return "DW_OP_LLVM_tag_offset" ; |
152 | case DW_OP_LLVM_entry_value: |
153 | return "DW_OP_LLVM_entry_value" ; |
154 | case DW_OP_LLVM_implicit_pointer: |
155 | return "DW_OP_LLVM_implicit_pointer" ; |
156 | case DW_OP_LLVM_arg: |
157 | return "DW_OP_LLVM_arg" ; |
158 | case DW_OP_LLVM_extract_bits_sext: |
159 | return "DW_OP_LLVM_extract_bits_sext" ; |
160 | case DW_OP_LLVM_extract_bits_zext: |
161 | return "DW_OP_LLVM_extract_bits_zext" ; |
162 | } |
163 | } |
164 | |
165 | unsigned llvm::dwarf::getOperationEncoding(StringRef OperationEncodingString) { |
166 | return StringSwitch<unsigned>(OperationEncodingString) |
167 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
168 | .Case("DW_OP_" #NAME, DW_OP_##NAME) |
169 | #include "llvm/BinaryFormat/Dwarf.def" |
170 | .Case(S: "DW_OP_LLVM_convert" , Value: DW_OP_LLVM_convert) |
171 | .Case(S: "DW_OP_LLVM_fragment" , Value: DW_OP_LLVM_fragment) |
172 | .Case(S: "DW_OP_LLVM_tag_offset" , Value: DW_OP_LLVM_tag_offset) |
173 | .Case(S: "DW_OP_LLVM_entry_value" , Value: DW_OP_LLVM_entry_value) |
174 | .Case(S: "DW_OP_LLVM_implicit_pointer" , Value: DW_OP_LLVM_implicit_pointer) |
175 | .Case(S: "DW_OP_LLVM_arg" , Value: DW_OP_LLVM_arg) |
176 | .Case(S: "DW_OP_LLVM_extract_bits_sext" , Value: DW_OP_LLVM_extract_bits_sext) |
177 | .Case(S: "DW_OP_LLVM_extract_bits_zext" , Value: DW_OP_LLVM_extract_bits_zext) |
178 | .Default(Value: 0); |
179 | } |
180 | |
181 | static StringRef LlvmUserOperationEncodingString(unsigned Encoding) { |
182 | switch (Encoding) { |
183 | default: |
184 | llvm_unreachable("unhandled DWARF operation with LLVM user op" ); |
185 | #define HANDLE_DW_OP_LLVM_USEROP(ID, NAME) \ |
186 | case DW_OP_LLVM_##NAME: \ |
187 | return "DW_OP_LLVM_" #NAME; |
188 | #include "llvm/BinaryFormat/Dwarf.def" |
189 | } |
190 | } |
191 | |
192 | static unsigned |
193 | getLlvmUserOperationEncoding(StringRef LlvmUserOperationEncodingString) { |
194 | unsigned E = StringSwitch<unsigned>(LlvmUserOperationEncodingString) |
195 | #define HANDLE_DW_OP_LLVM_USEROP(ID, NAME) .Case(#NAME, DW_OP_LLVM_##NAME) |
196 | #include "llvm/BinaryFormat/Dwarf.def" |
197 | .Default(Value: 0); |
198 | assert(E && "unhandled DWARF operation string with LLVM user op" ); |
199 | return E; |
200 | } |
201 | |
202 | StringRef llvm::dwarf::SubOperationEncodingString(unsigned OpEncoding, |
203 | unsigned SubOpEncoding) { |
204 | assert(OpEncoding == DW_OP_LLVM_user); |
205 | return LlvmUserOperationEncodingString(Encoding: SubOpEncoding); |
206 | } |
207 | |
208 | unsigned |
209 | llvm::dwarf::getSubOperationEncoding(unsigned OpEncoding, |
210 | StringRef SubOperationEncodingString) { |
211 | assert(OpEncoding == DW_OP_LLVM_user); |
212 | return getLlvmUserOperationEncoding(LlvmUserOperationEncodingString: SubOperationEncodingString); |
213 | } |
214 | |
215 | unsigned llvm::dwarf::OperationVersion(dwarf::LocationAtom Op) { |
216 | switch (Op) { |
217 | default: |
218 | return 0; |
219 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
220 | case DW_OP_##NAME: \ |
221 | return VERSION; |
222 | #include "llvm/BinaryFormat/Dwarf.def" |
223 | } |
224 | } |
225 | |
226 | std::optional<unsigned> llvm::dwarf::OperationOperands(dwarf::LocationAtom Op) { |
227 | switch (Op) { |
228 | default: |
229 | return std::nullopt; |
230 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
231 | case DW_OP_##NAME: \ |
232 | if (OPERANDS == -1) \ |
233 | return std::nullopt; \ |
234 | return OPERANDS; |
235 | #include "llvm/BinaryFormat/Dwarf.def" |
236 | } |
237 | } |
238 | |
239 | std::optional<unsigned> llvm::dwarf::OperationArity(dwarf::LocationAtom Op) { |
240 | switch (Op) { |
241 | default: |
242 | return std::nullopt; |
243 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
244 | case DW_OP_##NAME: \ |
245 | if (ARITY == -1) \ |
246 | return std::nullopt; \ |
247 | return ARITY; |
248 | #include "llvm/BinaryFormat/Dwarf.def" |
249 | } |
250 | } |
251 | |
252 | unsigned llvm::dwarf::OperationVendor(dwarf::LocationAtom Op) { |
253 | switch (Op) { |
254 | default: |
255 | return 0; |
256 | #define HANDLE_DW_OP(ID, NAME, OPERANDS, ARITY, VERSION, VENDOR) \ |
257 | case DW_OP_##NAME: \ |
258 | return DWARF_VENDOR_##VENDOR; |
259 | #include "llvm/BinaryFormat/Dwarf.def" |
260 | } |
261 | } |
262 | |
263 | StringRef llvm::dwarf::AttributeEncodingString(unsigned Encoding) { |
264 | switch (Encoding) { |
265 | default: |
266 | return StringRef(); |
267 | #define HANDLE_DW_ATE(ID, NAME, VERSION, VENDOR) \ |
268 | case DW_ATE_##NAME: \ |
269 | return "DW_ATE_" #NAME; |
270 | #include "llvm/BinaryFormat/Dwarf.def" |
271 | } |
272 | } |
273 | |
274 | unsigned llvm::dwarf::getAttributeEncoding(StringRef EncodingString) { |
275 | return StringSwitch<unsigned>(EncodingString) |
276 | #define HANDLE_DW_ATE(ID, NAME, VERSION, VENDOR) \ |
277 | .Case("DW_ATE_" #NAME, DW_ATE_##NAME) |
278 | #include "llvm/BinaryFormat/Dwarf.def" |
279 | .Default(Value: 0); |
280 | } |
281 | |
282 | unsigned llvm::dwarf::AttributeEncodingVersion(dwarf::TypeKind ATE) { |
283 | switch (ATE) { |
284 | default: |
285 | return 0; |
286 | #define HANDLE_DW_ATE(ID, NAME, VERSION, VENDOR) \ |
287 | case DW_ATE_##NAME: \ |
288 | return VERSION; |
289 | #include "llvm/BinaryFormat/Dwarf.def" |
290 | } |
291 | } |
292 | |
293 | unsigned llvm::dwarf::AttributeEncodingVendor(dwarf::TypeKind ATE) { |
294 | switch (ATE) { |
295 | default: |
296 | return 0; |
297 | #define HANDLE_DW_ATE(ID, NAME, VERSION, VENDOR) \ |
298 | case DW_ATE_##NAME: \ |
299 | return DWARF_VENDOR_##VENDOR; |
300 | #include "llvm/BinaryFormat/Dwarf.def" |
301 | } |
302 | } |
303 | |
304 | StringRef llvm::dwarf::DecimalSignString(unsigned Sign) { |
305 | switch (Sign) { |
306 | case DW_DS_unsigned: |
307 | return "DW_DS_unsigned" ; |
308 | case DW_DS_leading_overpunch: |
309 | return "DW_DS_leading_overpunch" ; |
310 | case DW_DS_trailing_overpunch: |
311 | return "DW_DS_trailing_overpunch" ; |
312 | case DW_DS_leading_separate: |
313 | return "DW_DS_leading_separate" ; |
314 | case DW_DS_trailing_separate: |
315 | return "DW_DS_trailing_separate" ; |
316 | } |
317 | return StringRef(); |
318 | } |
319 | |
320 | StringRef llvm::dwarf::EndianityString(unsigned Endian) { |
321 | switch (Endian) { |
322 | case DW_END_default: |
323 | return "DW_END_default" ; |
324 | case DW_END_big: |
325 | return "DW_END_big" ; |
326 | case DW_END_little: |
327 | return "DW_END_little" ; |
328 | case DW_END_lo_user: |
329 | return "DW_END_lo_user" ; |
330 | case DW_END_hi_user: |
331 | return "DW_END_hi_user" ; |
332 | } |
333 | return StringRef(); |
334 | } |
335 | |
336 | StringRef llvm::dwarf::AccessibilityString(unsigned Access) { |
337 | switch (Access) { |
338 | // Accessibility codes |
339 | case DW_ACCESS_public: |
340 | return "DW_ACCESS_public" ; |
341 | case DW_ACCESS_protected: |
342 | return "DW_ACCESS_protected" ; |
343 | case DW_ACCESS_private: |
344 | return "DW_ACCESS_private" ; |
345 | } |
346 | return StringRef(); |
347 | } |
348 | |
349 | StringRef llvm::dwarf::DefaultedMemberString(unsigned DefaultedEncodings) { |
350 | switch (DefaultedEncodings) { |
351 | // Defaulted Member Encodings codes |
352 | case DW_DEFAULTED_no: |
353 | return "DW_DEFAULTED_no" ; |
354 | case DW_DEFAULTED_in_class: |
355 | return "DW_DEFAULTED_in_class" ; |
356 | case DW_DEFAULTED_out_of_class: |
357 | return "DW_DEFAULTED_out_of_class" ; |
358 | } |
359 | return StringRef(); |
360 | } |
361 | |
362 | StringRef llvm::dwarf::VisibilityString(unsigned Visibility) { |
363 | switch (Visibility) { |
364 | case DW_VIS_local: |
365 | return "DW_VIS_local" ; |
366 | case DW_VIS_exported: |
367 | return "DW_VIS_exported" ; |
368 | case DW_VIS_qualified: |
369 | return "DW_VIS_qualified" ; |
370 | } |
371 | return StringRef(); |
372 | } |
373 | |
374 | StringRef llvm::dwarf::VirtualityString(unsigned Virtuality) { |
375 | switch (Virtuality) { |
376 | default: |
377 | return StringRef(); |
378 | #define HANDLE_DW_VIRTUALITY(ID, NAME) \ |
379 | case DW_VIRTUALITY_##NAME: \ |
380 | return "DW_VIRTUALITY_" #NAME; |
381 | #include "llvm/BinaryFormat/Dwarf.def" |
382 | } |
383 | } |
384 | |
385 | unsigned llvm::dwarf::getVirtuality(StringRef VirtualityString) { |
386 | return StringSwitch<unsigned>(VirtualityString) |
387 | #define HANDLE_DW_VIRTUALITY(ID, NAME) \ |
388 | .Case("DW_VIRTUALITY_" #NAME, DW_VIRTUALITY_##NAME) |
389 | #include "llvm/BinaryFormat/Dwarf.def" |
390 | .Default(Value: DW_VIRTUALITY_invalid); |
391 | } |
392 | |
393 | StringRef llvm::dwarf::EnumKindString(unsigned EnumKind) { |
394 | switch (EnumKind) { |
395 | default: |
396 | return StringRef(); |
397 | #define HANDLE_DW_APPLE_ENUM_KIND(ID, NAME) \ |
398 | case DW_APPLE_ENUM_KIND_##NAME: \ |
399 | return "DW_APPLE_ENUM_KIND_" #NAME; |
400 | #include "llvm/BinaryFormat/Dwarf.def" |
401 | } |
402 | } |
403 | |
404 | unsigned llvm::dwarf::getEnumKind(StringRef EnumKindString) { |
405 | return StringSwitch<unsigned>(EnumKindString) |
406 | #define HANDLE_DW_APPLE_ENUM_KIND(ID, NAME) \ |
407 | .Case("DW_APPLE_ENUM_KIND_" #NAME, DW_APPLE_ENUM_KIND_##NAME) |
408 | #include "llvm/BinaryFormat/Dwarf.def" |
409 | .Default(Value: DW_APPLE_ENUM_KIND_invalid); |
410 | } |
411 | |
412 | StringRef llvm::dwarf::LanguageString(unsigned Language) { |
413 | switch (Language) { |
414 | default: |
415 | return StringRef(); |
416 | #define HANDLE_DW_LANG(ID, NAME, LOWER_BOUND, VERSION, VENDOR) \ |
417 | case DW_LANG_##NAME: \ |
418 | return "DW_LANG_" #NAME; |
419 | #include "llvm/BinaryFormat/Dwarf.def" |
420 | } |
421 | } |
422 | |
423 | unsigned llvm::dwarf::getLanguage(StringRef LanguageString) { |
424 | return StringSwitch<unsigned>(LanguageString) |
425 | #define HANDLE_DW_LANG(ID, NAME, LOWER_BOUND, VERSION, VENDOR) \ |
426 | .Case("DW_LANG_" #NAME, DW_LANG_##NAME) |
427 | #include "llvm/BinaryFormat/Dwarf.def" |
428 | .Default(Value: 0); |
429 | } |
430 | |
431 | unsigned llvm::dwarf::LanguageVersion(dwarf::SourceLanguage Lang) { |
432 | switch (Lang) { |
433 | default: |
434 | return 0; |
435 | #define HANDLE_DW_LANG(ID, NAME, LOWER_BOUND, VERSION, VENDOR) \ |
436 | case DW_LANG_##NAME: \ |
437 | return VERSION; |
438 | #include "llvm/BinaryFormat/Dwarf.def" |
439 | } |
440 | } |
441 | |
442 | unsigned llvm::dwarf::LanguageVendor(dwarf::SourceLanguage Lang) { |
443 | switch (Lang) { |
444 | default: |
445 | return 0; |
446 | #define HANDLE_DW_LANG(ID, NAME, LOWER_BOUND, VERSION, VENDOR) \ |
447 | case DW_LANG_##NAME: \ |
448 | return DWARF_VENDOR_##VENDOR; |
449 | #include "llvm/BinaryFormat/Dwarf.def" |
450 | } |
451 | } |
452 | |
453 | std::optional<unsigned> |
454 | llvm::dwarf::LanguageLowerBound(dwarf::SourceLanguage Lang) { |
455 | switch (Lang) { |
456 | default: |
457 | return std::nullopt; |
458 | #define HANDLE_DW_LANG(ID, NAME, LOWER_BOUND, VERSION, VENDOR) \ |
459 | case DW_LANG_##NAME: \ |
460 | return LOWER_BOUND; |
461 | #include "llvm/BinaryFormat/Dwarf.def" |
462 | } |
463 | } |
464 | |
465 | StringRef llvm::dwarf::LanguageDescription(dwarf::SourceLanguageName lname) { |
466 | switch (lname) { |
467 | #define HANDLE_DW_LNAME(ID, NAME, DESC, LOWER_BOUND) \ |
468 | case DW_LNAME_##NAME: \ |
469 | return DESC; |
470 | #include "llvm/BinaryFormat/Dwarf.def" |
471 | } |
472 | return "Unknown" ; |
473 | } |
474 | |
475 | StringRef llvm::dwarf::CaseString(unsigned Case) { |
476 | switch (Case) { |
477 | case DW_ID_case_sensitive: |
478 | return "DW_ID_case_sensitive" ; |
479 | case DW_ID_up_case: |
480 | return "DW_ID_up_case" ; |
481 | case DW_ID_down_case: |
482 | return "DW_ID_down_case" ; |
483 | case DW_ID_case_insensitive: |
484 | return "DW_ID_case_insensitive" ; |
485 | } |
486 | return StringRef(); |
487 | } |
488 | |
489 | StringRef llvm::dwarf::ConventionString(unsigned CC) { |
490 | switch (CC) { |
491 | default: |
492 | return StringRef(); |
493 | #define HANDLE_DW_CC(ID, NAME) \ |
494 | case DW_CC_##NAME: \ |
495 | return "DW_CC_" #NAME; |
496 | #include "llvm/BinaryFormat/Dwarf.def" |
497 | } |
498 | } |
499 | |
500 | unsigned llvm::dwarf::getCallingConvention(StringRef CCString) { |
501 | return StringSwitch<unsigned>(CCString) |
502 | #define HANDLE_DW_CC(ID, NAME) .Case("DW_CC_" #NAME, DW_CC_##NAME) |
503 | #include "llvm/BinaryFormat/Dwarf.def" |
504 | .Default(Value: 0); |
505 | } |
506 | |
507 | StringRef llvm::dwarf::InlineCodeString(unsigned Code) { |
508 | switch (Code) { |
509 | case DW_INL_not_inlined: |
510 | return "DW_INL_not_inlined" ; |
511 | case DW_INL_inlined: |
512 | return "DW_INL_inlined" ; |
513 | case DW_INL_declared_not_inlined: |
514 | return "DW_INL_declared_not_inlined" ; |
515 | case DW_INL_declared_inlined: |
516 | return "DW_INL_declared_inlined" ; |
517 | } |
518 | return StringRef(); |
519 | } |
520 | |
521 | StringRef llvm::dwarf::ArrayOrderString(unsigned Order) { |
522 | switch (Order) { |
523 | case DW_ORD_row_major: |
524 | return "DW_ORD_row_major" ; |
525 | case DW_ORD_col_major: |
526 | return "DW_ORD_col_major" ; |
527 | } |
528 | return StringRef(); |
529 | } |
530 | |
531 | StringRef llvm::dwarf::LNStandardString(unsigned Standard) { |
532 | switch (Standard) { |
533 | default: |
534 | return StringRef(); |
535 | #define HANDLE_DW_LNS(ID, NAME) \ |
536 | case DW_LNS_##NAME: \ |
537 | return "DW_LNS_" #NAME; |
538 | #include "llvm/BinaryFormat/Dwarf.def" |
539 | } |
540 | } |
541 | |
542 | StringRef llvm::dwarf::LNExtendedString(unsigned Encoding) { |
543 | switch (Encoding) { |
544 | default: |
545 | return StringRef(); |
546 | #define HANDLE_DW_LNE(ID, NAME) \ |
547 | case DW_LNE_##NAME: \ |
548 | return "DW_LNE_" #NAME; |
549 | #include "llvm/BinaryFormat/Dwarf.def" |
550 | } |
551 | } |
552 | |
553 | StringRef llvm::dwarf::MacinfoString(unsigned Encoding) { |
554 | switch (Encoding) { |
555 | // Macinfo Type Encodings |
556 | case DW_MACINFO_define: |
557 | return "DW_MACINFO_define" ; |
558 | case DW_MACINFO_undef: |
559 | return "DW_MACINFO_undef" ; |
560 | case DW_MACINFO_start_file: |
561 | return "DW_MACINFO_start_file" ; |
562 | case DW_MACINFO_end_file: |
563 | return "DW_MACINFO_end_file" ; |
564 | case DW_MACINFO_vendor_ext: |
565 | return "DW_MACINFO_vendor_ext" ; |
566 | case DW_MACINFO_invalid: |
567 | return "DW_MACINFO_invalid" ; |
568 | } |
569 | return StringRef(); |
570 | } |
571 | |
572 | unsigned llvm::dwarf::getMacinfo(StringRef MacinfoString) { |
573 | return StringSwitch<unsigned>(MacinfoString) |
574 | .Case(S: "DW_MACINFO_define" , Value: DW_MACINFO_define) |
575 | .Case(S: "DW_MACINFO_undef" , Value: DW_MACINFO_undef) |
576 | .Case(S: "DW_MACINFO_start_file" , Value: DW_MACINFO_start_file) |
577 | .Case(S: "DW_MACINFO_end_file" , Value: DW_MACINFO_end_file) |
578 | .Case(S: "DW_MACINFO_vendor_ext" , Value: DW_MACINFO_vendor_ext) |
579 | .Default(Value: DW_MACINFO_invalid); |
580 | } |
581 | |
582 | StringRef llvm::dwarf::MacroString(unsigned Encoding) { |
583 | switch (Encoding) { |
584 | default: |
585 | return StringRef(); |
586 | #define HANDLE_DW_MACRO(ID, NAME) \ |
587 | case DW_MACRO_##NAME: \ |
588 | return "DW_MACRO_" #NAME; |
589 | #include "llvm/BinaryFormat/Dwarf.def" |
590 | } |
591 | } |
592 | |
593 | StringRef llvm::dwarf::GnuMacroString(unsigned Encoding) { |
594 | switch (Encoding) { |
595 | default: |
596 | return StringRef(); |
597 | #define HANDLE_DW_MACRO_GNU(ID, NAME) \ |
598 | case DW_MACRO_GNU_##NAME: \ |
599 | return "DW_MACRO_GNU_" #NAME; |
600 | #include "llvm/BinaryFormat/Dwarf.def" |
601 | } |
602 | } |
603 | |
604 | unsigned llvm::dwarf::getMacro(StringRef MacroString) { |
605 | return StringSwitch<unsigned>(MacroString) |
606 | #define HANDLE_DW_MACRO(ID, NAME) .Case("DW_MACRO_" #NAME, ID) |
607 | #include "llvm/BinaryFormat/Dwarf.def" |
608 | .Default(Value: DW_MACINFO_invalid); |
609 | } |
610 | StringRef llvm::dwarf::RangeListEncodingString(unsigned Encoding) { |
611 | switch (Encoding) { |
612 | default: |
613 | return StringRef(); |
614 | #define HANDLE_DW_RLE(ID, NAME) \ |
615 | case DW_RLE_##NAME: \ |
616 | return "DW_RLE_" #NAME; |
617 | #include "llvm/BinaryFormat/Dwarf.def" |
618 | } |
619 | } |
620 | |
621 | StringRef llvm::dwarf::LocListEncodingString(unsigned Encoding) { |
622 | switch (Encoding) { |
623 | default: |
624 | return StringRef(); |
625 | #define HANDLE_DW_LLE(ID, NAME) \ |
626 | case DW_LLE_##NAME: \ |
627 | return "DW_LLE_" #NAME; |
628 | #include "llvm/BinaryFormat/Dwarf.def" |
629 | } |
630 | } |
631 | |
632 | StringRef llvm::dwarf::CallFrameString(unsigned Encoding, |
633 | Triple::ArchType Arch) { |
634 | assert(Arch != llvm::Triple::ArchType::UnknownArch); |
635 | #define SELECT_AARCH64 (Arch == llvm::Triple::aarch64_be || Arch == llvm::Triple::aarch64) |
636 | #define SELECT_MIPS64 Arch == llvm::Triple::mips64 |
637 | #define SELECT_SPARC (Arch == llvm::Triple::sparc || Arch == llvm::Triple::sparcv9) |
638 | #define SELECT_X86 (Arch == llvm::Triple::x86 || Arch == llvm::Triple::x86_64) |
639 | #define HANDLE_DW_CFA(ID, NAME) |
640 | #define HANDLE_DW_CFA_PRED(ID, NAME, PRED) \ |
641 | if (ID == Encoding && PRED) \ |
642 | return "DW_CFA_" #NAME; |
643 | #include "llvm/BinaryFormat/Dwarf.def" |
644 | |
645 | switch (Encoding) { |
646 | default: |
647 | return StringRef(); |
648 | #define HANDLE_DW_CFA_PRED(ID, NAME, PRED) |
649 | #define HANDLE_DW_CFA(ID, NAME) \ |
650 | case DW_CFA_##NAME: \ |
651 | return "DW_CFA_" #NAME; |
652 | #include "llvm/BinaryFormat/Dwarf.def" |
653 | |
654 | #undef SELECT_X86 |
655 | #undef SELECT_SPARC |
656 | #undef SELECT_MIPS64 |
657 | #undef SELECT_AARCH64 |
658 | } |
659 | } |
660 | |
661 | StringRef llvm::dwarf::ApplePropertyString(unsigned Prop) { |
662 | switch (Prop) { |
663 | default: |
664 | return StringRef(); |
665 | #define HANDLE_DW_APPLE_PROPERTY(ID, NAME) \ |
666 | case DW_APPLE_PROPERTY_##NAME: \ |
667 | return "DW_APPLE_PROPERTY_" #NAME; |
668 | #include "llvm/BinaryFormat/Dwarf.def" |
669 | } |
670 | } |
671 | |
672 | StringRef llvm::dwarf::UnitTypeString(unsigned UT) { |
673 | switch (UT) { |
674 | default: |
675 | return StringRef(); |
676 | #define HANDLE_DW_UT(ID, NAME) \ |
677 | case DW_UT_##NAME: \ |
678 | return "DW_UT_" #NAME; |
679 | #include "llvm/BinaryFormat/Dwarf.def" |
680 | } |
681 | } |
682 | |
683 | StringRef llvm::dwarf::AtomTypeString(unsigned AT) { |
684 | switch (AT) { |
685 | case dwarf::DW_ATOM_null: |
686 | return "DW_ATOM_null" ; |
687 | case dwarf::DW_ATOM_die_offset: |
688 | return "DW_ATOM_die_offset" ; |
689 | case DW_ATOM_cu_offset: |
690 | return "DW_ATOM_cu_offset" ; |
691 | case DW_ATOM_die_tag: |
692 | return "DW_ATOM_die_tag" ; |
693 | case DW_ATOM_type_flags: |
694 | case DW_ATOM_type_type_flags: |
695 | return "DW_ATOM_type_flags" ; |
696 | case DW_ATOM_qual_name_hash: |
697 | return "DW_ATOM_qual_name_hash" ; |
698 | } |
699 | return StringRef(); |
700 | } |
701 | |
702 | StringRef llvm::dwarf::GDBIndexEntryKindString(GDBIndexEntryKind Kind) { |
703 | switch (Kind) { |
704 | case GIEK_NONE: |
705 | return "NONE" ; |
706 | case GIEK_TYPE: |
707 | return "TYPE" ; |
708 | case GIEK_VARIABLE: |
709 | return "VARIABLE" ; |
710 | case GIEK_FUNCTION: |
711 | return "FUNCTION" ; |
712 | case GIEK_OTHER: |
713 | return "OTHER" ; |
714 | case GIEK_UNUSED5: |
715 | return "UNUSED5" ; |
716 | case GIEK_UNUSED6: |
717 | return "UNUSED6" ; |
718 | case GIEK_UNUSED7: |
719 | return "UNUSED7" ; |
720 | } |
721 | llvm_unreachable("Unknown GDBIndexEntryKind value" ); |
722 | } |
723 | |
724 | StringRef |
725 | llvm::dwarf::GDBIndexEntryLinkageString(GDBIndexEntryLinkage Linkage) { |
726 | switch (Linkage) { |
727 | case GIEL_EXTERNAL: |
728 | return "EXTERNAL" ; |
729 | case GIEL_STATIC: |
730 | return "STATIC" ; |
731 | } |
732 | llvm_unreachable("Unknown GDBIndexEntryLinkage value" ); |
733 | } |
734 | |
735 | StringRef llvm::dwarf::AttributeValueString(uint16_t Attr, unsigned Val) { |
736 | switch (Attr) { |
737 | case DW_AT_accessibility: |
738 | return AccessibilityString(Access: Val); |
739 | case DW_AT_virtuality: |
740 | return VirtualityString(Virtuality: Val); |
741 | case DW_AT_language: |
742 | return LanguageString(Language: Val); |
743 | case DW_AT_encoding: |
744 | return AttributeEncodingString(Encoding: Val); |
745 | case DW_AT_decimal_sign: |
746 | return DecimalSignString(Sign: Val); |
747 | case DW_AT_endianity: |
748 | return EndianityString(Endian: Val); |
749 | case DW_AT_visibility: |
750 | return VisibilityString(Visibility: Val); |
751 | case DW_AT_identifier_case: |
752 | return CaseString(Case: Val); |
753 | case DW_AT_calling_convention: |
754 | return ConventionString(CC: Val); |
755 | case DW_AT_inline: |
756 | return InlineCodeString(Code: Val); |
757 | case DW_AT_ordering: |
758 | return ArrayOrderString(Order: Val); |
759 | case DW_AT_APPLE_runtime_class: |
760 | return LanguageString(Language: Val); |
761 | case DW_AT_defaulted: |
762 | return DefaultedMemberString(DefaultedEncodings: Val); |
763 | case DW_AT_APPLE_enum_kind: |
764 | return EnumKindString(EnumKind: Val); |
765 | } |
766 | |
767 | return StringRef(); |
768 | } |
769 | |
770 | StringRef llvm::dwarf::AtomValueString(uint16_t Atom, unsigned Val) { |
771 | switch (Atom) { |
772 | case DW_ATOM_null: |
773 | return "NULL" ; |
774 | case DW_ATOM_die_tag: |
775 | return TagString(Tag: Val); |
776 | } |
777 | |
778 | return StringRef(); |
779 | } |
780 | |
781 | StringRef llvm::dwarf::IndexString(unsigned Idx) { |
782 | switch (Idx) { |
783 | default: |
784 | return StringRef(); |
785 | #define HANDLE_DW_IDX(ID, NAME) \ |
786 | case DW_IDX_##NAME: \ |
787 | return "DW_IDX_" #NAME; |
788 | #include "llvm/BinaryFormat/Dwarf.def" |
789 | } |
790 | } |
791 | |
792 | std::optional<uint8_t> llvm::dwarf::getFixedFormByteSize(dwarf::Form Form, |
793 | FormParams Params) { |
794 | switch (Form) { |
795 | case DW_FORM_addr: |
796 | if (Params) |
797 | return Params.AddrSize; |
798 | return std::nullopt; |
799 | |
800 | case DW_FORM_block: // ULEB128 length L followed by L bytes. |
801 | case DW_FORM_block1: // 1 byte length L followed by L bytes. |
802 | case DW_FORM_block2: // 2 byte length L followed by L bytes. |
803 | case DW_FORM_block4: // 4 byte length L followed by L bytes. |
804 | case DW_FORM_string: // C-string with null terminator. |
805 | case DW_FORM_sdata: // SLEB128. |
806 | case DW_FORM_udata: // ULEB128. |
807 | case DW_FORM_ref_udata: // ULEB128. |
808 | case DW_FORM_indirect: // ULEB128. |
809 | case DW_FORM_exprloc: // ULEB128 length L followed by L bytes. |
810 | case DW_FORM_strx: // ULEB128. |
811 | case DW_FORM_addrx: // ULEB128. |
812 | case DW_FORM_loclistx: // ULEB128. |
813 | case DW_FORM_rnglistx: // ULEB128. |
814 | case DW_FORM_GNU_addr_index: // ULEB128. |
815 | case DW_FORM_GNU_str_index: // ULEB128. |
816 | return std::nullopt; |
817 | |
818 | case DW_FORM_ref_addr: |
819 | if (Params) |
820 | return Params.getRefAddrByteSize(); |
821 | return std::nullopt; |
822 | |
823 | case DW_FORM_flag: |
824 | case DW_FORM_data1: |
825 | case DW_FORM_ref1: |
826 | case DW_FORM_strx1: |
827 | case DW_FORM_addrx1: |
828 | return 1; |
829 | |
830 | case DW_FORM_data2: |
831 | case DW_FORM_ref2: |
832 | case DW_FORM_strx2: |
833 | case DW_FORM_addrx2: |
834 | return 2; |
835 | |
836 | case DW_FORM_strx3: |
837 | case DW_FORM_addrx3: |
838 | return 3; |
839 | |
840 | case DW_FORM_data4: |
841 | case DW_FORM_ref4: |
842 | case DW_FORM_ref_sup4: |
843 | case DW_FORM_strx4: |
844 | case DW_FORM_addrx4: |
845 | return 4; |
846 | |
847 | case DW_FORM_strp: |
848 | case DW_FORM_GNU_ref_alt: |
849 | case DW_FORM_GNU_strp_alt: |
850 | case DW_FORM_line_strp: |
851 | case DW_FORM_sec_offset: |
852 | case DW_FORM_strp_sup: |
853 | if (Params) |
854 | return Params.getDwarfOffsetByteSize(); |
855 | return std::nullopt; |
856 | |
857 | case DW_FORM_data8: |
858 | case DW_FORM_ref8: |
859 | case DW_FORM_ref_sig8: |
860 | case DW_FORM_ref_sup8: |
861 | return 8; |
862 | |
863 | case DW_FORM_flag_present: |
864 | return 0; |
865 | |
866 | case DW_FORM_data16: |
867 | return 16; |
868 | |
869 | case DW_FORM_implicit_const: |
870 | // The implicit value is stored in the abbreviation as a SLEB128, and |
871 | // there no data in debug info. |
872 | return 0; |
873 | |
874 | default: |
875 | break; |
876 | } |
877 | return std::nullopt; |
878 | } |
879 | |
880 | bool llvm::dwarf::isValidFormForVersion(Form F, unsigned Version, |
881 | bool ExtensionsOk) { |
882 | if (FormVendor(Form: F) == DWARF_VENDOR_DWARF) { |
883 | unsigned FV = FormVersion(Form: F); |
884 | return FV > 0 && FV <= Version; |
885 | } |
886 | return ExtensionsOk; |
887 | } |
888 | |
889 | StringRef llvm::dwarf::FormatString(DwarfFormat Format) { |
890 | switch (Format) { |
891 | case DWARF32: |
892 | return "DWARF32" ; |
893 | case DWARF64: |
894 | return "DWARF64" ; |
895 | } |
896 | return StringRef(); |
897 | } |
898 | |
899 | StringRef llvm::dwarf::FormatString(bool IsDWARF64) { |
900 | return FormatString(Format: IsDWARF64 ? DWARF64 : DWARF32); |
901 | } |
902 | |
903 | StringRef llvm::dwarf::RLEString(unsigned RLE) { |
904 | switch (RLE) { |
905 | default: |
906 | return StringRef(); |
907 | #define HANDLE_DW_RLE(ID, NAME) \ |
908 | case DW_RLE_##NAME: \ |
909 | return "DW_RLE_" #NAME; |
910 | #include "llvm/BinaryFormat/Dwarf.def" |
911 | } |
912 | } |
913 | |
914 | StringRef (*const llvm::dwarf::EnumTraits<Tag>::StringFn)(unsigned) = TagString; |
915 | StringRef (*const llvm::dwarf::EnumTraits<Attribute>::StringFn)(unsigned) = |
916 | AttributeString; |
917 | StringRef (*const llvm::dwarf::EnumTraits<Form>::StringFn)(unsigned) = |
918 | FormEncodingString; |
919 | StringRef (*const llvm::dwarf::EnumTraits<LocationAtom>::StringFn)(unsigned) = |
920 | OperationEncodingString; |
921 | StringRef (*const llvm::dwarf::EnumTraits<LineNumberOps>::StringFn)(unsigned) = |
922 | LNStandardString; |
923 | StringRef (*const llvm::dwarf::EnumTraits<Index>::StringFn)(unsigned) = |
924 | IndexString; |
925 | |
926 | constexpr char llvm::dwarf::EnumTraits<Attribute>::Type[]; |
927 | constexpr char llvm::dwarf::EnumTraits<Form>::Type[]; |
928 | constexpr char llvm::dwarf::EnumTraits<Index>::Type[]; |
929 | constexpr char llvm::dwarf::EnumTraits<Tag>::Type[]; |
930 | constexpr char llvm::dwarf::EnumTraits<LineNumberOps>::Type[]; |
931 | constexpr char llvm::dwarf::EnumTraits<LocationAtom>::Type[]; |
932 | |