https://github.com/UltimateForce21 created https://github.com/llvm/llvm-project/pull/144238
This patch introduces a new struct and helper API in `DWARFExpressionList` to expose variable location metadata (base address, end address, and DWARFExpression pointer) for a given PC address. It will be used in later patches to annotate disassembly instructions with source-level variable locations. ## New struct ``` /// Represents one entry in a DWARFExpressionList, with its range and expr. struct DWARFExpressionEntry { lldb::addr_t base; // file‐address start of this location range lldb::addr_t end; // file‐address end of this range (exclusive) const DWARFExpression *expr; // the DWARF expression for this range }; ``` ## New API ``` /// Retrieve the DWARFExpressionEntry covering a particular instruction. /// /// \param func_load_addr /// The load address of the start of the function containing this location list; /// used to translate between file offsets and load addresses. If this is /// LLDB_INVALID_ADDRESS, the stored CU base (m_func_file_addr) is used. /// /// \param load_addr /// The load address of the *current* PC (i.e., the instruction for which /// we want its variable‐location entry). We first convert this back into /// the function’s file‐address space to find the correct DWARF range. /// /// \returns /// On success, an entry whose `[base,end)` covers this PC; else an Error. llvm::Expected<DWARFExpressionEntry> GetExpressionEntryAtAddress(lldb::addr_t func_load_addr, lldb::addr_t load_addr) const; ``` ## Rationale LLDB already provides: ``` const DWARFExpression * GetExpressionAtAddress(lldb::addr_t func_load_addr, lldb::addr_t load_addr) const; ``` However, this only returns the DWARF expression itself, without the file‐address start (base) and end (end) of the location range. Those bounds are crucial for: 1) Detecting range beginnings: render a var = <location> annotation exactly when a variable’s live‐range starts. 2) Detecting range continuation: optionally display a “|” on subsequent instructions in the same range. 3) Detecting state changes: know when a variable moves (e.g. from one register to another), becomes a constant, or goes out of scope. These primitives form the foundation for the Rich Disassembler feature proposed for GSoC 25. >From 8ed8c540e7600d720a63bc2882a81a2c65c11d41 Mon Sep 17 00:00:00 2001 From: ultimateforce21 <abdullahmohammad...@gmail.com> Date: Wed, 11 Jun 2025 00:11:09 -0400 Subject: [PATCH] [lldb] Add DWARFExpressionEntry and GetExpressionEntryAtAddress() to DWARFExpressionList This introduces a new API for retrieving DWARF expression metadata associated with variable location entries at a given PC address. It provides the base, end, and expression pointer for downstream consumers such as disassembler annotations. Intended for use in richer instruction annotations in Instruction::Dump(). --- .../lldb/Expression/DWARFExpressionList.h | 12 +++++++++++ .../source/Expression/DWARFExpressionList.cpp | 21 +++++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/lldb/include/lldb/Expression/DWARFExpressionList.h b/lldb/include/lldb/Expression/DWARFExpressionList.h index d8f8ec247ed56..a329b37393018 100644 --- a/lldb/include/lldb/Expression/DWARFExpressionList.h +++ b/lldb/include/lldb/Expression/DWARFExpressionList.h @@ -59,6 +59,18 @@ class DWARFExpressionList { lldb::addr_t GetFuncFileAddress() { return m_func_file_addr; } + /// Represents an entry in the DWARFExpressionList with all needed metadata + struct DWARFExpressionEntry { + lldb::addr_t base; + lldb::addr_t end; + const DWARFExpression *expr; + }; + + /// Returns the entry (base, end, data) for a given PC address + llvm::Expected<DWARFExpressionEntry> + GetExpressionEntryAtAddress(lldb::addr_t func_load_addr, + lldb::addr_t load_addr) const; + const DWARFExpression *GetExpressionAtAddress(lldb::addr_t func_load_addr, lldb::addr_t load_addr) const; diff --git a/lldb/source/Expression/DWARFExpressionList.cpp b/lldb/source/Expression/DWARFExpressionList.cpp index 04592a1eb7ff4..b55bc7120c4af 100644 --- a/lldb/source/Expression/DWARFExpressionList.cpp +++ b/lldb/source/Expression/DWARFExpressionList.cpp @@ -53,6 +53,27 @@ bool DWARFExpressionList::ContainsAddress(lldb::addr_t func_load_addr, return GetExpressionAtAddress(func_load_addr, addr) != nullptr; } +llvm::Expected<DWARFExpressionList::DWARFExpressionEntry> +DWARFExpressionList::GetExpressionEntryAtAddress(lldb::addr_t func_load_addr, + lldb::addr_t load_addr) const { + if (const DWARFExpression *expr = GetAlwaysValidExpr()) { + return DWARFExpressionEntry{0, LLDB_INVALID_ADDRESS, expr}; + } + + if (func_load_addr == LLDB_INVALID_ADDRESS) + func_load_addr = m_func_file_addr; + + addr_t addr = load_addr - func_load_addr + m_func_file_addr; + uint32_t index = m_exprs.FindEntryIndexThatContains(addr); + if (index == UINT32_MAX) { + return llvm::createStringError(llvm::inconvertibleErrorCode(), + "No DWARF expression found for address 0x%llx", addr); + } + + const Entry &entry = *m_exprs.GetEntryAtIndex(index); + return DWARFExpressionEntry{entry.base, entry.GetRangeEnd(), &entry.data}; +} + const DWARFExpression * DWARFExpressionList::GetExpressionAtAddress(lldb::addr_t func_load_addr, lldb::addr_t load_addr) const { _______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits