Author: adrian Date: Thu May 3 09:51:37 2018 New Revision: 331462 URL: http://llvm.org/viewvc/llvm-project?rev=331462&view=rev Log: DWARFExpression: Convert file addresses to load addresses early on.
This is a change that only affects Swift and is NFC for the language plugins on llvm.org. In Swift, we can have global variables with a location such as DW_OP_addr <addr> DW_OP_deref. The DWARF expression evaluator doesn't know how to apply a DW_OP_deref to a file address, but at the very end we convert the file address into a load address. This patch moves the file->load address conversion to right after the result of the DW_OP_addr is pushed onto the stack so that a subsequent DW_OP_deref (and potentially other operations) can be interpreted. rdar://problem/39767528 Differential revision: https://reviews.llvm.org/D46362 Modified: lldb/trunk/include/lldb/Core/Value.h lldb/trunk/source/Core/Value.cpp lldb/trunk/source/Core/ValueObjectVariable.cpp lldb/trunk/source/Expression/DWARFExpression.cpp Modified: lldb/trunk/include/lldb/Core/Value.h URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/Value.h?rev=331462&r1=331461&r2=331462&view=diff ============================================================================== --- lldb/trunk/include/lldb/Core/Value.h (original) +++ lldb/trunk/include/lldb/Core/Value.h Thu May 3 09:51:37 2018 @@ -228,6 +228,9 @@ public: static const char *GetContextTypeAsCString(ContextType context_type); + /// Convert this value's file address to a load address, if possible. + void ConvertToLoadAddress(SymbolContext sc); + bool GetData(DataExtractor &data); void Clear(); Modified: lldb/trunk/source/Core/Value.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/Value.cpp?rev=331462&r1=331461&r2=331462&view=diff ============================================================================== --- lldb/trunk/source/Core/Value.cpp (original) +++ lldb/trunk/source/Core/Value.cpp Thu May 3 09:51:37 2018 @@ -669,6 +669,28 @@ const char *Value::GetContextTypeAsCStri return "???"; } +void Value::ConvertToLoadAddress(SymbolContext sc) { + if (GetValueType() != eValueTypeFileAddress) + return; + + if (!sc.module_sp) + return; + + lldb::addr_t file_addr = GetScalar().ULongLong(LLDB_INVALID_ADDRESS); + if (file_addr == LLDB_INVALID_ADDRESS) + return; + + Address so_addr; + if (!sc.module_sp->ResolveFileAddress(file_addr, so_addr)) + return; + lldb::addr_t load_addr = so_addr.GetLoadAddress(sc.target_sp.get()); + if (load_addr == LLDB_INVALID_ADDRESS) + return; + + SetValueType(Value::eValueTypeLoadAddress); + GetScalar() = load_addr; +} + ValueList::ValueList(const ValueList &rhs) { m_values = rhs.m_values; } const ValueList &ValueList::operator=(const ValueList &rhs) { Modified: lldb/trunk/source/Core/ValueObjectVariable.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/ValueObjectVariable.cpp?rev=331462&r1=331461&r2=331462&view=diff ============================================================================== --- lldb/trunk/source/Core/ValueObjectVariable.cpp (original) +++ lldb/trunk/source/Core/ValueObjectVariable.cpp Thu May 3 09:51:37 2018 @@ -234,26 +234,10 @@ bool ValueObjectVariable::UpdateValue() // If this variable is a simple type, we read all data for it into // m_data. Make sure this type has a value before we try and read it + SymbolContext var_sc; + variable->CalculateSymbolContext(&var_sc); // If we have a file address, convert it to a load address if we can. - if (value_type == Value::eValueTypeFileAddress && process_is_alive) { - lldb::addr_t file_addr = - m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); - if (file_addr != LLDB_INVALID_ADDRESS) { - SymbolContext var_sc; - variable->CalculateSymbolContext(&var_sc); - if (var_sc.module_sp) { - ObjectFile *objfile = var_sc.module_sp->GetObjectFile(); - if (objfile) { - Address so_addr(file_addr, objfile->GetSectionList()); - lldb::addr_t load_addr = so_addr.GetLoadAddress(target); - if (load_addr != LLDB_INVALID_ADDRESS) { - m_value.SetValueType(Value::eValueTypeLoadAddress); - m_value.GetScalar() = load_addr; - } - } - } - } - } + m_value.ConvertToLoadAddress(var_sc); if (!CanProvideValue()) { // this value object represents an aggregate type whose children have Modified: lldb/trunk/source/Expression/DWARFExpression.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/DWARFExpression.cpp?rev=331462&r1=331461&r2=331462&view=diff ============================================================================== --- lldb/trunk/source/Expression/DWARFExpression.cpp (original) +++ lldb/trunk/source/Expression/DWARFExpression.cpp Thu May 3 09:51:37 2018 @@ -1379,10 +1379,13 @@ bool DWARFExpression::Evaluate( // The DW_OP_addr operation has a single operand that encodes a machine // address and whose size is the size of an address on the target machine. //---------------------------------------------------------------------- - case DW_OP_addr: + case DW_OP_addr: { stack.push_back(Scalar(opcodes.GetAddress(&offset))); stack.back().SetValueType(Value::eValueTypeFileAddress); + auto sc = frame->GetSymbolContext(eSymbolContextFunction); + stack.back().ConvertToLoadAddress(sc); break; + } //---------------------------------------------------------------------- // The DW_OP_addr_sect_offset4 is used for any location expressions in _______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits