summaryrefslogtreecommitdiffstats
path: root/lldb/source/Plugins/SymbolFile
diff options
context:
space:
mode:
Diffstat (limited to 'lldb/source/Plugins/SymbolFile')
-rw-r--r--lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp6
-rw-r--r--lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp68
-rw-r--r--lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h18
-rw-r--r--lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp22
-rw-r--r--lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h3
5 files changed, 105 insertions, 12 deletions
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
index 26ca8c3acf4..f42164deafc 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugInfoEntry.cpp
@@ -1067,9 +1067,9 @@ size_t DWARFDebugInfoEntry::GetAttributeAddressRanges(
dwarf2Data, cu, DW_AT_ranges, DW_INVALID_OFFSET,
check_specification_or_abstract_origin);
if (debug_ranges_offset != DW_INVALID_OFFSET) {
- DWARFDebugRanges *debug_ranges = dwarf2Data->DebugRanges();
-
- debug_ranges->FindRanges(cu->GetRangesBase(), debug_ranges_offset, ranges);
+ if (DWARFDebugRanges *debug_ranges = dwarf2Data->DebugRanges())
+ debug_ranges->FindRanges(cu->GetRangesBase(), debug_ranges_offset,
+ ranges);
ranges.Slide(cu->GetBaseAddress());
} else if (check_hi_lo_pc) {
dw_addr_t lo_pc = LLDB_INVALID_ADDRESS;
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
index 89e27efb3cc..e891fce4288 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.cpp
@@ -123,3 +123,71 @@ bool DWARFDebugRanges::FindRanges(dw_addr_t debug_ranges_base,
}
return false;
}
+
+bool DWARFDebugRngLists::ExtractRangeList(const DWARFDataExtractor &data,
+ uint8_t addrSize,
+ lldb::offset_t *offset_ptr,
+ DWARFRangeList &rangeList) {
+ rangeList.Clear();
+
+ bool error = false;
+ while (!error) {
+ switch (data.GetU8(offset_ptr)) {
+ case DW_RLE_end_of_list:
+ return true;
+
+ case DW_RLE_start_length: {
+ dw_addr_t begin = data.GetMaxU64(offset_ptr, addrSize);
+ dw_addr_t len = data.GetULEB128(offset_ptr);
+ rangeList.Append(DWARFRangeList::Entry(begin, len));
+ break;
+ }
+
+ default:
+ // Next encodings are not yet supported:
+ // DW_RLE_base_addressx, DW_RLE_startx_endx, DW_RLE_startx_length,
+ // DW_RLE_offset_pair, DW_RLE_base_address, DW_RLE_start_end
+ lldbassert(0 && "unknown range list entry encoding");
+ error = true;
+ }
+ }
+
+ return false;
+}
+
+void DWARFDebugRngLists::Extract(SymbolFileDWARF *dwarf2Data) {
+ const DWARFDataExtractor &data = dwarf2Data->get_debug_rnglists_data();
+ lldb::offset_t offset = 0;
+
+ uint64_t length = data.GetU32(&offset);
+ bool isDwarf64 = false;
+ if (length == 0xffffffff) {
+ length = data.GetU64(&offset);
+ isDwarf64 = true;
+ }
+ lldb::offset_t end = offset + length;
+
+ // Check version.
+ if (data.GetU16(&offset) < 5)
+ return;
+
+ uint8_t addrSize = data.GetU8(&offset);
+
+ // We do not support non-zero segment selector size.
+ if (data.GetU8(&offset) != 0) {
+ lldbassert(0 && "not implemented");
+ return;
+ }
+
+ uint32_t offsetsAmount = data.GetU32(&offset);
+ for (uint32_t i = 0; i < offsetsAmount; ++i)
+ Offsets.push_back(data.GetPointer(&offset));
+
+ lldb::offset_t listOffset = offset;
+ DWARFRangeList rangeList;
+ while (offset < end && ExtractRangeList(data, addrSize, &offset, rangeList)) {
+ rangeList.Sort();
+ m_range_map[listOffset] = rangeList;
+ listOffset = offset;
+ }
+}
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h
index f514359e00a..e239bc54add 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h
+++ b/lldb/source/Plugins/SymbolFile/DWARF/DWARFDebugRanges.h
@@ -18,8 +18,9 @@
class DWARFDebugRanges {
public:
DWARFDebugRanges();
- ~DWARFDebugRanges();
- void Extract(SymbolFileDWARF *dwarf2Data);
+ virtual ~DWARFDebugRanges();
+ virtual void Extract(SymbolFileDWARF *dwarf2Data);
+
static void Dump(lldb_private::Stream &s,
const lldb_private::DWARFDataExtractor &debug_ranges_data,
lldb::offset_t *offset_ptr, dw_addr_t cu_base_addr);
@@ -37,4 +38,17 @@ protected:
range_map m_range_map;
};
+// DWARF v5 .debug_rnglists section.
+class DWARFDebugRngLists : public DWARFDebugRanges {
+public:
+ void Extract(SymbolFileDWARF *dwarf2Data) override;
+
+protected:
+ bool ExtractRangeList(const lldb_private::DWARFDataExtractor &data,
+ uint8_t addrSize, lldb::offset_t *offset_ptr,
+ DWARFRangeList &list);
+
+ std::vector<uint64_t> Offsets;
+};
+
#endif // SymbolFileDWARF_DWARFDebugRanges_h_
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
index 4f9e726f065..59163a9a027 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
+++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
@@ -410,9 +410,9 @@ SymbolFileDWARF::SymbolFileDWARF(ObjectFile *objfile)
m_debug_map_module_wp(), m_debug_map_symfile(NULL), m_data_debug_abbrev(),
m_data_debug_aranges(), m_data_debug_frame(), m_data_debug_info(),
m_data_debug_line(), m_data_debug_macro(), m_data_debug_loc(),
- m_data_debug_ranges(), m_data_debug_str(), m_data_apple_names(),
- m_data_apple_types(), m_data_apple_namespaces(), m_abbr(), m_info(),
- m_line(), m_fetched_external_modules(false),
+ m_data_debug_ranges(), m_data_debug_rnglists(), m_data_debug_str(),
+ m_data_apple_names(), m_data_apple_types(), m_data_apple_namespaces(),
+ m_abbr(), m_info(), m_line(), m_fetched_external_modules(false),
m_supports_DW_AT_APPLE_objc_complete_type(eLazyBoolCalculate), m_ranges(),
m_unique_ast_type_map() {}
@@ -659,6 +659,11 @@ const DWARFDataExtractor &SymbolFileDWARF::get_debug_ranges_data() {
m_data_debug_ranges);
}
+const DWARFDataExtractor &SymbolFileDWARF::get_debug_rnglists_data() {
+ return GetCachedSectionData(eSectionTypeDWARFDebugRngLists,
+ m_data_debug_rnglists);
+}
+
const DWARFDataExtractor &SymbolFileDWARF::get_debug_str_data() {
return GetCachedSectionData(eSectionTypeDWARFDebugStr, m_data_debug_str);
}
@@ -753,11 +758,14 @@ DWARFDebugRanges *SymbolFileDWARF::DebugRanges() {
static Timer::Category func_cat(LLVM_PRETTY_FUNCTION);
Timer scoped_timer(func_cat, "%s this = %p", LLVM_PRETTY_FUNCTION,
static_cast<void *>(this));
- if (get_debug_ranges_data().GetByteSize() > 0) {
+
+ if (get_debug_ranges_data().GetByteSize() > 0)
m_ranges.reset(new DWARFDebugRanges());
- if (m_ranges.get())
- m_ranges->Extract(this);
- }
+ else if (get_debug_rnglists_data().GetByteSize() > 0)
+ m_ranges.reset(new DWARFDebugRngLists());
+
+ if (m_ranges.get())
+ m_ranges->Extract(this);
}
return m_ranges.get();
}
diff --git a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h
index abf4e39bc47..b3d087f0812 100644
--- a/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h
+++ b/lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h
@@ -54,6 +54,7 @@ class DWARFDebugInfo;
class DWARFDebugInfoEntry;
class DWARFDebugLine;
class DWARFDebugRanges;
+class DWARFDebugRngLists;
class DWARFDeclContext;
class DWARFDIECollection;
class DWARFFormValue;
@@ -244,6 +245,7 @@ public:
const lldb_private::DWARFDataExtractor &get_debug_macro_data();
const lldb_private::DWARFDataExtractor &get_debug_loc_data();
const lldb_private::DWARFDataExtractor &get_debug_ranges_data();
+ const lldb_private::DWARFDataExtractor &get_debug_rnglists_data();
const lldb_private::DWARFDataExtractor &get_debug_str_data();
const lldb_private::DWARFDataExtractor &get_debug_str_offsets_data();
const lldb_private::DWARFDataExtractor &get_debug_types_data();
@@ -474,6 +476,7 @@ protected:
DWARFDataSegment m_data_debug_macro;
DWARFDataSegment m_data_debug_loc;
DWARFDataSegment m_data_debug_ranges;
+ DWARFDataSegment m_data_debug_rnglists;
DWARFDataSegment m_data_debug_str;
DWARFDataSegment m_data_debug_str_offsets;
DWARFDataSegment m_data_debug_types;
OpenPOWER on IntegriCloud