diff options
author | emaste <emaste@FreeBSD.org> | 2015-02-06 21:38:51 +0000 |
---|---|---|
committer | emaste <emaste@FreeBSD.org> | 2015-02-06 21:38:51 +0000 |
commit | 0c2019f4ca6b2dc6d710f6bb16a0e3ed10271531 (patch) | |
tree | 09bc83f73246ee3c7a779605cd0122093d2a8a19 /source/Core/ValueObjectVariable.cpp | |
parent | 01ee1789d6aa7294e5966a97f8d29387f6f81699 (diff) | |
download | FreeBSD-src-0c2019f4ca6b2dc6d710f6bb16a0e3ed10271531.zip FreeBSD-src-0c2019f4ca6b2dc6d710f6bb16a0e3ed10271531.tar.gz |
Import LLDB as of upstream SVN r225923 (git 2b588ecd)
This corresponds with the branchpoint for the 3.6 release.
A number of files not required for the FreeBSD build have been removed.
Sponsored by: DARPA, AFRL
Diffstat (limited to 'source/Core/ValueObjectVariable.cpp')
-rw-r--r-- | source/Core/ValueObjectVariable.cpp | 43 |
1 files changed, 37 insertions, 6 deletions
diff --git a/source/Core/ValueObjectVariable.cpp b/source/Core/ValueObjectVariable.cpp index 225dc02..ab74a50 100644 --- a/source/Core/ValueObjectVariable.cpp +++ b/source/Core/ValueObjectVariable.cpp @@ -171,14 +171,44 @@ ValueObjectVariable::UpdateValue () m_value.SetClangType(clang_type); Value::ValueType value_type = m_value.GetValueType(); - + + Process *process = exe_ctx.GetProcessPtr(); + const bool process_is_alive = process && process->IsAlive(); + const uint32_t type_info = clang_type.GetTypeInfo(); + const bool is_pointer_or_ref = (type_info & (lldb::eTypeIsPointer | lldb::eTypeIsReference)) != 0; + switch (value_type) { case Value::eValueTypeFileAddress: - SetAddressTypeOfChildren(eAddressTypeFile); + // If this type is a pointer, then its children will be considered load addresses + // if the pointer or reference is dereferenced, but only if the process is alive. + // + // There could be global variables like in the following code: + // struct LinkedListNode { Foo* foo; LinkedListNode* next; }; + // Foo g_foo1; + // Foo g_foo2; + // LinkedListNode g_second_node = { &g_foo2, NULL }; + // LinkedListNode g_first_node = { &g_foo1, &g_second_node }; + // + // When we aren't running, we should be able to look at these variables using + // the "target variable" command. Children of the "g_first_node" always will + // be of the same address type as the parent. But children of the "next" member of + // LinkedListNode will become load addresses if we have a live process, or remain + // what a file address if it what a file address. + if (process_is_alive && is_pointer_or_ref) + SetAddressTypeOfChildren(eAddressTypeLoad); + else + SetAddressTypeOfChildren(eAddressTypeFile); break; case Value::eValueTypeHostAddress: - SetAddressTypeOfChildren(eAddressTypeHost); + // Same as above for load addresses, except children of pointer or refs are always + // load addresses. Host addresses are used to store freeze dried variables. If this + // type is a struct, the entire struct contents will be copied into the heap of the + // LLDB process, but we do not currrently follow any pointers. + if (is_pointer_or_ref) + SetAddressTypeOfChildren(eAddressTypeLoad); + else + SetAddressTypeOfChildren(eAddressTypeHost); break; case Value::eValueTypeLoadAddress: case Value::eValueTypeScalar: @@ -209,8 +239,7 @@ ValueObjectVariable::UpdateValue () // Make sure this type has a value before we try and read it // If we have a file address, convert it to a load address if we can. - Process *process = exe_ctx.GetProcessPtr(); - if (value_type == Value::eValueTypeFileAddress && process && process->IsAlive()) + 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) @@ -234,7 +263,7 @@ ValueObjectVariable::UpdateValue () } } - if (GetClangType().IsAggregateType()) + if (!CanProvideValue()) { // this value object represents an aggregate type whose // children have values, but this object does not. So we @@ -248,6 +277,8 @@ ValueObjectVariable::UpdateValue () Value value(m_value); value.SetContext(Value::eContextTypeVariable, variable); m_error = value.GetValueAsData(&exe_ctx, m_data, 0, GetModule().get()); + + SetValueDidChange (value_type != old_value.GetValueType() || m_value.GetScalar() != old_value.GetScalar()); } break; } |