DWARFDebugInfoEntry.cpp revision 3887a902a1b8e5a6aad4fc822479845ce3ba0dfe
1//===-- DWARFDebugInfoEntry.cpp -------------------------------------------===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "DWARFDebugInfoEntry.h"
11#include "DWARFCompileUnit.h"
12#include "DWARFContext.h"
13#include "DWARFDebugAbbrev.h"
14#include "DWARFFormValue.h"
15#include "llvm/Support/Dwarf.h"
16#include "llvm/Support/Format.h"
17#include "llvm/Support/raw_ostream.h"
18using namespace llvm;
19using namespace dwarf;
20
21void DWARFDebugInfoEntryMinimal::dump(raw_ostream &OS,
22                                      const DWARFCompileUnit *cu,
23                                      unsigned recurseDepth,
24                                      unsigned indent) const {
25  DataExtractor debug_info_data = cu->getDebugInfoExtractor();
26  uint32_t offset = Offset;
27
28  if (debug_info_data.isValidOffset(offset)) {
29    uint32_t abbrCode = debug_info_data.getULEB128(&offset);
30
31    OS << format("\n0x%8.8x: ", Offset);
32    if (abbrCode) {
33      if (AbbrevDecl) {
34        const char *tagString = TagString(getTag());
35        if (tagString)
36          OS.indent(indent) << tagString;
37        else
38          OS.indent(indent) << format("DW_TAG_Unknown_%x", getTag());
39        OS << format(" [%u] %c\n", abbrCode,
40                     AbbrevDecl->hasChildren() ? '*' : ' ');
41
42        // Dump all data in the .debug_info for the attributes
43        const uint32_t numAttributes = AbbrevDecl->getNumAttributes();
44        for (uint32_t i = 0; i != numAttributes; ++i) {
45          uint16_t attr = AbbrevDecl->getAttrByIndex(i);
46          uint16_t form = AbbrevDecl->getFormByIndex(i);
47          dumpAttribute(OS, cu, &offset, attr, form, indent);
48        }
49
50        const DWARFDebugInfoEntryMinimal *child = getFirstChild();
51        if (recurseDepth > 0 && child) {
52          while (child) {
53            child->dump(OS, cu, recurseDepth-1, indent+2);
54            child = child->getSibling();
55          }
56        }
57      } else {
58        OS << "Abbreviation code not found in 'debug_abbrev' class for code: "
59           << abbrCode << '\n';
60      }
61    } else {
62      OS.indent(indent) << "NULL\n";
63    }
64  }
65}
66
67void DWARFDebugInfoEntryMinimal::dumpAttribute(raw_ostream &OS,
68                                               const DWARFCompileUnit *cu,
69                                               uint32_t* offset_ptr,
70                                               uint16_t attr,
71                                               uint16_t form,
72                                               unsigned indent) const {
73  OS << format("0x%8.8x: ", *offset_ptr);
74  OS.indent(indent+2);
75  const char *attrString = AttributeString(attr);
76  if (attrString)
77    OS << attrString;
78  else
79    OS << format("DW_AT_Unknown_%x", attr);
80  const char *formString = FormEncodingString(form);
81  if (formString)
82    OS << " [" << formString << ']';
83  else
84    OS << format(" [DW_FORM_Unknown_%x]", form);
85
86  DWARFFormValue formValue(form);
87
88  if (!formValue.extractValue(cu->getDebugInfoExtractor(), offset_ptr, cu))
89    return;
90
91  OS << "\t(";
92  formValue.dump(OS, cu);
93  OS << ")\n";
94}
95
96bool DWARFDebugInfoEntryMinimal::extractFast(const DWARFCompileUnit *cu,
97                                             const uint8_t *fixed_form_sizes,
98                                             uint32_t *offset_ptr) {
99  Offset = *offset_ptr;
100
101  DataExtractor debug_info_data = cu->getDebugInfoExtractor();
102  uint64_t abbrCode = debug_info_data.getULEB128(offset_ptr);
103
104  assert(fixed_form_sizes); // For best performance this should be specified!
105
106  if (abbrCode) {
107    uint32_t offset = *offset_ptr;
108
109    AbbrevDecl = cu->getAbbreviations()->getAbbreviationDeclaration(abbrCode);
110
111    // Skip all data in the .debug_info for the attributes
112    const uint32_t numAttributes = AbbrevDecl->getNumAttributes();
113    uint32_t i;
114    uint16_t form;
115    for (i=0; i<numAttributes; ++i) {
116      form = AbbrevDecl->getFormByIndex(i);
117
118      const uint8_t fixed_skip_size = fixed_form_sizes[form];
119      if (fixed_skip_size)
120        offset += fixed_skip_size;
121      else {
122        bool form_is_indirect = false;
123        do {
124          form_is_indirect = false;
125          uint32_t form_size = 0;
126          switch (form) {
127          // Blocks if inlined data that have a length field and the data bytes
128          // inlined in the .debug_info.
129          case DW_FORM_exprloc:
130          case DW_FORM_block:
131            form_size = debug_info_data.getULEB128(&offset);
132            break;
133          case DW_FORM_block1:
134            form_size = debug_info_data.getU8(&offset);
135            break;
136          case DW_FORM_block2:
137            form_size = debug_info_data.getU16(&offset);
138            break;
139          case DW_FORM_block4:
140            form_size = debug_info_data.getU32(&offset);
141            break;
142
143          // Inlined NULL terminated C-strings
144          case DW_FORM_string:
145            debug_info_data.getCStr(&offset);
146            break;
147
148          // Compile unit address sized values
149          case DW_FORM_addr:
150          case DW_FORM_ref_addr:
151            form_size = cu->getAddressByteSize();
152            break;
153
154          // 0 sized form.
155          case DW_FORM_flag_present:
156            form_size = 0;
157            break;
158
159          // 1 byte values
160          case DW_FORM_data1:
161          case DW_FORM_flag:
162          case DW_FORM_ref1:
163            form_size = 1;
164            break;
165
166          // 2 byte values
167          case DW_FORM_data2:
168          case DW_FORM_ref2:
169            form_size = 2;
170            break;
171
172          // 4 byte values
173          case DW_FORM_strp:
174          case DW_FORM_data4:
175          case DW_FORM_ref4:
176            form_size = 4;
177            break;
178
179          // 8 byte values
180          case DW_FORM_data8:
181          case DW_FORM_ref8:
182          case DW_FORM_ref_sig8:
183            form_size = 8;
184            break;
185
186          // signed or unsigned LEB 128 values
187          case DW_FORM_sdata:
188          case DW_FORM_udata:
189          case DW_FORM_ref_udata:
190            debug_info_data.getULEB128(&offset);
191            break;
192
193          case DW_FORM_indirect:
194            form_is_indirect = true;
195            form = debug_info_data.getULEB128(&offset);
196            break;
197
198          case DW_FORM_sec_offset:
199            if (cu->getAddressByteSize() == 4)
200              debug_info_data.getU32(offset_ptr);
201            else
202              debug_info_data.getU64(offset_ptr);
203            break;
204
205          default:
206            *offset_ptr = Offset;
207            return false;
208          }
209          offset += form_size;
210
211        } while (form_is_indirect);
212      }
213    }
214    *offset_ptr = offset;
215    return true;
216  } else {
217    AbbrevDecl = NULL;
218    return true; // NULL debug tag entry
219  }
220}
221
222bool
223DWARFDebugInfoEntryMinimal::extract(const DWARFCompileUnit *cu,
224                                    uint32_t *offset_ptr) {
225  DataExtractor debug_info_data = cu->getDebugInfoExtractor();
226  const uint32_t cu_end_offset = cu->getNextCompileUnitOffset();
227  const uint8_t cu_addr_size = cu->getAddressByteSize();
228  uint32_t offset = *offset_ptr;
229  if ((offset < cu_end_offset) && debug_info_data.isValidOffset(offset)) {
230    Offset = offset;
231
232    uint64_t abbrCode = debug_info_data.getULEB128(&offset);
233
234    if (abbrCode) {
235      AbbrevDecl = cu->getAbbreviations()->getAbbreviationDeclaration(abbrCode);
236
237      if (AbbrevDecl) {
238        uint16_t tag = AbbrevDecl->getTag();
239
240        bool isCompileUnitTag = tag == DW_TAG_compile_unit;
241        if(cu && isCompileUnitTag)
242          const_cast<DWARFCompileUnit*>(cu)->setBaseAddress(0);
243
244        // Skip all data in the .debug_info for the attributes
245        const uint32_t numAttributes = AbbrevDecl->getNumAttributes();
246        for (uint32_t i = 0; i != numAttributes; ++i) {
247          uint16_t attr = AbbrevDecl->getAttrByIndex(i);
248          uint16_t form = AbbrevDecl->getFormByIndex(i);
249
250          if (isCompileUnitTag &&
251              ((attr == DW_AT_entry_pc) || (attr == DW_AT_low_pc))) {
252            DWARFFormValue form_value(form);
253            if (form_value.extractValue(debug_info_data, &offset, cu)) {
254              if (attr == DW_AT_low_pc || attr == DW_AT_entry_pc)
255                const_cast<DWARFCompileUnit*>(cu)
256                  ->setBaseAddress(form_value.getUnsigned());
257            }
258          } else {
259            bool form_is_indirect = false;
260            do {
261              form_is_indirect = false;
262              register uint32_t form_size = 0;
263              switch (form) {
264              // Blocks if inlined data that have a length field and the data
265              // bytes // inlined in the .debug_info
266              case DW_FORM_exprloc:
267              case DW_FORM_block:
268                form_size = debug_info_data.getULEB128(&offset);
269                break;
270              case DW_FORM_block1:
271                form_size = debug_info_data.getU8(&offset);
272                break;
273              case DW_FORM_block2:
274                form_size = debug_info_data.getU16(&offset);
275                break;
276              case DW_FORM_block4:
277                form_size = debug_info_data.getU32(&offset);
278                break;
279
280              // Inlined NULL terminated C-strings
281              case DW_FORM_string:
282                debug_info_data.getCStr(&offset);
283                break;
284
285              // Compile unit address sized values
286              case DW_FORM_addr:
287              case DW_FORM_ref_addr:
288                form_size = cu_addr_size;
289                break;
290
291              // 0 byte value
292              case DW_FORM_flag_present:
293                form_size = 0;
294                break;
295
296              // 1 byte values
297              case DW_FORM_data1:
298              case DW_FORM_flag:
299              case DW_FORM_ref1:
300                form_size = 1;
301                break;
302
303              // 2 byte values
304              case DW_FORM_data2:
305              case DW_FORM_ref2:
306                form_size = 2;
307                break;
308
309                // 4 byte values
310              case DW_FORM_strp:
311                form_size = 4;
312                break;
313
314              case DW_FORM_data4:
315              case DW_FORM_ref4:
316                form_size = 4;
317                break;
318
319              // 8 byte values
320              case DW_FORM_data8:
321              case DW_FORM_ref8:
322              case DW_FORM_ref_sig8:
323                form_size = 8;
324                break;
325
326              // signed or unsigned LEB 128 values
327              case DW_FORM_sdata:
328              case DW_FORM_udata:
329              case DW_FORM_ref_udata:
330                debug_info_data.getULEB128(&offset);
331                break;
332
333              case DW_FORM_indirect:
334                form = debug_info_data.getULEB128(&offset);
335                form_is_indirect = true;
336                break;
337
338              case DW_FORM_sec_offset:
339                if (cu->getAddressByteSize() == 4)
340                  debug_info_data.getU32(offset_ptr);
341                else
342                  debug_info_data.getU64(offset_ptr);
343                break;
344
345              default:
346                *offset_ptr = offset;
347                return false;
348              }
349
350              offset += form_size;
351            } while (form_is_indirect);
352          }
353        }
354        *offset_ptr = offset;
355        return true;
356      }
357    } else {
358      AbbrevDecl = NULL;
359      *offset_ptr = offset;
360      return true;    // NULL debug tag entry
361    }
362  }
363
364  return false;
365}
366
367uint32_t
368DWARFDebugInfoEntryMinimal::getAttributeValue(const DWARFCompileUnit *cu,
369                                              const uint16_t attr,
370                                              DWARFFormValue &form_value,
371                                              uint32_t *end_attr_offset_ptr)
372                                              const {
373  if (AbbrevDecl) {
374    uint32_t attr_idx = AbbrevDecl->findAttributeIndex(attr);
375
376    if (attr_idx != -1U) {
377      uint32_t offset = getOffset();
378
379      DataExtractor debug_info_data = cu->getDebugInfoExtractor();
380
381      // Skip the abbreviation code so we are at the data for the attributes
382      debug_info_data.getULEB128(&offset);
383
384      uint32_t idx = 0;
385      while (idx < attr_idx)
386        DWARFFormValue::skipValue(AbbrevDecl->getFormByIndex(idx++),
387                                  debug_info_data, &offset, cu);
388
389      const uint32_t attr_offset = offset;
390      form_value = DWARFFormValue(AbbrevDecl->getFormByIndex(idx));
391      if (form_value.extractValue(debug_info_data, &offset, cu)) {
392        if (end_attr_offset_ptr)
393          *end_attr_offset_ptr = offset;
394        return attr_offset;
395      }
396    }
397  }
398
399  return 0;
400}
401
402const char*
403DWARFDebugInfoEntryMinimal::getAttributeValueAsString(
404    const DWARFCompileUnit* cu,
405    const uint16_t attr,
406    const char* fail_value) const {
407  DWARFFormValue form_value;
408  if (getAttributeValue(cu, attr, form_value)) {
409    DataExtractor stringExtractor(cu->getContext().getStringSection(),
410        false, 0);
411    return form_value.getAsCString(&stringExtractor);
412  }
413  return fail_value;
414}
415
416uint64_t
417DWARFDebugInfoEntryMinimal::getAttributeValueAsUnsigned(
418    const DWARFCompileUnit* cu,
419    const uint16_t attr,
420    uint64_t fail_value) const {
421  DWARFFormValue form_value;
422  if (getAttributeValue(cu, attr, form_value))
423      return form_value.getUnsigned();
424  return fail_value;
425}
426
427int64_t
428DWARFDebugInfoEntryMinimal::getAttributeValueAsSigned(
429    const DWARFCompileUnit* cu,
430    const uint16_t attr,
431    int64_t fail_value) const {
432  DWARFFormValue form_value;
433  if (getAttributeValue(cu, attr, form_value))
434      return form_value.getSigned();
435  return fail_value;
436}
437
438uint64_t
439DWARFDebugInfoEntryMinimal::getAttributeValueAsReference(
440                                                  const DWARFCompileUnit* cu,
441                                                  const uint16_t attr,
442                                                  uint64_t fail_value) const {
443  DWARFFormValue form_value;
444  if (getAttributeValue(cu, attr, form_value))
445      return form_value.getReference(cu);
446  return fail_value;
447}
448
449void
450DWARFDebugInfoEntryMinimal::buildAddressRangeTable(const DWARFCompileUnit *cu,
451                                               DWARFDebugAranges *debug_aranges)
452                                                   const {
453  if (AbbrevDecl) {
454    uint16_t tag = AbbrevDecl->getTag();
455    if (tag == DW_TAG_subprogram) {
456      uint64_t hi_pc = -1ULL;
457      uint64_t lo_pc = getAttributeValueAsUnsigned(cu, DW_AT_low_pc, -1ULL);
458      if (lo_pc != -1ULL)
459        hi_pc = getAttributeValueAsUnsigned(cu, DW_AT_high_pc, -1ULL);
460      if (hi_pc != -1ULL)
461        debug_aranges->appendRange(cu->getOffset(), lo_pc, hi_pc);
462    }
463
464    const DWARFDebugInfoEntryMinimal *child = getFirstChild();
465    while (child) {
466      child->buildAddressRangeTable(cu, debug_aranges);
467      child = child->getSibling();
468    }
469  }
470}
471
472bool
473DWARFDebugInfoEntryMinimal::addressRangeContainsAddress(
474    const DWARFCompileUnit *cu, const uint64_t address) const {
475  if (!isNULL() && getTag() == DW_TAG_subprogram) {
476    uint64_t hi_pc = -1ULL;
477    uint64_t lo_pc = getAttributeValueAsUnsigned(cu, DW_AT_low_pc, -1ULL);
478    if (lo_pc != -1ULL)
479      hi_pc = getAttributeValueAsUnsigned(cu, DW_AT_high_pc, -1ULL);
480    if (hi_pc != -1ULL) {
481      return (lo_pc <= address && address < hi_pc);
482    }
483  }
484  return false;
485}
486
487const char*
488DWARFDebugInfoEntryMinimal::getSubprogramName(
489    const DWARFCompileUnit *cu) const {
490  if (isNULL() || getTag() != DW_TAG_subprogram)
491    return 0;
492  // Try to get mangled name if possible.
493  if (const char *name =
494      getAttributeValueAsString(cu, DW_AT_MIPS_linkage_name, 0))
495    return name;
496  if (const char *name = getAttributeValueAsString(cu, DW_AT_linkage_name, 0))
497    return name;
498  if (const char *name = getAttributeValueAsString(cu, DW_AT_name, 0))
499    return name;
500  // Try to get name from specification DIE.
501  uint32_t spec_ref =
502      getAttributeValueAsReference(cu, DW_AT_specification, -1U);
503  if (spec_ref != -1U) {
504    DWARFDebugInfoEntryMinimal spec_die;
505    if (spec_die.extract(cu, &spec_ref)) {
506      if (const char *name = spec_die.getSubprogramName(cu))
507        return name;
508    }
509  }
510  // Try to get name from abstract origin DIE.
511  uint32_t abs_origin_ref =
512      getAttributeValueAsReference(cu, DW_AT_abstract_origin, -1U);
513  if (abs_origin_ref != -1U) {
514    DWARFDebugInfoEntryMinimal abs_origin_die;
515    if (abs_origin_die.extract(cu, &abs_origin_ref)) {
516      if (const char *name = abs_origin_die.getSubprogramName(cu))
517        return name;
518    }
519  }
520  return 0;
521}
522