84 lines · cpp
1//===-- DWARFDebugAranges.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-exception6//7//===----------------------------------------------------------------------===//8 9#include "DWARFDebugAranges.h"10#include "DWARFUnit.h"11#include "LogChannelDWARF.h"12#include "lldb/Utility/Log.h"13#include "lldb/Utility/Timer.h"14#include "llvm/DebugInfo/DWARF/DWARFDebugArangeSet.h"15 16using namespace lldb;17using namespace lldb_private;18using namespace lldb_private::plugin::dwarf;19using llvm::DWARFDebugArangeSet;20 21// Constructor22DWARFDebugAranges::DWARFDebugAranges() : m_aranges() {}23 24// Extract25void DWARFDebugAranges::extract(const DWARFDataExtractor &debug_aranges_data) {26 llvm::DWARFDataExtractor dwarf_data = debug_aranges_data.GetAsLLVMDWARF();27 lldb::offset_t offset = 0;28 29 DWARFDebugArangeSet set;30 Range range;31 while (dwarf_data.isValidOffset(offset)) {32 const lldb::offset_t set_offset = offset;33 if (llvm::Error error = set.extract(dwarf_data, &offset)) {34 Log *log = GetLog(DWARFLog::DebugInfo);35 LLDB_LOG_ERROR(log, std::move(error),36 "DWARFDebugAranges::extract failed to extract "37 ".debug_aranges set at offset {1:x}: {0}",38 set_offset);39 set.clear();40 return;41 }42 const uint64_t cu_offset = set.getCompileUnitDIEOffset();43 for (const auto &desc : set.descriptors()) {44 if (desc.Length != 0)45 m_aranges.Append(46 RangeToDIE::Entry(desc.Address, desc.Length, cu_offset));47 }48 }49}50 51void DWARFDebugAranges::Dump(Log *log) const {52 if (log == nullptr)53 return;54 55 const size_t num_entries = m_aranges.GetSize();56 for (size_t i = 0; i < num_entries; ++i) {57 const RangeToDIE::Entry *entry = m_aranges.GetEntryAtIndex(i);58 if (entry)59 LLDB_LOG(log, "{0:x8}: [{1:x16} - {2:x16})", entry->data,60 entry->GetRangeBase(), entry->GetRangeEnd());61 }62}63 64void DWARFDebugAranges::AppendRange(dw_offset_t offset, dw_addr_t low_pc,65 dw_addr_t high_pc) {66 if (high_pc > low_pc)67 m_aranges.Append(RangeToDIE::Entry(low_pc, high_pc - low_pc, offset));68}69 70void DWARFDebugAranges::Sort(bool minimize) {71 LLDB_SCOPED_TIMER();72 73 m_aranges.Sort();74 m_aranges.CombineConsecutiveEntriesWithEqualData();75}76 77// FindAddress78dw_offset_t DWARFDebugAranges::FindAddress(dw_addr_t address) const {79 const RangeToDIE::Entry *entry = m_aranges.FindEntryThatContains(address);80 if (entry)81 return entry->data;82 return DW_INVALID_OFFSET;83}84