This revision was automatically updated to reflect the committed changes.
Closed by commit rL245932: Handle DW_OP_GNU_addr_index in DWARF expressions 
(authored by tberghammer).

Changed prior to commit:
  http://reviews.llvm.org/D12290?vs=32971&id=33061#toc

Repository:
  rL LLVM

http://reviews.llvm.org/D12290

Files:
  lldb/trunk/include/lldb/Expression/DWARFExpression.h
  lldb/trunk/source/Expression/DWARFExpression.cpp
  lldb/trunk/source/Plugins/Process/Utility/RegisterContextLLDB.cpp
  lldb/trunk/source/Plugins/SymbolFile/DWARF/DWARFLocationDescription.cpp
  lldb/trunk/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
  lldb/trunk/source/Symbol/ClangASTContext.cpp
  lldb/trunk/source/Symbol/Function.cpp

Index: lldb/trunk/source/Plugins/Process/Utility/RegisterContextLLDB.cpp
===================================================================
--- lldb/trunk/source/Plugins/Process/Utility/RegisterContextLLDB.cpp
+++ lldb/trunk/source/Plugins/Process/Utility/RegisterContextLLDB.cpp
@@ -1488,7 +1488,11 @@
                                  unwindplan_regloc.GetDWARFExpressionLength(),
                                  process->GetByteOrder(), process->GetAddressByteSize());
         ModuleSP opcode_ctx;
-        DWARFExpression dwarfexpr (opcode_ctx, dwarfdata, 0, unwindplan_regloc.GetDWARFExpressionLength());
+        DWARFExpression dwarfexpr (opcode_ctx,
+                                   dwarfdata,
+                                   nullptr,
+                                   0,
+                                   unwindplan_regloc.GetDWARFExpressionLength());
         dwarfexpr.SetRegisterKind (unwindplan_registerkind);
         Value result;
         Error error;
@@ -1784,7 +1788,11 @@
                                      row->GetCFAValue().GetDWARFExpressionLength(),
                                      process->GetByteOrder(), process->GetAddressByteSize());
             ModuleSP opcode_ctx;
-            DWARFExpression dwarfexpr (opcode_ctx, dwarfdata, 0, row->GetCFAValue().GetDWARFExpressionLength());
+            DWARFExpression dwarfexpr (opcode_ctx,
+                                       dwarfdata,
+                                       nullptr,
+                                       0,
+                                       row->GetCFAValue().GetDWARFExpressionLength());
             dwarfexpr.SetRegisterKind (row_register_kind);
             Value result;
             Error error;
Index: lldb/trunk/source/Plugins/SymbolFile/DWARF/DWARFLocationDescription.cpp
===================================================================
--- lldb/trunk/source/Plugins/SymbolFile/DWARF/DWARFLocationDescription.cpp
+++ lldb/trunk/source/Plugins/SymbolFile/DWARF/DWARFLocationDescription.cpp
@@ -149,6 +149,8 @@
             size = 128; break;
         case DW_OP_regx:
             size = 128; break;
+        case DW_OP_GNU_addr_index:
+            size = 128; break;
         default:
             s.Printf("UNKNOWN ONE-OPERAND OPCODE, #%u", opcode);
             return 1;
Index: lldb/trunk/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
===================================================================
--- lldb/trunk/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
+++ lldb/trunk/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp
@@ -4013,7 +4013,7 @@
             Declaration decl;
             uint32_t i;
             lldb::user_id_t type_uid = LLDB_INVALID_UID;
-            DWARFExpression location;
+            DWARFExpression location(dwarf_cu);
             bool is_external = false;
             bool is_artificial = false;
             bool location_is_const_value_data = false;
Index: lldb/trunk/source/Symbol/ClangASTContext.cpp
===================================================================
--- lldb/trunk/source/Symbol/ClangASTContext.cpp
+++ lldb/trunk/source/Symbol/ClangASTContext.cpp
@@ -9616,7 +9616,7 @@
     int call_file = 0;
     int call_line = 0;
     int call_column = 0;
-    DWARFExpression frame_base;
+    DWARFExpression frame_base(dwarf_cu);
 
     assert (die->Tag() == DW_TAG_subprogram);
 
@@ -9835,6 +9835,7 @@
                                                                       NULL, // RegisterContext *
                                                                       module_sp,
                                                                       debug_info_data,
+                                                                      dwarf_cu,
                                                                       block_offset,
                                                                       block_length,
                                                                       eRegisterKindDWARF,
@@ -10204,7 +10205,7 @@
                 if (num_attributes > 0)
                 {
                     Declaration decl;
-                    DWARFExpression location;
+                    DWARFExpression location(dwarf_cu);
                     lldb::user_id_t encoding_uid = LLDB_INVALID_UID;
                     AccessType accessibility = default_accessibility;
                     bool is_virtual = false;
@@ -10237,6 +10238,7 @@
                                                                        NULL,
                                                                        module_sp,
                                                                        debug_info_data,
+                                                                       dwarf_cu,
                                                                        block_offset,
                                                                        block_length,
                                                                        eRegisterKindDWARF,
Index: lldb/trunk/source/Symbol/Function.cpp
===================================================================
--- lldb/trunk/source/Symbol/Function.cpp
+++ lldb/trunk/source/Symbol/Function.cpp
@@ -217,7 +217,7 @@
     m_mangled (mangled),
     m_block (func_uid),
     m_range (range),
-    m_frame_base (),
+    m_frame_base (nullptr),
     m_flags (),
     m_prologue_byte_size (0)
 {
@@ -241,7 +241,7 @@
     m_mangled (ConstString(mangled), true),
     m_block (func_uid),
     m_range (range),
-    m_frame_base (),
+    m_frame_base (nullptr),
     m_flags (),
     m_prologue_byte_size (0)
 {
Index: lldb/trunk/source/Expression/DWARFExpression.cpp
===================================================================
--- lldb/trunk/source/Expression/DWARFExpression.cpp
+++ lldb/trunk/source/Expression/DWARFExpression.cpp
@@ -38,6 +38,8 @@
 #include "lldb/Target/StackID.h"
 #include "lldb/Target/Thread.h"
 
+#include "Plugins/SymbolFile/DWARF/DWARFCompileUnit.h"
+
 using namespace lldb;
 using namespace lldb_private;
 
@@ -196,6 +198,7 @@
     case 0x98: return "DW_OP_call2";
     case 0x99: return "DW_OP_call4";
     case 0x9a: return "DW_OP_call_ref";
+    case 0xfb: return "DW_OP_GNU_addr_index";
 //    case DW_OP_APPLE_array_ref: return "DW_OP_APPLE_array_ref";
 //    case DW_OP_APPLE_extern: return "DW_OP_APPLE_extern";
     case DW_OP_APPLE_uninit: return "DW_OP_APPLE_uninit";
@@ -219,26 +222,33 @@
 //----------------------------------------------------------------------
 // DWARFExpression constructor
 //----------------------------------------------------------------------
-DWARFExpression::DWARFExpression() :
+DWARFExpression::DWARFExpression(DWARFCompileUnit* dwarf_cu) :
     m_module_wp(),
     m_data(),
+    m_dwarf_cu(dwarf_cu),
     m_reg_kind (eRegisterKindDWARF),
     m_loclist_slide (LLDB_INVALID_ADDRESS)
 {
 }
 
 DWARFExpression::DWARFExpression(const DWARFExpression& rhs) :
     m_module_wp(rhs.m_module_wp),
     m_data(rhs.m_data),
+    m_dwarf_cu(rhs.m_dwarf_cu),
     m_reg_kind (rhs.m_reg_kind),
     m_loclist_slide(rhs.m_loclist_slide)
 {
 }
 
 
-DWARFExpression::DWARFExpression(lldb::ModuleSP module_sp, const DataExtractor& data, lldb::offset_t data_offset, lldb::offset_t data_length) :
+DWARFExpression::DWARFExpression(lldb::ModuleSP module_sp,
+                                 const DataExtractor& data,
+                                 DWARFCompileUnit* dwarf_cu,
+                                 lldb::offset_t data_offset,
+                                 lldb::offset_t data_length) :
     m_module_wp(),
     m_data(data, data_offset, data_length),
+    m_dwarf_cu(dwarf_cu),
     m_reg_kind (eRegisterKindDWARF),
     m_loclist_slide(LLDB_INVALID_ADDRESS)
 {
@@ -624,6 +634,9 @@
         case DW_OP_form_tls_address:
             s->PutCString("DW_OP_form_tls_address");  // 0x9b
             break;
+        case DW_OP_GNU_addr_index:                                          // 0xfb
+            s->Printf("DW_OP_GNU_addr_index(0x%" PRIx64 ")", m_data.GetULEB128(&offset));
+            break;
         case DW_OP_GNU_push_tls_address:
             s->PutCString("DW_OP_GNU_push_tls_address");  // 0xe0
             break;
@@ -1027,6 +1040,7 @@
         case DW_OP_regx:        // 0x90 1 ULEB128 register
         case DW_OP_fbreg:       // 0x91 1 SLEB128 offset
         case DW_OP_piece:       // 0x93 1 ULEB128 size of piece addressed
+        case DW_OP_GNU_addr_index: // 0xfb 1 ULEB128 index
             data.Skip_LEB128(&offset); 
             return offset - data_offset;   
             
@@ -1051,7 +1065,8 @@
 }
 
 lldb::addr_t
-DWARFExpression::GetLocation_DW_OP_addr (uint32_t op_addr_idx, bool &error) const
+DWARFExpression::GetLocation_DW_OP_addr (uint32_t op_addr_idx,
+                                         bool &error) const
 {
     error = false;
     if (IsLocationList())
@@ -1070,6 +1085,25 @@
             else
                 ++curr_op_addr_idx;
         }
+        else if (op == DW_OP_GNU_addr_index)
+        {
+            uint64_t index = m_data.GetULEB128(&offset);
+            if (curr_op_addr_idx == op_addr_idx)
+            {
+                if (!m_dwarf_cu)
+                {
+                    error = true;
+                    break;
+                }
+
+                uint32_t index_size = m_dwarf_cu->GetAddressByteSize();
+                dw_offset_t addr_base = m_dwarf_cu->GetAddrBase();
+                lldb::offset_t offset = addr_base + index * index_size;
+                return m_dwarf_cu->GetSymbolFileDWARF()->get_debug_addr_data().GetMaxU64(&offset, index_size);
+            }
+            else
+                ++curr_op_addr_idx;
+        }
         else
         {
             const offset_t op_arg_size = GetOpcodeDataSize (m_data, offset, op);
@@ -1104,7 +1138,7 @@
             
             // So first we copy the data into a heap buffer
             std::unique_ptr<DataBufferHeap> head_data_ap (new DataBufferHeap (m_data.GetDataStart(),
-                                                                             m_data.GetByteSize()));
+                                                                              m_data.GetByteSize()));
             
             // Make en encoder so we can write the address into the buffer using
             // the correct byte order (endianness)
@@ -1310,7 +1344,19 @@
 
                     if (length > 0 && lo_pc <= pc && pc < hi_pc)
                     {
-                        return DWARFExpression::Evaluate (exe_ctx, expr_locals, decl_map, reg_ctx, module_sp, m_data, offset, length, m_reg_kind, initial_value_ptr, result, error_ptr);
+                        return DWARFExpression::Evaluate (exe_ctx,
+                                                          expr_locals,
+                                                          decl_map,
+                                                          reg_ctx,
+                                                          module_sp,
+                                                          m_data,
+                                                          m_dwarf_cu,
+                                                          offset,
+                                                          length,
+                                                          m_reg_kind,
+                                                          initial_value_ptr,
+                                                          result,
+                                                          error_ptr);
                     }
                     offset += length;
                 }
@@ -1322,7 +1368,19 @@
     }
 
     // Not a location list, just a single expression.
-    return DWARFExpression::Evaluate (exe_ctx, expr_locals, decl_map, reg_ctx, module_sp, m_data, 0, m_data.GetByteSize(), m_reg_kind, initial_value_ptr, result, error_ptr);
+    return DWARFExpression::Evaluate (exe_ctx,
+                                      expr_locals,
+                                      decl_map,
+                                      reg_ctx,
+                                      module_sp,
+                                      m_data,
+                                      m_dwarf_cu,
+                                      0,
+                                      m_data.GetByteSize(),
+                                      m_reg_kind,
+                                      initial_value_ptr,
+                                      result,
+                                      error_ptr);
 }
 
 
@@ -1336,6 +1394,7 @@
     RegisterContext *reg_ctx,
     lldb::ModuleSP module_sp,
     const DataExtractor& opcodes,
+    DWARFCompileUnit* dwarf_cu,
     const lldb::offset_t opcodes_offset,
     const lldb::offset_t opcodes_length,
     const lldb::RegisterKind reg_kind,
@@ -2950,6 +3009,32 @@
             }
             break;
 
+        //----------------------------------------------------------------------
+        // OPCODE: DW_OP_GNU_addr_index
+        // OPERANDS: 1
+        //      ULEB128: index to the .debug_addr section
+        // DESCRIPTION: Pushes an address to the stack from the .debug_addr
+        // section with the base address specified by the DW_AT_addr_base
+        // attribute and the 0 based index is the ULEB128 encoded index.
+        //----------------------------------------------------------------------
+        case DW_OP_GNU_addr_index:
+            {
+                if (!dwarf_cu)
+                {
+                    if (error_ptr)
+                        error_ptr->SetErrorString ("DW_OP_GNU_addr_index found without a compile being specified");
+                    return false;
+                }
+                uint64_t index = opcodes.GetULEB128(&offset);
+                uint32_t index_size = dwarf_cu->GetAddressByteSize();
+                dw_offset_t addr_base = dwarf_cu->GetAddrBase();
+                lldb::offset_t offset = addr_base + index * index_size;
+                uint64_t value = dwarf_cu->GetSymbolFileDWARF()->get_debug_addr_data().GetMaxU64(&offset, index_size);
+                stack.push_back(Scalar(value));
+                stack.back().SetValueType(Value::eValueTypeFileAddress);
+            }
+            break;
+
         default:
             if (log)
                 log->Printf("Unhandled opcode %s in DWARFExpression.", DW_OP_value_to_name(op));
Index: lldb/trunk/include/lldb/Expression/DWARFExpression.h
===================================================================
--- lldb/trunk/include/lldb/Expression/DWARFExpression.h
+++ lldb/trunk/include/lldb/Expression/DWARFExpression.h
@@ -17,12 +17,14 @@
 #include "lldb/Core/Error.h"
 #include "lldb/Core/Scalar.h"
 
+class DWARFCompileUnit;
+
 namespace lldb_private {
     
+class ClangExpressionDeclMap;
 class ClangExpressionVariable;
 class ClangExpressionVariableList;
 
-class ClangExpressionDeclMap;
 
 //----------------------------------------------------------------------
 /// @class DWARFExpression DWARFExpression.h "lldb/Expression/DWARFExpression.h"
@@ -43,7 +45,7 @@
     //------------------------------------------------------------------
     /// Constructor
     //------------------------------------------------------------------
-    DWARFExpression();
+    explicit DWARFExpression(DWARFCompileUnit* dwarf_cu);
 
     //------------------------------------------------------------------
     /// Constructor
@@ -60,6 +62,7 @@
     //------------------------------------------------------------------
     DWARFExpression(lldb::ModuleSP module,
                     const DataExtractor& data,
+                    DWARFCompileUnit* dwarf_cu,
                     lldb::offset_t data_offset,
                     lldb::offset_t data_length);
 
@@ -356,6 +359,7 @@
               RegisterContext *reg_ctx,
               lldb::ModuleSP opcode_ctx,
               const DataExtractor& opcodes,
+              DWARFCompileUnit* dwarf_cu,
               const lldb::offset_t offset,
               const lldb::offset_t length,
               const lldb::RegisterKind reg_set,
@@ -436,6 +440,9 @@
 
     lldb::ModuleWP m_module_wp;                 ///< Module which defined this expression.
     DataExtractor m_data;                       ///< A data extractor capable of reading opcode bytes
+    DWARFCompileUnit* m_dwarf_cu;               ///< The DWARF compile unit this expression belongs to. It is used
+                                                ///< to evaluate values indexing into the .debug_addr section (e.g.
+                                                ///< DW_OP_GNU_addr_index
     lldb::RegisterKind m_reg_kind;              ///< One of the defines that starts with LLDB_REGKIND_
     lldb::addr_t m_loclist_slide;               ///< A value used to slide the location list offsets so that 
                                                 ///< they are relative to the object that owns the location list
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to