ValueObject.cpp revision ef1923d722126810ef879edb959eed8c85a0742f
1//===-- ValueObject.cpp -----------------------------------------*- C++ -*-===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9 10#include "lldb/Core/ValueObject.h" 11 12// C Includes 13#include <stdlib.h> 14 15// C++ Includes 16// Other libraries and framework includes 17#include "llvm/Support/raw_ostream.h" 18#include "clang/AST/Type.h" 19 20// Project includes 21#include "lldb/Core/DataBufferHeap.h" 22#include "lldb/Core/DataVisualization.h" 23#include "lldb/Core/Debugger.h" 24#include "lldb/Core/Log.h" 25#include "lldb/Core/StreamString.h" 26#include "lldb/Core/ValueObjectChild.h" 27#include "lldb/Core/ValueObjectConstResult.h" 28#include "lldb/Core/ValueObjectDynamicValue.h" 29#include "lldb/Core/ValueObjectList.h" 30#include "lldb/Core/ValueObjectMemory.h" 31#include "lldb/Core/ValueObjectSyntheticFilter.h" 32 33#include "lldb/Host/Endian.h" 34 35#include "lldb/Interpreter/CommandInterpreter.h" 36#include "lldb/Interpreter/ScriptInterpreterPython.h" 37 38#include "lldb/Symbol/ClangASTType.h" 39#include "lldb/Symbol/ClangASTContext.h" 40#include "lldb/Symbol/Type.h" 41 42#include "lldb/Target/ExecutionContext.h" 43#include "lldb/Target/LanguageRuntime.h" 44#include "lldb/Target/ObjCLanguageRuntime.h" 45#include "lldb/Target/Process.h" 46#include "lldb/Target/RegisterContext.h" 47#include "lldb/Target/Target.h" 48#include "lldb/Target/Thread.h" 49 50#include "lldb/Utility/RefCounter.h" 51 52using namespace lldb; 53using namespace lldb_private; 54using namespace lldb_utility; 55 56static lldb::user_id_t g_value_obj_uid = 0; 57 58//---------------------------------------------------------------------- 59// ValueObject constructor 60//---------------------------------------------------------------------- 61ValueObject::ValueObject (ValueObject &parent) : 62 UserID (++g_value_obj_uid), // Unique identifier for every value object 63 m_parent (&parent), 64 m_update_point (parent.GetUpdatePoint ()), 65 m_name (), 66 m_data (), 67 m_value (), 68 m_error (), 69 m_value_str (), 70 m_old_value_str (), 71 m_location_str (), 72 m_summary_str (), 73 m_object_desc_str (), 74 m_manager(parent.GetManager()), 75 m_children (), 76 m_synthetic_children (), 77 m_dynamic_value (NULL), 78 m_synthetic_value(NULL), 79 m_deref_valobj(NULL), 80 m_format (eFormatDefault), 81 m_last_format_mgr_revision(0), 82 m_last_format_mgr_dynamic(parent.m_last_format_mgr_dynamic), 83 m_last_summary_format(), 84 m_forced_summary_format(), 85 m_last_value_format(), 86 m_last_synthetic_filter(), 87 m_user_id_of_forced_summary(), 88 m_value_is_valid (false), 89 m_value_did_change (false), 90 m_children_count_valid (false), 91 m_old_value_valid (false), 92 m_pointers_point_to_load_addrs (false), 93 m_is_deref_of_parent (false), 94 m_is_array_item_for_pointer(false), 95 m_is_bitfield_for_scalar(false), 96 m_is_expression_path_child(false), 97 m_is_child_at_offset(false), 98 m_is_expression_result(parent.m_is_expression_result), 99 m_dump_printable_counter(0) 100{ 101 m_manager->ManageObject(this); 102} 103 104//---------------------------------------------------------------------- 105// ValueObject constructor 106//---------------------------------------------------------------------- 107ValueObject::ValueObject (ExecutionContextScope *exe_scope) : 108 UserID (++g_value_obj_uid), // Unique identifier for every value object 109 m_parent (NULL), 110 m_update_point (exe_scope), 111 m_name (), 112 m_data (), 113 m_value (), 114 m_error (), 115 m_value_str (), 116 m_old_value_str (), 117 m_location_str (), 118 m_summary_str (), 119 m_object_desc_str (), 120 m_manager(), 121 m_children (), 122 m_synthetic_children (), 123 m_dynamic_value (NULL), 124 m_synthetic_value(NULL), 125 m_deref_valobj(NULL), 126 m_format (eFormatDefault), 127 m_last_format_mgr_revision(0), 128 m_last_format_mgr_dynamic(lldb::eNoDynamicValues), 129 m_last_summary_format(), 130 m_forced_summary_format(), 131 m_last_value_format(), 132 m_last_synthetic_filter(), 133 m_user_id_of_forced_summary(), 134 m_value_is_valid (false), 135 m_value_did_change (false), 136 m_children_count_valid (false), 137 m_old_value_valid (false), 138 m_pointers_point_to_load_addrs (false), 139 m_is_deref_of_parent (false), 140 m_is_array_item_for_pointer(false), 141 m_is_bitfield_for_scalar(false), 142 m_is_expression_path_child(false), 143 m_is_child_at_offset(false), 144 m_is_expression_result(false), 145 m_dump_printable_counter(0) 146{ 147 m_manager = new ValueObjectManager(); 148 m_manager->ManageObject (this); 149} 150 151//---------------------------------------------------------------------- 152// Destructor 153//---------------------------------------------------------------------- 154ValueObject::~ValueObject () 155{ 156} 157 158bool 159ValueObject::UpdateValueIfNeeded (bool update_format) 160{ 161 return UpdateValueIfNeeded(m_last_format_mgr_dynamic, update_format); 162} 163 164bool 165ValueObject::UpdateValueIfNeeded (lldb::DynamicValueType use_dynamic, bool update_format) 166{ 167 168 if (update_format) 169 UpdateFormatsIfNeeded(use_dynamic); 170 171 // If this is a constant value, then our success is predicated on whether 172 // we have an error or not 173 if (GetIsConstant()) 174 return m_error.Success(); 175 176 bool first_update = m_update_point.IsFirstEvaluation(); 177 178 if (m_update_point.NeedsUpdating()) 179 { 180 m_update_point.SetUpdated(); 181 182 // Save the old value using swap to avoid a string copy which 183 // also will clear our m_value_str 184 if (m_value_str.empty()) 185 { 186 m_old_value_valid = false; 187 } 188 else 189 { 190 m_old_value_valid = true; 191 m_old_value_str.swap (m_value_str); 192 m_value_str.clear(); 193 } 194 195 ClearUserVisibleData(); 196 197 const bool value_was_valid = GetValueIsValid(); 198 SetValueDidChange (false); 199 200 m_error.Clear(); 201 202 // Call the pure virtual function to update the value 203 bool success = UpdateValue (); 204 205 SetValueIsValid (success); 206 207 if (first_update) 208 SetValueDidChange (false); 209 else if (!m_value_did_change && success == false) 210 { 211 // The value wasn't gotten successfully, so we mark this 212 // as changed if the value used to be valid and now isn't 213 SetValueDidChange (value_was_valid); 214 } 215 } 216 return m_error.Success(); 217} 218 219void 220ValueObject::UpdateFormatsIfNeeded(lldb::DynamicValueType use_dynamic) 221{ 222 LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_TYPES)); 223 if (log) 224 log->Printf("checking for FormatManager revisions. VO named %s is at revision %d, while the format manager is at revision %d", 225 GetName().GetCString(), 226 m_last_format_mgr_revision, 227 DataVisualization::GetCurrentRevision()); 228 if (HasCustomSummaryFormat() && m_update_point.GetModID() != m_user_id_of_forced_summary) 229 { 230 ClearCustomSummaryFormat(); 231 m_summary_str.clear(); 232 } 233 if ( (m_last_format_mgr_revision != DataVisualization::GetCurrentRevision()) || 234 m_last_format_mgr_dynamic != use_dynamic) 235 { 236 if (m_last_summary_format.get()) 237 m_last_summary_format.reset((StringSummaryFormat*)NULL); 238 if (m_last_value_format.get()) 239 m_last_value_format.reset(/*(ValueFormat*)NULL*/); 240 if (m_last_synthetic_filter.get()) 241 m_last_synthetic_filter.reset(/*(SyntheticFilter*)NULL*/); 242 243 m_synthetic_value = NULL; 244 245 DataVisualization::ValueFormats::Get(*this, lldb::eNoDynamicValues, m_last_value_format); 246 DataVisualization::GetSummaryFormat(*this, use_dynamic, m_last_summary_format); 247 DataVisualization::GetSyntheticChildren(*this, use_dynamic, m_last_synthetic_filter); 248 249 m_last_format_mgr_revision = DataVisualization::GetCurrentRevision(); 250 m_last_format_mgr_dynamic = use_dynamic; 251 252 ClearUserVisibleData(); 253 } 254} 255 256void 257ValueObject::SetNeedsUpdate () 258{ 259 m_update_point.SetNeedsUpdate(); 260 // We have to clear the value string here so ConstResult children will notice if their values are 261 // changed by hand (i.e. with SetValueAsCString). 262 m_value_str.clear(); 263} 264 265DataExtractor & 266ValueObject::GetDataExtractor () 267{ 268 UpdateValueIfNeeded(false); 269 return m_data; 270} 271 272const Error & 273ValueObject::GetError() 274{ 275 UpdateValueIfNeeded(false); 276 return m_error; 277} 278 279const ConstString & 280ValueObject::GetName() const 281{ 282 return m_name; 283} 284 285const char * 286ValueObject::GetLocationAsCString () 287{ 288 if (UpdateValueIfNeeded(false)) 289 { 290 if (m_location_str.empty()) 291 { 292 StreamString sstr; 293 294 switch (m_value.GetValueType()) 295 { 296 default: 297 break; 298 299 case Value::eValueTypeScalar: 300 if (m_value.GetContextType() == Value::eContextTypeRegisterInfo) 301 { 302 RegisterInfo *reg_info = m_value.GetRegisterInfo(); 303 if (reg_info) 304 { 305 if (reg_info->name) 306 m_location_str = reg_info->name; 307 else if (reg_info->alt_name) 308 m_location_str = reg_info->alt_name; 309 break; 310 } 311 } 312 m_location_str = "scalar"; 313 break; 314 315 case Value::eValueTypeLoadAddress: 316 case Value::eValueTypeFileAddress: 317 case Value::eValueTypeHostAddress: 318 { 319 uint32_t addr_nibble_size = m_data.GetAddressByteSize() * 2; 320 sstr.Printf("0x%*.*llx", addr_nibble_size, addr_nibble_size, m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS)); 321 m_location_str.swap(sstr.GetString()); 322 } 323 break; 324 } 325 } 326 } 327 return m_location_str.c_str(); 328} 329 330Value & 331ValueObject::GetValue() 332{ 333 return m_value; 334} 335 336const Value & 337ValueObject::GetValue() const 338{ 339 return m_value; 340} 341 342bool 343ValueObject::ResolveValue (Scalar &scalar) 344{ 345 if (UpdateValueIfNeeded(false)) // make sure that you are up to date before returning anything 346 { 347 ExecutionContext exe_ctx; 348 ExecutionContextScope *exe_scope = GetExecutionContextScope(); 349 if (exe_scope) 350 exe_scope->CalculateExecutionContext(exe_ctx); 351 Value tmp_value(m_value); 352 scalar = tmp_value.ResolveValue(&exe_ctx, GetClangAST ()); 353 return scalar.IsValid(); 354 } 355 else 356 return false; 357} 358 359bool 360ValueObject::GetValueIsValid () const 361{ 362 return m_value_is_valid; 363} 364 365 366void 367ValueObject::SetValueIsValid (bool b) 368{ 369 m_value_is_valid = b; 370} 371 372bool 373ValueObject::GetValueDidChange () 374{ 375 GetValueAsCString (); 376 return m_value_did_change; 377} 378 379void 380ValueObject::SetValueDidChange (bool value_changed) 381{ 382 m_value_did_change = value_changed; 383} 384 385ValueObjectSP 386ValueObject::GetChildAtIndex (uint32_t idx, bool can_create) 387{ 388 ValueObjectSP child_sp; 389 // We may need to update our value if we are dynamic 390 if (IsPossibleDynamicType ()) 391 UpdateValueIfNeeded(false); 392 if (idx < GetNumChildren()) 393 { 394 // Check if we have already made the child value object? 395 if (can_create && m_children[idx] == NULL) 396 { 397 // No we haven't created the child at this index, so lets have our 398 // subclass do it and cache the result for quick future access. 399 m_children[idx] = CreateChildAtIndex (idx, false, 0); 400 } 401 402 if (m_children[idx] != NULL) 403 return m_children[idx]->GetSP(); 404 } 405 return child_sp; 406} 407 408uint32_t 409ValueObject::GetIndexOfChildWithName (const ConstString &name) 410{ 411 bool omit_empty_base_classes = true; 412 return ClangASTContext::GetIndexOfChildWithName (GetClangAST(), 413 GetClangType(), 414 name.GetCString(), 415 omit_empty_base_classes); 416} 417 418ValueObjectSP 419ValueObject::GetChildMemberWithName (const ConstString &name, bool can_create) 420{ 421 // when getting a child by name, it could be buried inside some base 422 // classes (which really aren't part of the expression path), so we 423 // need a vector of indexes that can get us down to the correct child 424 ValueObjectSP child_sp; 425 426 // We may need to update our value if we are dynamic 427 if (IsPossibleDynamicType ()) 428 UpdateValueIfNeeded(false); 429 430 std::vector<uint32_t> child_indexes; 431 clang::ASTContext *clang_ast = GetClangAST(); 432 void *clang_type = GetClangType(); 433 bool omit_empty_base_classes = true; 434 const size_t num_child_indexes = ClangASTContext::GetIndexOfChildMemberWithName (clang_ast, 435 clang_type, 436 name.GetCString(), 437 omit_empty_base_classes, 438 child_indexes); 439 if (num_child_indexes > 0) 440 { 441 std::vector<uint32_t>::const_iterator pos = child_indexes.begin (); 442 std::vector<uint32_t>::const_iterator end = child_indexes.end (); 443 444 child_sp = GetChildAtIndex(*pos, can_create); 445 for (++pos; pos != end; ++pos) 446 { 447 if (child_sp) 448 { 449 ValueObjectSP new_child_sp(child_sp->GetChildAtIndex (*pos, can_create)); 450 child_sp = new_child_sp; 451 } 452 else 453 { 454 child_sp.reset(); 455 } 456 457 } 458 } 459 return child_sp; 460} 461 462 463uint32_t 464ValueObject::GetNumChildren () 465{ 466 if (!m_children_count_valid) 467 { 468 SetNumChildren (CalculateNumChildren()); 469 } 470 return m_children.size(); 471} 472void 473ValueObject::SetNumChildren (uint32_t num_children) 474{ 475 m_children_count_valid = true; 476 m_children.resize(num_children); 477} 478 479void 480ValueObject::SetName (const ConstString &name) 481{ 482 m_name = name; 483} 484 485ValueObject * 486ValueObject::CreateChildAtIndex (uint32_t idx, bool synthetic_array_member, int32_t synthetic_index) 487{ 488 ValueObject *valobj = NULL; 489 490 bool omit_empty_base_classes = true; 491 bool ignore_array_bounds = synthetic_array_member; 492 std::string child_name_str; 493 uint32_t child_byte_size = 0; 494 int32_t child_byte_offset = 0; 495 uint32_t child_bitfield_bit_size = 0; 496 uint32_t child_bitfield_bit_offset = 0; 497 bool child_is_base_class = false; 498 bool child_is_deref_of_parent = false; 499 500 const bool transparent_pointers = synthetic_array_member == false; 501 clang::ASTContext *clang_ast = GetClangAST(); 502 clang_type_t clang_type = GetClangType(); 503 clang_type_t child_clang_type; 504 505 ExecutionContext exe_ctx; 506 GetExecutionContextScope()->CalculateExecutionContext (exe_ctx); 507 508 child_clang_type = ClangASTContext::GetChildClangTypeAtIndex (&exe_ctx, 509 clang_ast, 510 GetName().GetCString(), 511 clang_type, 512 idx, 513 transparent_pointers, 514 omit_empty_base_classes, 515 ignore_array_bounds, 516 child_name_str, 517 child_byte_size, 518 child_byte_offset, 519 child_bitfield_bit_size, 520 child_bitfield_bit_offset, 521 child_is_base_class, 522 child_is_deref_of_parent); 523 if (child_clang_type && child_byte_size) 524 { 525 if (synthetic_index) 526 child_byte_offset += child_byte_size * synthetic_index; 527 528 ConstString child_name; 529 if (!child_name_str.empty()) 530 child_name.SetCString (child_name_str.c_str()); 531 532 valobj = new ValueObjectChild (*this, 533 clang_ast, 534 child_clang_type, 535 child_name, 536 child_byte_size, 537 child_byte_offset, 538 child_bitfield_bit_size, 539 child_bitfield_bit_offset, 540 child_is_base_class, 541 child_is_deref_of_parent); 542 if (m_pointers_point_to_load_addrs) 543 valobj->SetPointersPointToLoadAddrs (m_pointers_point_to_load_addrs); 544 } 545 546 return valobj; 547} 548 549const char * 550ValueObject::GetSummaryAsCString () 551{ 552 if (UpdateValueIfNeeded (true)) 553 { 554 if (m_summary_str.empty()) 555 { 556 SummaryFormat *summary_format = GetSummaryFormat().get(); 557 558 if (summary_format) 559 { 560 m_summary_str = summary_format->FormatObject(GetSP()); 561 } 562 else 563 { 564 clang_type_t clang_type = GetClangType(); 565 566 // Do some default printout for function pointers 567 if (clang_type) 568 { 569 StreamString sstr; 570 clang_type_t elem_or_pointee_clang_type; 571 const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, 572 GetClangAST(), 573 &elem_or_pointee_clang_type)); 574 575 ExecutionContextScope *exe_scope = GetExecutionContextScope(); 576 if (exe_scope) 577 { 578 if (ClangASTContext::IsFunctionPointerType (clang_type)) 579 { 580 AddressType func_ptr_address_type = eAddressTypeInvalid; 581 lldb::addr_t func_ptr_address = GetPointerValue (func_ptr_address_type, true); 582 583 if (func_ptr_address != 0 && func_ptr_address != LLDB_INVALID_ADDRESS) 584 { 585 switch (func_ptr_address_type) 586 { 587 case eAddressTypeInvalid: 588 case eAddressTypeFile: 589 break; 590 591 case eAddressTypeLoad: 592 { 593 Address so_addr; 594 Target *target = exe_scope->CalculateTarget(); 595 if (target && target->GetSectionLoadList().IsEmpty() == false) 596 { 597 if (target->GetSectionLoadList().ResolveLoadAddress(func_ptr_address, so_addr)) 598 { 599 so_addr.Dump (&sstr, 600 exe_scope, 601 Address::DumpStyleResolvedDescription, 602 Address::DumpStyleSectionNameOffset); 603 } 604 } 605 } 606 break; 607 608 case eAddressTypeHost: 609 break; 610 } 611 } 612 if (sstr.GetSize() > 0) 613 { 614 m_summary_str.assign (1, '('); 615 m_summary_str.append (sstr.GetData(), sstr.GetSize()); 616 m_summary_str.append (1, ')'); 617 } 618 } 619 } 620 } 621 } 622 } 623 } 624 if (m_summary_str.empty()) 625 return NULL; 626 return m_summary_str.c_str(); 627} 628 629bool 630ValueObject::IsCStringContainer(bool check_pointer) 631{ 632 clang_type_t elem_or_pointee_clang_type; 633 const Flags type_flags (ClangASTContext::GetTypeInfo (GetClangType(), 634 GetClangAST(), 635 &elem_or_pointee_clang_type)); 636 bool is_char_arr_ptr (type_flags.AnySet (ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) && 637 ClangASTContext::IsCharType (elem_or_pointee_clang_type)); 638 if (!is_char_arr_ptr) 639 return false; 640 if (!check_pointer) 641 return true; 642 if (type_flags.Test(ClangASTContext::eTypeIsArray)) 643 return true; 644 lldb::addr_t cstr_address = LLDB_INVALID_ADDRESS; 645 AddressType cstr_address_type = eAddressTypeInvalid; 646 cstr_address = GetAddressOf (cstr_address_type, true); 647 return (cstr_address != LLDB_INVALID_ADDRESS); 648} 649 650void 651ValueObject::ReadPointedString(Stream& s, 652 Error& error, 653 uint32_t max_length, 654 bool honor_array, 655 lldb::Format item_format) 656{ 657 658 if (max_length == 0) 659 max_length = 128; // FIXME this should be a setting, or a formatting parameter 660 661 clang_type_t clang_type = GetClangType(); 662 clang_type_t elem_or_pointee_clang_type; 663 const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, 664 GetClangAST(), 665 &elem_or_pointee_clang_type)); 666 if (type_flags.AnySet (ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) && 667 ClangASTContext::IsCharType (elem_or_pointee_clang_type)) 668 { 669 ExecutionContextScope *exe_scope = GetExecutionContextScope(); 670 if (exe_scope) 671 { 672 Target *target = exe_scope->CalculateTarget(); 673 if (target == NULL) 674 { 675 s << "<no target to read from>"; 676 } 677 else 678 { 679 lldb::addr_t cstr_address = LLDB_INVALID_ADDRESS; 680 AddressType cstr_address_type = eAddressTypeInvalid; 681 682 size_t cstr_len = 0; 683 bool capped_data = false; 684 if (type_flags.Test (ClangASTContext::eTypeIsArray)) 685 { 686 // We have an array 687 cstr_len = ClangASTContext::GetArraySize (clang_type); 688 if (cstr_len > max_length) 689 { 690 capped_data = true; 691 cstr_len = max_length; 692 } 693 cstr_address = GetAddressOf (cstr_address_type, true); 694 } 695 else 696 { 697 // We have a pointer 698 cstr_address = GetPointerValue (cstr_address_type, true); 699 } 700 if (cstr_address == LLDB_INVALID_ADDRESS) 701 { 702 s << "<invalid address for data>"; 703 } 704 else 705 { 706 Address cstr_so_addr (NULL, cstr_address); 707 DataExtractor data; 708 size_t bytes_read = 0; 709 std::vector<char> data_buffer; 710 bool prefer_file_cache = false; 711 if (cstr_len > 0 && honor_array) 712 { 713 data_buffer.resize(cstr_len); 714 data.SetData (&data_buffer.front(), data_buffer.size(), lldb::endian::InlHostByteOrder()); 715 bytes_read = target->ReadMemory (cstr_so_addr, 716 prefer_file_cache, 717 &data_buffer.front(), 718 cstr_len, 719 error); 720 if (bytes_read > 0) 721 { 722 s << '"'; 723 data.Dump (&s, 724 0, // Start offset in "data" 725 item_format, 726 1, // Size of item (1 byte for a char!) 727 bytes_read, // How many bytes to print? 728 UINT32_MAX, // num per line 729 LLDB_INVALID_ADDRESS,// base address 730 0, // bitfield bit size 731 0); // bitfield bit offset 732 if (capped_data) 733 s << "..."; 734 s << '"'; 735 } 736 else 737 s << "\"<data not available>\""; 738 } 739 else 740 { 741 cstr_len = max_length; 742 const size_t k_max_buf_size = 64; 743 data_buffer.resize (k_max_buf_size + 1); 744 // NULL terminate in case we don't get the entire C string 745 data_buffer.back() = '\0'; 746 747 s << '"'; 748 749 bool any_data = false; 750 751 data.SetData (&data_buffer.front(), data_buffer.size(), endian::InlHostByteOrder()); 752 while ((bytes_read = target->ReadMemory (cstr_so_addr, 753 prefer_file_cache, 754 &data_buffer.front(), 755 k_max_buf_size, 756 error)) > 0) 757 { 758 any_data = true; 759 size_t len = strlen(&data_buffer.front()); 760 if (len == 0) 761 break; 762 if (len > bytes_read) 763 len = bytes_read; 764 if (len > cstr_len) 765 len = cstr_len; 766 767 data.Dump (&s, 768 0, // Start offset in "data" 769 item_format, 770 1, // Size of item (1 byte for a char!) 771 len, // How many bytes to print? 772 UINT32_MAX, // num per line 773 LLDB_INVALID_ADDRESS,// base address 774 0, // bitfield bit size 775 0); // bitfield bit offset 776 777 if (len < k_max_buf_size) 778 break; 779 if (len >= cstr_len) 780 { 781 s << "..."; 782 break; 783 } 784 cstr_len -= len; 785 cstr_so_addr.Slide (k_max_buf_size); 786 } 787 788 if (any_data == false) 789 s << "<data not available>"; 790 791 s << '"'; 792 } 793 } 794 } 795 } 796 } 797 else 798 { 799 error.SetErrorString("impossible to read a string from this object"); 800 s << "<not a string object>"; 801 } 802} 803 804const char * 805ValueObject::GetObjectDescription () 806{ 807 808 if (!UpdateValueIfNeeded (true)) 809 return NULL; 810 811 if (!m_object_desc_str.empty()) 812 return m_object_desc_str.c_str(); 813 814 ExecutionContextScope *exe_scope = GetExecutionContextScope(); 815 if (exe_scope == NULL) 816 return NULL; 817 818 Process *process = exe_scope->CalculateProcess(); 819 if (process == NULL) 820 return NULL; 821 822 StreamString s; 823 824 lldb::LanguageType language = GetObjectRuntimeLanguage(); 825 LanguageRuntime *runtime = process->GetLanguageRuntime(language); 826 827 if (runtime == NULL) 828 { 829 // Aw, hell, if the things a pointer, or even just an integer, let's try ObjC anyway... 830 clang_type_t opaque_qual_type = GetClangType(); 831 if (opaque_qual_type != NULL) 832 { 833 bool is_signed; 834 if (ClangASTContext::IsIntegerType (opaque_qual_type, is_signed) 835 || ClangASTContext::IsPointerType (opaque_qual_type)) 836 { 837 runtime = process->GetLanguageRuntime(lldb::eLanguageTypeObjC); 838 } 839 } 840 } 841 842 if (runtime && runtime->GetObjectDescription(s, *this)) 843 { 844 m_object_desc_str.append (s.GetData()); 845 } 846 847 if (m_object_desc_str.empty()) 848 return NULL; 849 else 850 return m_object_desc_str.c_str(); 851} 852 853const char * 854ValueObject::GetValueAsCString () 855{ 856 // If our byte size is zero this is an aggregate type that has children 857 if (ClangASTContext::IsAggregateType (GetClangType()) == false) 858 { 859 if (UpdateValueIfNeeded(true)) 860 { 861 if (m_value_str.empty()) 862 { 863 const Value::ContextType context_type = m_value.GetContextType(); 864 865 switch (context_type) 866 { 867 case Value::eContextTypeClangType: 868 case Value::eContextTypeLLDBType: 869 case Value::eContextTypeVariable: 870 { 871 clang_type_t clang_type = GetClangType (); 872 if (clang_type) 873 { 874 if (m_format == lldb::eFormatDefault && m_last_value_format) 875 { 876 m_value_str = m_last_value_format->FormatObject(GetSP()); 877 } 878 else 879 { 880 StreamString sstr; 881 Format format = GetFormat(); 882 if (format == eFormatDefault) 883 format = (m_is_bitfield_for_scalar ? eFormatUnsigned : 884 ClangASTType::GetFormat(clang_type)); 885 886 if (ClangASTType::DumpTypeValue (GetClangAST(), // The clang AST 887 clang_type, // The clang type to display 888 &sstr, 889 format, // Format to display this type with 890 m_data, // Data to extract from 891 0, // Byte offset into "m_data" 892 GetByteSize(), // Byte size of item in "m_data" 893 GetBitfieldBitSize(), // Bitfield bit size 894 GetBitfieldBitOffset())) // Bitfield bit offset 895 m_value_str.swap(sstr.GetString()); 896 else 897 { 898 m_error.SetErrorStringWithFormat ("unsufficient data for value (only %u of %u bytes available)", 899 m_data.GetByteSize(), 900 GetByteSize()); 901 m_value_str.clear(); 902 } 903 } 904 } 905 } 906 break; 907 908 case Value::eContextTypeRegisterInfo: 909 { 910 const RegisterInfo *reg_info = m_value.GetRegisterInfo(); 911 if (reg_info) 912 { 913 StreamString reg_sstr; 914 m_data.Dump(®_sstr, 0, reg_info->format, reg_info->byte_size, 1, UINT32_MAX, LLDB_INVALID_ADDRESS, 0, 0); 915 m_value_str.swap(reg_sstr.GetString()); 916 } 917 } 918 break; 919 920 default: 921 break; 922 } 923 } 924 925 if (!m_value_did_change && m_old_value_valid) 926 { 927 // The value was gotten successfully, so we consider the 928 // value as changed if the value string differs 929 SetValueDidChange (m_old_value_str != m_value_str); 930 } 931 } 932 } 933 if (m_value_str.empty()) 934 return NULL; 935 return m_value_str.c_str(); 936} 937 938// if > 8bytes, 0 is returned. this method should mostly be used 939// to read address values out of pointers 940uint64_t 941ValueObject::GetValueAsUnsigned (uint64_t fail_value) 942{ 943 // If our byte size is zero this is an aggregate type that has children 944 if (ClangASTContext::IsAggregateType (GetClangType()) == false) 945 { 946 Scalar scalar; 947 if (ResolveValue (scalar)) 948 return scalar.GetRawBits64(fail_value); 949 } 950 return fail_value; 951} 952 953bool 954ValueObject::GetPrintableRepresentation(Stream& s, 955 ValueObjectRepresentationStyle val_obj_display, 956 lldb::Format custom_format) 957{ 958 959 RefCounter ref(&m_dump_printable_counter); 960 961 if (custom_format != lldb::eFormatInvalid) 962 SetFormat(custom_format); 963 964 const char * return_value; 965 std::string alloc_mem; 966 967 switch(val_obj_display) 968 { 969 case eDisplayValue: 970 return_value = GetValueAsCString(); 971 break; 972 case eDisplaySummary: 973 return_value = GetSummaryAsCString(); 974 break; 975 case eDisplayLanguageSpecific: 976 return_value = GetObjectDescription(); 977 break; 978 case eDisplayLocation: 979 return_value = GetLocationAsCString(); 980 break; 981 case eDisplayChildrenCount: 982 { 983 alloc_mem.resize(512); 984 return_value = &alloc_mem[0]; 985 int count = GetNumChildren(); 986 snprintf((char*)return_value, 512, "%d", count); 987 break; 988 } 989 case eDisplayType: 990 return_value = GetTypeName().AsCString(); 991 break; 992 default: 993 break; 994 } 995 996 // this code snippet might lead to endless recursion, thus we use a RefCounter here to 997 // check that we are not looping endlessly 998 if (!return_value && (m_dump_printable_counter < 3)) 999 { 1000 // try to pick the other choice 1001 if (val_obj_display == eDisplayValue) 1002 return_value = GetSummaryAsCString(); 1003 else if (val_obj_display == eDisplaySummary) 1004 { 1005 if (ClangASTContext::IsAggregateType (GetClangType()) == true) 1006 { 1007 // this thing has no value, and it seems to have no summary 1008 // some combination of unitialized data and other factors can also 1009 // raise this condition, so let's print a nice generic error message 1010 { 1011 alloc_mem.resize(684); 1012 return_value = &alloc_mem[0]; 1013 snprintf((char*)return_value, 684, "%s @ %s", GetTypeName().AsCString(), GetLocationAsCString()); 1014 } 1015 } 1016 else 1017 return_value = GetValueAsCString(); 1018 } 1019 } 1020 1021 if (return_value) 1022 s.PutCString(return_value); 1023 else 1024 { 1025 if (m_error.Fail()) 1026 s.Printf("<%s>", m_error.AsCString()); 1027 else if (val_obj_display == eDisplaySummary) 1028 s.PutCString("<no summary available>"); 1029 else if (val_obj_display == eDisplayValue) 1030 s.PutCString("<no value available>"); 1031 else if (val_obj_display == eDisplayLanguageSpecific) 1032 s.PutCString("<not a valid Objective-C object>"); // edit this if we have other runtimes that support a description 1033 else 1034 s.PutCString("<no printable representation>"); 1035 } 1036 1037 // we should only return false here if we could not do *anything* 1038 // even if we have an error message as output, that's a success 1039 // from our callers' perspective, so return true 1040 return true; 1041 1042} 1043 1044// if any more "special cases" are added to ValueObject::DumpPrintableRepresentation() please keep 1045// this call up to date by returning true for your new special cases. We will eventually move 1046// to checking this call result before trying to display special cases 1047bool 1048ValueObject::HasSpecialCasesForPrintableRepresentation(ValueObjectRepresentationStyle val_obj_display, 1049 lldb::Format custom_format) 1050{ 1051 clang_type_t elem_or_pointee_type; 1052 Flags flags(ClangASTContext::GetTypeInfo(GetClangType(), GetClangAST(), &elem_or_pointee_type)); 1053 1054 if (flags.AnySet(ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) 1055 && val_obj_display == ValueObject::eDisplayValue) 1056 { 1057 if (IsCStringContainer(true) && 1058 (custom_format == lldb::eFormatCString || 1059 custom_format == lldb::eFormatCharArray || 1060 custom_format == lldb::eFormatChar || 1061 custom_format == lldb::eFormatVectorOfChar)) 1062 return true; 1063 1064 if (flags.Test(ClangASTContext::eTypeIsArray)) 1065 { 1066 if ((custom_format == lldb::eFormatBytes) || 1067 (custom_format == lldb::eFormatBytesWithASCII)) 1068 return true; 1069 1070 if ((custom_format == lldb::eFormatVectorOfChar) || 1071 (custom_format == lldb::eFormatVectorOfFloat32) || 1072 (custom_format == lldb::eFormatVectorOfFloat64) || 1073 (custom_format == lldb::eFormatVectorOfSInt16) || 1074 (custom_format == lldb::eFormatVectorOfSInt32) || 1075 (custom_format == lldb::eFormatVectorOfSInt64) || 1076 (custom_format == lldb::eFormatVectorOfSInt8) || 1077 (custom_format == lldb::eFormatVectorOfUInt128) || 1078 (custom_format == lldb::eFormatVectorOfUInt16) || 1079 (custom_format == lldb::eFormatVectorOfUInt32) || 1080 (custom_format == lldb::eFormatVectorOfUInt64) || 1081 (custom_format == lldb::eFormatVectorOfUInt8)) 1082 return true; 1083 } 1084 } 1085 return false; 1086} 1087 1088bool 1089ValueObject::DumpPrintableRepresentation(Stream& s, 1090 ValueObjectRepresentationStyle val_obj_display, 1091 lldb::Format custom_format, 1092 bool only_special) 1093{ 1094 1095 clang_type_t elem_or_pointee_type; 1096 Flags flags(ClangASTContext::GetTypeInfo(GetClangType(), GetClangAST(), &elem_or_pointee_type)); 1097 1098 if (flags.AnySet(ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) 1099 && val_obj_display == ValueObject::eDisplayValue) 1100 { 1101 // when being asked to get a printable display an array or pointer type directly, 1102 // try to "do the right thing" 1103 1104 if (IsCStringContainer(true) && 1105 (custom_format == lldb::eFormatCString || 1106 custom_format == lldb::eFormatCharArray || 1107 custom_format == lldb::eFormatChar || 1108 custom_format == lldb::eFormatVectorOfChar)) // print char[] & char* directly 1109 { 1110 Error error; 1111 ReadPointedString(s, 1112 error, 1113 0, 1114 (custom_format == lldb::eFormatVectorOfChar) || 1115 (custom_format == lldb::eFormatCharArray)); 1116 return !error.Fail(); 1117 } 1118 1119 if (custom_format == lldb::eFormatEnum) 1120 return false; 1121 1122 // this only works for arrays, because I have no way to know when 1123 // the pointed memory ends, and no special \0 end of data marker 1124 if (flags.Test(ClangASTContext::eTypeIsArray)) 1125 { 1126 if ((custom_format == lldb::eFormatBytes) || 1127 (custom_format == lldb::eFormatBytesWithASCII)) 1128 { 1129 uint32_t count = GetNumChildren(); 1130 1131 s << '['; 1132 for (uint32_t low = 0; low < count; low++) 1133 { 1134 1135 if (low) 1136 s << ','; 1137 1138 ValueObjectSP child = GetChildAtIndex(low,true); 1139 if (!child.get()) 1140 { 1141 s << "<invalid child>"; 1142 continue; 1143 } 1144 child->DumpPrintableRepresentation(s, ValueObject::eDisplayValue, custom_format); 1145 } 1146 1147 s << ']'; 1148 1149 return true; 1150 } 1151 1152 if ((custom_format == lldb::eFormatVectorOfChar) || 1153 (custom_format == lldb::eFormatVectorOfFloat32) || 1154 (custom_format == lldb::eFormatVectorOfFloat64) || 1155 (custom_format == lldb::eFormatVectorOfSInt16) || 1156 (custom_format == lldb::eFormatVectorOfSInt32) || 1157 (custom_format == lldb::eFormatVectorOfSInt64) || 1158 (custom_format == lldb::eFormatVectorOfSInt8) || 1159 (custom_format == lldb::eFormatVectorOfUInt128) || 1160 (custom_format == lldb::eFormatVectorOfUInt16) || 1161 (custom_format == lldb::eFormatVectorOfUInt32) || 1162 (custom_format == lldb::eFormatVectorOfUInt64) || 1163 (custom_format == lldb::eFormatVectorOfUInt8)) // arrays of bytes, bytes with ASCII or any vector format should be printed directly 1164 { 1165 uint32_t count = GetNumChildren(); 1166 1167 lldb::Format format = FormatManager::GetSingleItemFormat(custom_format); 1168 1169 s << '['; 1170 for (uint32_t low = 0; low < count; low++) 1171 { 1172 1173 if (low) 1174 s << ','; 1175 1176 ValueObjectSP child = GetChildAtIndex(low,true); 1177 if (!child.get()) 1178 { 1179 s << "<invalid child>"; 1180 continue; 1181 } 1182 child->DumpPrintableRepresentation(s, ValueObject::eDisplayValue, format); 1183 } 1184 1185 s << ']'; 1186 1187 return true; 1188 } 1189 } 1190 1191 if ((custom_format == lldb::eFormatBoolean) || 1192 (custom_format == lldb::eFormatBinary) || 1193 (custom_format == lldb::eFormatChar) || 1194 (custom_format == lldb::eFormatCharPrintable) || 1195 (custom_format == lldb::eFormatComplexFloat) || 1196 (custom_format == lldb::eFormatDecimal) || 1197 (custom_format == lldb::eFormatHex) || 1198 (custom_format == lldb::eFormatFloat) || 1199 (custom_format == lldb::eFormatOctal) || 1200 (custom_format == lldb::eFormatOSType) || 1201 (custom_format == lldb::eFormatUnicode16) || 1202 (custom_format == lldb::eFormatUnicode32) || 1203 (custom_format == lldb::eFormatUnsigned) || 1204 (custom_format == lldb::eFormatPointer) || 1205 (custom_format == lldb::eFormatComplexInteger) || 1206 (custom_format == lldb::eFormatComplex) || 1207 (custom_format == lldb::eFormatDefault)) // use the [] operator 1208 return false; 1209 } 1210 1211 if (only_special) 1212 return false; 1213 1214 bool var_success = GetPrintableRepresentation(s, val_obj_display, custom_format); 1215 if (custom_format != eFormatInvalid) 1216 SetFormat(eFormatDefault); 1217 return var_success; 1218} 1219 1220addr_t 1221ValueObject::GetAddressOf (AddressType &address_type, bool scalar_is_load_address) 1222{ 1223 if (!UpdateValueIfNeeded(false)) 1224 return LLDB_INVALID_ADDRESS; 1225 1226 switch (m_value.GetValueType()) 1227 { 1228 case Value::eValueTypeScalar: 1229 if (scalar_is_load_address) 1230 { 1231 address_type = eAddressTypeLoad; 1232 return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 1233 } 1234 break; 1235 1236 case Value::eValueTypeLoadAddress: 1237 case Value::eValueTypeFileAddress: 1238 case Value::eValueTypeHostAddress: 1239 { 1240 address_type = m_value.GetValueAddressType (); 1241 return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 1242 } 1243 break; 1244 } 1245 address_type = eAddressTypeInvalid; 1246 return LLDB_INVALID_ADDRESS; 1247} 1248 1249addr_t 1250ValueObject::GetPointerValue (AddressType &address_type, bool scalar_is_load_address) 1251{ 1252 lldb::addr_t address = LLDB_INVALID_ADDRESS; 1253 address_type = eAddressTypeInvalid; 1254 1255 if (!UpdateValueIfNeeded(false)) 1256 return address; 1257 1258 switch (m_value.GetValueType()) 1259 { 1260 case Value::eValueTypeScalar: 1261 if (scalar_is_load_address) 1262 { 1263 address = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS); 1264 address_type = eAddressTypeLoad; 1265 } 1266 break; 1267 1268 case Value::eValueTypeLoadAddress: 1269 case Value::eValueTypeFileAddress: 1270 case Value::eValueTypeHostAddress: 1271 { 1272 uint32_t data_offset = 0; 1273 address = m_data.GetPointer(&data_offset); 1274 address_type = m_value.GetValueAddressType(); 1275 if (address_type == eAddressTypeInvalid) 1276 address_type = eAddressTypeLoad; 1277 } 1278 break; 1279 } 1280 1281 if (m_pointers_point_to_load_addrs) 1282 address_type = eAddressTypeLoad; 1283 1284 return address; 1285} 1286 1287bool 1288ValueObject::SetValueFromCString (const char *value_str) 1289{ 1290 // Make sure our value is up to date first so that our location and location 1291 // type is valid. 1292 if (!UpdateValueIfNeeded(false)) 1293 return false; 1294 1295 uint32_t count = 0; 1296 lldb::Encoding encoding = ClangASTType::GetEncoding (GetClangType(), count); 1297 1298 const size_t byte_size = GetByteSize(); 1299 1300 Value::ValueType value_type = m_value.GetValueType(); 1301 1302 if (value_type == Value::eValueTypeScalar) 1303 { 1304 // If the value is already a scalar, then let the scalar change itself: 1305 m_value.GetScalar().SetValueFromCString (value_str, encoding, byte_size); 1306 } 1307 else if (byte_size <= Scalar::GetMaxByteSize()) 1308 { 1309 // If the value fits in a scalar, then make a new scalar and again let the 1310 // scalar code do the conversion, then figure out where to put the new value. 1311 Scalar new_scalar; 1312 Error error; 1313 error = new_scalar.SetValueFromCString (value_str, encoding, byte_size); 1314 if (error.Success()) 1315 { 1316 switch (value_type) 1317 { 1318 case Value::eValueTypeLoadAddress: 1319 { 1320 // If it is a load address, then the scalar value is the storage location 1321 // of the data, and we have to shove this value down to that load location. 1322 ProcessSP process_sp = GetUpdatePoint().GetProcessSP(); 1323 if (process_sp) 1324 { 1325 lldb::addr_t target_addr = m_value.GetScalar().GetRawBits64(LLDB_INVALID_ADDRESS); 1326 size_t bytes_written = process_sp->WriteScalarToMemory (target_addr, 1327 new_scalar, 1328 byte_size, 1329 error); 1330 if (!error.Success() || bytes_written != byte_size) 1331 return false; 1332 } 1333 } 1334 break; 1335 case Value::eValueTypeHostAddress: 1336 { 1337 // If it is a host address, then we stuff the scalar as a DataBuffer into the Value's data. 1338 DataExtractor new_data; 1339 new_data.SetByteOrder (m_data.GetByteOrder()); 1340 1341 DataBufferSP buffer_sp (new DataBufferHeap(byte_size, 0)); 1342 m_data.SetData(buffer_sp, 0); 1343 bool success = new_scalar.GetData(new_data); 1344 if (success) 1345 { 1346 new_data.CopyByteOrderedData(0, 1347 byte_size, 1348 const_cast<uint8_t *>(m_data.GetDataStart()), 1349 byte_size, 1350 m_data.GetByteOrder()); 1351 } 1352 m_value.GetScalar() = (uintptr_t)m_data.GetDataStart(); 1353 1354 } 1355 break; 1356 case Value::eValueTypeFileAddress: 1357 case Value::eValueTypeScalar: 1358 break; 1359 } 1360 } 1361 else 1362 { 1363 return false; 1364 } 1365 } 1366 else 1367 { 1368 // We don't support setting things bigger than a scalar at present. 1369 return false; 1370 } 1371 1372 // If we have reached this point, then we have successfully changed the value. 1373 SetNeedsUpdate(); 1374 return true; 1375} 1376 1377lldb::LanguageType 1378ValueObject::GetObjectRuntimeLanguage () 1379{ 1380 return ClangASTType::GetMinimumLanguage (GetClangAST(), 1381 GetClangType()); 1382} 1383 1384void 1385ValueObject::AddSyntheticChild (const ConstString &key, ValueObject *valobj) 1386{ 1387 m_synthetic_children[key] = valobj; 1388} 1389 1390ValueObjectSP 1391ValueObject::GetSyntheticChild (const ConstString &key) const 1392{ 1393 ValueObjectSP synthetic_child_sp; 1394 std::map<ConstString, ValueObject *>::const_iterator pos = m_synthetic_children.find (key); 1395 if (pos != m_synthetic_children.end()) 1396 synthetic_child_sp = pos->second->GetSP(); 1397 return synthetic_child_sp; 1398} 1399 1400bool 1401ValueObject::IsPointerType () 1402{ 1403 return ClangASTContext::IsPointerType (GetClangType()); 1404} 1405 1406bool 1407ValueObject::IsArrayType () 1408{ 1409 return ClangASTContext::IsArrayType (GetClangType()); 1410} 1411 1412bool 1413ValueObject::IsScalarType () 1414{ 1415 return ClangASTContext::IsScalarType (GetClangType()); 1416} 1417 1418bool 1419ValueObject::IsIntegerType (bool &is_signed) 1420{ 1421 return ClangASTContext::IsIntegerType (GetClangType(), is_signed); 1422} 1423 1424bool 1425ValueObject::IsPointerOrReferenceType () 1426{ 1427 return ClangASTContext::IsPointerOrReferenceType (GetClangType()); 1428} 1429 1430bool 1431ValueObject::IsPossibleCPlusPlusDynamicType () 1432{ 1433 return ClangASTContext::IsPossibleCPlusPlusDynamicType (GetClangAST (), GetClangType()); 1434} 1435 1436bool 1437ValueObject::IsPossibleDynamicType () 1438{ 1439 return ClangASTContext::IsPossibleDynamicType (GetClangAST (), GetClangType()); 1440} 1441 1442lldb::ValueObjectSP 1443ValueObject::GetSyntheticArrayMember (int32_t index, bool can_create) 1444{ 1445 if (IsArrayType()) 1446 return GetSyntheticArrayMemberFromArray(index, can_create); 1447 1448 if (IsPointerType()) 1449 return GetSyntheticArrayMemberFromPointer(index, can_create); 1450 1451 return ValueObjectSP(); 1452 1453} 1454 1455ValueObjectSP 1456ValueObject::GetSyntheticArrayMemberFromPointer (int32_t index, bool can_create) 1457{ 1458 ValueObjectSP synthetic_child_sp; 1459 if (IsPointerType ()) 1460 { 1461 char index_str[64]; 1462 snprintf(index_str, sizeof(index_str), "[%i]", index); 1463 ConstString index_const_str(index_str); 1464 // Check if we have already created a synthetic array member in this 1465 // valid object. If we have we will re-use it. 1466 synthetic_child_sp = GetSyntheticChild (index_const_str); 1467 if (!synthetic_child_sp) 1468 { 1469 ValueObject *synthetic_child; 1470 // We haven't made a synthetic array member for INDEX yet, so 1471 // lets make one and cache it for any future reference. 1472 synthetic_child = CreateChildAtIndex(0, true, index); 1473 1474 // Cache the value if we got one back... 1475 if (synthetic_child) 1476 { 1477 AddSyntheticChild(index_const_str, synthetic_child); 1478 synthetic_child_sp = synthetic_child->GetSP(); 1479 synthetic_child_sp->SetName(ConstString(index_str)); 1480 synthetic_child_sp->m_is_array_item_for_pointer = true; 1481 } 1482 } 1483 } 1484 return synthetic_child_sp; 1485} 1486 1487// This allows you to create an array member using and index 1488// that doesn't not fall in the normal bounds of the array. 1489// Many times structure can be defined as: 1490// struct Collection 1491// { 1492// uint32_t item_count; 1493// Item item_array[0]; 1494// }; 1495// The size of the "item_array" is 1, but many times in practice 1496// there are more items in "item_array". 1497 1498ValueObjectSP 1499ValueObject::GetSyntheticArrayMemberFromArray (int32_t index, bool can_create) 1500{ 1501 ValueObjectSP synthetic_child_sp; 1502 if (IsArrayType ()) 1503 { 1504 char index_str[64]; 1505 snprintf(index_str, sizeof(index_str), "[%i]", index); 1506 ConstString index_const_str(index_str); 1507 // Check if we have already created a synthetic array member in this 1508 // valid object. If we have we will re-use it. 1509 synthetic_child_sp = GetSyntheticChild (index_const_str); 1510 if (!synthetic_child_sp) 1511 { 1512 ValueObject *synthetic_child; 1513 // We haven't made a synthetic array member for INDEX yet, so 1514 // lets make one and cache it for any future reference. 1515 synthetic_child = CreateChildAtIndex(0, true, index); 1516 1517 // Cache the value if we got one back... 1518 if (synthetic_child) 1519 { 1520 AddSyntheticChild(index_const_str, synthetic_child); 1521 synthetic_child_sp = synthetic_child->GetSP(); 1522 synthetic_child_sp->SetName(ConstString(index_str)); 1523 synthetic_child_sp->m_is_array_item_for_pointer = true; 1524 } 1525 } 1526 } 1527 return synthetic_child_sp; 1528} 1529 1530ValueObjectSP 1531ValueObject::GetSyntheticBitFieldChild (uint32_t from, uint32_t to, bool can_create) 1532{ 1533 ValueObjectSP synthetic_child_sp; 1534 if (IsScalarType ()) 1535 { 1536 char index_str[64]; 1537 snprintf(index_str, sizeof(index_str), "[%i-%i]", from, to); 1538 ConstString index_const_str(index_str); 1539 // Check if we have already created a synthetic array member in this 1540 // valid object. If we have we will re-use it. 1541 synthetic_child_sp = GetSyntheticChild (index_const_str); 1542 if (!synthetic_child_sp) 1543 { 1544 ValueObjectChild *synthetic_child; 1545 // We haven't made a synthetic array member for INDEX yet, so 1546 // lets make one and cache it for any future reference. 1547 synthetic_child = new ValueObjectChild(*this, 1548 GetClangAST(), 1549 GetClangType(), 1550 index_const_str, 1551 GetByteSize(), 1552 0, 1553 to-from+1, 1554 from, 1555 false, 1556 false); 1557 1558 // Cache the value if we got one back... 1559 if (synthetic_child) 1560 { 1561 AddSyntheticChild(index_const_str, synthetic_child); 1562 synthetic_child_sp = synthetic_child->GetSP(); 1563 synthetic_child_sp->SetName(ConstString(index_str)); 1564 synthetic_child_sp->m_is_bitfield_for_scalar = true; 1565 } 1566 } 1567 } 1568 return synthetic_child_sp; 1569} 1570 1571lldb::ValueObjectSP 1572ValueObject::GetSyntheticArrayRangeChild (uint32_t from, uint32_t to, bool can_create) 1573{ 1574 ValueObjectSP synthetic_child_sp; 1575 if (IsArrayType () || IsPointerType ()) 1576 { 1577 char index_str[64]; 1578 snprintf(index_str, sizeof(index_str), "[%i-%i]", from, to); 1579 ConstString index_const_str(index_str); 1580 // Check if we have already created a synthetic array member in this 1581 // valid object. If we have we will re-use it. 1582 synthetic_child_sp = GetSyntheticChild (index_const_str); 1583 if (!synthetic_child_sp) 1584 { 1585 ValueObjectSynthetic *synthetic_child; 1586 1587 // We haven't made a synthetic array member for INDEX yet, so 1588 // lets make one and cache it for any future reference. 1589 SyntheticArrayView *view = new SyntheticArrayView(); 1590 view->AddRange(from,to); 1591 SyntheticChildrenSP view_sp(view); 1592 synthetic_child = new ValueObjectSynthetic(*this, view_sp); 1593 1594 // Cache the value if we got one back... 1595 if (synthetic_child) 1596 { 1597 AddSyntheticChild(index_const_str, synthetic_child); 1598 synthetic_child_sp = synthetic_child->GetSP(); 1599 synthetic_child_sp->SetName(ConstString(index_str)); 1600 synthetic_child_sp->m_is_bitfield_for_scalar = true; 1601 } 1602 } 1603 } 1604 return synthetic_child_sp; 1605} 1606 1607lldb::ValueObjectSP 1608ValueObject::GetSyntheticChildAtOffset(uint32_t offset, const ClangASTType& type, bool can_create) 1609{ 1610 1611 ValueObjectSP synthetic_child_sp; 1612 1613 char name_str[64]; 1614 snprintf(name_str, sizeof(name_str), "@%i", offset); 1615 ConstString name_const_str(name_str); 1616 1617 // Check if we have already created a synthetic array member in this 1618 // valid object. If we have we will re-use it. 1619 synthetic_child_sp = GetSyntheticChild (name_const_str); 1620 1621 if (synthetic_child_sp.get()) 1622 return synthetic_child_sp; 1623 1624 if (!can_create) 1625 return lldb::ValueObjectSP(); 1626 1627 ValueObjectChild *synthetic_child = new ValueObjectChild(*this, 1628 type.GetASTContext(), 1629 type.GetOpaqueQualType(), 1630 name_const_str, 1631 type.GetTypeByteSize(), 1632 offset, 1633 0, 1634 0, 1635 false, 1636 false); 1637 if (synthetic_child) 1638 { 1639 AddSyntheticChild(name_const_str, synthetic_child); 1640 synthetic_child_sp = synthetic_child->GetSP(); 1641 synthetic_child_sp->SetName(name_const_str); 1642 synthetic_child_sp->m_is_child_at_offset = true; 1643 } 1644 return synthetic_child_sp; 1645} 1646 1647// your expression path needs to have a leading . or -> 1648// (unless it somehow "looks like" an array, in which case it has 1649// a leading [ symbol). while the [ is meaningful and should be shown 1650// to the user, . and -> are just parser design, but by no means 1651// added information for the user.. strip them off 1652static const char* 1653SkipLeadingExpressionPathSeparators(const char* expression) 1654{ 1655 if (!expression || !expression[0]) 1656 return expression; 1657 if (expression[0] == '.') 1658 return expression+1; 1659 if (expression[0] == '-' && expression[1] == '>') 1660 return expression+2; 1661 return expression; 1662} 1663 1664lldb::ValueObjectSP 1665ValueObject::GetSyntheticExpressionPathChild(const char* expression, bool can_create) 1666{ 1667 ValueObjectSP synthetic_child_sp; 1668 ConstString name_const_string(expression); 1669 // Check if we have already created a synthetic array member in this 1670 // valid object. If we have we will re-use it. 1671 synthetic_child_sp = GetSyntheticChild (name_const_string); 1672 if (!synthetic_child_sp) 1673 { 1674 // We haven't made a synthetic array member for expression yet, so 1675 // lets make one and cache it for any future reference. 1676 synthetic_child_sp = GetValueForExpressionPath(expression); 1677 1678 // Cache the value if we got one back... 1679 if (synthetic_child_sp.get()) 1680 { 1681 AddSyntheticChild(name_const_string, synthetic_child_sp.get()); 1682 synthetic_child_sp->SetName(ConstString(SkipLeadingExpressionPathSeparators(expression))); 1683 synthetic_child_sp->m_is_expression_path_child = true; 1684 } 1685 } 1686 return synthetic_child_sp; 1687} 1688 1689void 1690ValueObject::CalculateSyntheticValue (lldb::SyntheticValueType use_synthetic) 1691{ 1692 if (use_synthetic == lldb::eNoSyntheticFilter) 1693 return; 1694 1695 UpdateFormatsIfNeeded(m_last_format_mgr_dynamic); 1696 1697 if (m_last_synthetic_filter.get() == NULL) 1698 return; 1699 1700 if (m_synthetic_value == NULL) 1701 m_synthetic_value = new ValueObjectSynthetic(*this, m_last_synthetic_filter); 1702 1703} 1704 1705void 1706ValueObject::CalculateDynamicValue (lldb::DynamicValueType use_dynamic) 1707{ 1708 if (use_dynamic == lldb::eNoDynamicValues) 1709 return; 1710 1711 if (!m_dynamic_value && !IsDynamic()) 1712 { 1713 Process *process = m_update_point.GetProcessSP().get(); 1714 bool worth_having_dynamic_value = false; 1715 1716 1717 // FIXME: Process should have some kind of "map over Runtimes" so we don't have to 1718 // hard code this everywhere. 1719 lldb::LanguageType known_type = GetObjectRuntimeLanguage(); 1720 if (known_type != lldb::eLanguageTypeUnknown && known_type != lldb::eLanguageTypeC) 1721 { 1722 LanguageRuntime *runtime = process->GetLanguageRuntime (known_type); 1723 if (runtime) 1724 worth_having_dynamic_value = runtime->CouldHaveDynamicValue(*this); 1725 } 1726 else 1727 { 1728 LanguageRuntime *cpp_runtime = process->GetLanguageRuntime (lldb::eLanguageTypeC_plus_plus); 1729 if (cpp_runtime) 1730 worth_having_dynamic_value = cpp_runtime->CouldHaveDynamicValue(*this); 1731 1732 if (!worth_having_dynamic_value) 1733 { 1734 LanguageRuntime *objc_runtime = process->GetLanguageRuntime (lldb::eLanguageTypeObjC); 1735 if (objc_runtime) 1736 worth_having_dynamic_value = objc_runtime->CouldHaveDynamicValue(*this); 1737 } 1738 } 1739 1740 if (worth_having_dynamic_value) 1741 m_dynamic_value = new ValueObjectDynamicValue (*this, use_dynamic); 1742 1743// if (worth_having_dynamic_value) 1744// printf ("Adding dynamic value %s (%p) to (%p) - manager %p.\n", m_name.GetCString(), m_dynamic_value, this, m_manager); 1745 1746 } 1747} 1748 1749ValueObjectSP 1750ValueObject::GetDynamicValue (DynamicValueType use_dynamic) 1751{ 1752 if (use_dynamic == lldb::eNoDynamicValues) 1753 return ValueObjectSP(); 1754 1755 if (!IsDynamic() && m_dynamic_value == NULL) 1756 { 1757 CalculateDynamicValue(use_dynamic); 1758 } 1759 if (m_dynamic_value) 1760 return m_dynamic_value->GetSP(); 1761 else 1762 return ValueObjectSP(); 1763} 1764 1765// GetDynamicValue() returns a NULL SharedPointer if the object is not dynamic 1766// or we do not really want a dynamic VO. this method instead returns this object 1767// itself when making it synthetic has no meaning. this makes it much simpler 1768// to replace the SyntheticValue for the ValueObject 1769ValueObjectSP 1770ValueObject::GetSyntheticValue (SyntheticValueType use_synthetic) 1771{ 1772 if (use_synthetic == lldb::eNoSyntheticFilter) 1773 return GetSP(); 1774 1775 UpdateFormatsIfNeeded(m_last_format_mgr_dynamic); 1776 1777 if (m_last_synthetic_filter.get() == NULL) 1778 return GetSP(); 1779 1780 CalculateSyntheticValue(use_synthetic); 1781 1782 if (m_synthetic_value) 1783 return m_synthetic_value->GetSP(); 1784 else 1785 return GetSP(); 1786} 1787 1788bool 1789ValueObject::HasSyntheticValue() 1790{ 1791 UpdateFormatsIfNeeded(m_last_format_mgr_dynamic); 1792 1793 if (m_last_synthetic_filter.get() == NULL) 1794 return false; 1795 1796 CalculateSyntheticValue(lldb::eUseSyntheticFilter); 1797 1798 if (m_synthetic_value) 1799 return true; 1800 else 1801 return false; 1802} 1803 1804bool 1805ValueObject::GetBaseClassPath (Stream &s) 1806{ 1807 if (IsBaseClass()) 1808 { 1809 bool parent_had_base_class = GetParent() && GetParent()->GetBaseClassPath (s); 1810 clang_type_t clang_type = GetClangType(); 1811 std::string cxx_class_name; 1812 bool this_had_base_class = ClangASTContext::GetCXXClassName (clang_type, cxx_class_name); 1813 if (this_had_base_class) 1814 { 1815 if (parent_had_base_class) 1816 s.PutCString("::"); 1817 s.PutCString(cxx_class_name.c_str()); 1818 } 1819 return parent_had_base_class || this_had_base_class; 1820 } 1821 return false; 1822} 1823 1824 1825ValueObject * 1826ValueObject::GetNonBaseClassParent() 1827{ 1828 if (GetParent()) 1829 { 1830 if (GetParent()->IsBaseClass()) 1831 return GetParent()->GetNonBaseClassParent(); 1832 else 1833 return GetParent(); 1834 } 1835 return NULL; 1836} 1837 1838void 1839ValueObject::GetExpressionPath (Stream &s, bool qualify_cxx_base_classes, GetExpressionPathFormat epformat) 1840{ 1841 const bool is_deref_of_parent = IsDereferenceOfParent (); 1842 1843 if (is_deref_of_parent && epformat == eDereferencePointers) 1844 { 1845 // this is the original format of GetExpressionPath() producing code like *(a_ptr).memberName, which is entirely 1846 // fine, until you put this into StackFrame::GetValueForVariableExpressionPath() which prefers to see a_ptr->memberName. 1847 // the eHonorPointers mode is meant to produce strings in this latter format 1848 s.PutCString("*("); 1849 } 1850 1851 ValueObject* parent = GetParent(); 1852 1853 if (parent) 1854 parent->GetExpressionPath (s, qualify_cxx_base_classes, epformat); 1855 1856 // if we are a deref_of_parent just because we are synthetic array 1857 // members made up to allow ptr[%d] syntax to work in variable 1858 // printing, then add our name ([%d]) to the expression path 1859 if (m_is_array_item_for_pointer && epformat == eHonorPointers) 1860 s.PutCString(m_name.AsCString()); 1861 1862 if (!IsBaseClass()) 1863 { 1864 if (!is_deref_of_parent) 1865 { 1866 ValueObject *non_base_class_parent = GetNonBaseClassParent(); 1867 if (non_base_class_parent) 1868 { 1869 clang_type_t non_base_class_parent_clang_type = non_base_class_parent->GetClangType(); 1870 if (non_base_class_parent_clang_type) 1871 { 1872 const uint32_t non_base_class_parent_type_info = ClangASTContext::GetTypeInfo (non_base_class_parent_clang_type, NULL, NULL); 1873 1874 if (parent && parent->IsDereferenceOfParent() && epformat == eHonorPointers) 1875 { 1876 s.PutCString("->"); 1877 } 1878 else 1879 { 1880 if (non_base_class_parent_type_info & ClangASTContext::eTypeIsPointer) 1881 { 1882 s.PutCString("->"); 1883 } 1884 else if ((non_base_class_parent_type_info & ClangASTContext::eTypeHasChildren) && 1885 !(non_base_class_parent_type_info & ClangASTContext::eTypeIsArray)) 1886 { 1887 s.PutChar('.'); 1888 } 1889 } 1890 } 1891 } 1892 1893 const char *name = GetName().GetCString(); 1894 if (name) 1895 { 1896 if (qualify_cxx_base_classes) 1897 { 1898 if (GetBaseClassPath (s)) 1899 s.PutCString("::"); 1900 } 1901 s.PutCString(name); 1902 } 1903 } 1904 } 1905 1906 if (is_deref_of_parent && epformat == eDereferencePointers) 1907 { 1908 s.PutChar(')'); 1909 } 1910} 1911 1912lldb::ValueObjectSP 1913ValueObject::GetValueForExpressionPath(const char* expression, 1914 const char** first_unparsed, 1915 ExpressionPathScanEndReason* reason_to_stop, 1916 ExpressionPathEndResultType* final_value_type, 1917 const GetValueForExpressionPathOptions& options, 1918 ExpressionPathAftermath* final_task_on_target) 1919{ 1920 1921 const char* dummy_first_unparsed; 1922 ExpressionPathScanEndReason dummy_reason_to_stop; 1923 ExpressionPathEndResultType dummy_final_value_type; 1924 ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eNothing; 1925 1926 ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression, 1927 first_unparsed ? first_unparsed : &dummy_first_unparsed, 1928 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop, 1929 final_value_type ? final_value_type : &dummy_final_value_type, 1930 options, 1931 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target); 1932 1933 if (!final_task_on_target || *final_task_on_target == ValueObject::eNothing) 1934 { 1935 return ret_val; 1936 } 1937 if (ret_val.get() && *final_value_type == ePlain) // I can only deref and takeaddress of plain objects 1938 { 1939 if (*final_task_on_target == ValueObject::eDereference) 1940 { 1941 Error error; 1942 ValueObjectSP final_value = ret_val->Dereference(error); 1943 if (error.Fail() || !final_value.get()) 1944 { 1945 *reason_to_stop = ValueObject::eDereferencingFailed; 1946 *final_value_type = ValueObject::eInvalid; 1947 return ValueObjectSP(); 1948 } 1949 else 1950 { 1951 *final_task_on_target = ValueObject::eNothing; 1952 return final_value; 1953 } 1954 } 1955 if (*final_task_on_target == ValueObject::eTakeAddress) 1956 { 1957 Error error; 1958 ValueObjectSP final_value = ret_val->AddressOf(error); 1959 if (error.Fail() || !final_value.get()) 1960 { 1961 *reason_to_stop = ValueObject::eTakingAddressFailed; 1962 *final_value_type = ValueObject::eInvalid; 1963 return ValueObjectSP(); 1964 } 1965 else 1966 { 1967 *final_task_on_target = ValueObject::eNothing; 1968 return final_value; 1969 } 1970 } 1971 } 1972 return ret_val; // final_task_on_target will still have its original value, so you know I did not do it 1973} 1974 1975int 1976ValueObject::GetValuesForExpressionPath(const char* expression, 1977 lldb::ValueObjectListSP& list, 1978 const char** first_unparsed, 1979 ExpressionPathScanEndReason* reason_to_stop, 1980 ExpressionPathEndResultType* final_value_type, 1981 const GetValueForExpressionPathOptions& options, 1982 ExpressionPathAftermath* final_task_on_target) 1983{ 1984 const char* dummy_first_unparsed; 1985 ExpressionPathScanEndReason dummy_reason_to_stop; 1986 ExpressionPathEndResultType dummy_final_value_type; 1987 ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eNothing; 1988 1989 ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression, 1990 first_unparsed ? first_unparsed : &dummy_first_unparsed, 1991 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop, 1992 final_value_type ? final_value_type : &dummy_final_value_type, 1993 options, 1994 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target); 1995 1996 if (!ret_val.get()) // if there are errors, I add nothing to the list 1997 return 0; 1998 1999 if (*reason_to_stop != eArrayRangeOperatorMet) 2000 { 2001 // I need not expand a range, just post-process the final value and return 2002 if (!final_task_on_target || *final_task_on_target == ValueObject::eNothing) 2003 { 2004 list->Append(ret_val); 2005 return 1; 2006 } 2007 if (ret_val.get() && *final_value_type == ePlain) // I can only deref and takeaddress of plain objects 2008 { 2009 if (*final_task_on_target == ValueObject::eDereference) 2010 { 2011 Error error; 2012 ValueObjectSP final_value = ret_val->Dereference(error); 2013 if (error.Fail() || !final_value.get()) 2014 { 2015 *reason_to_stop = ValueObject::eDereferencingFailed; 2016 *final_value_type = ValueObject::eInvalid; 2017 return 0; 2018 } 2019 else 2020 { 2021 *final_task_on_target = ValueObject::eNothing; 2022 list->Append(final_value); 2023 return 1; 2024 } 2025 } 2026 if (*final_task_on_target == ValueObject::eTakeAddress) 2027 { 2028 Error error; 2029 ValueObjectSP final_value = ret_val->AddressOf(error); 2030 if (error.Fail() || !final_value.get()) 2031 { 2032 *reason_to_stop = ValueObject::eTakingAddressFailed; 2033 *final_value_type = ValueObject::eInvalid; 2034 return 0; 2035 } 2036 else 2037 { 2038 *final_task_on_target = ValueObject::eNothing; 2039 list->Append(final_value); 2040 return 1; 2041 } 2042 } 2043 } 2044 } 2045 else 2046 { 2047 return ExpandArraySliceExpression(first_unparsed ? *first_unparsed : dummy_first_unparsed, 2048 first_unparsed ? first_unparsed : &dummy_first_unparsed, 2049 ret_val, 2050 list, 2051 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop, 2052 final_value_type ? final_value_type : &dummy_final_value_type, 2053 options, 2054 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target); 2055 } 2056 // in any non-covered case, just do the obviously right thing 2057 list->Append(ret_val); 2058 return 1; 2059} 2060 2061lldb::ValueObjectSP 2062ValueObject::GetValueForExpressionPath_Impl(const char* expression_cstr, 2063 const char** first_unparsed, 2064 ExpressionPathScanEndReason* reason_to_stop, 2065 ExpressionPathEndResultType* final_result, 2066 const GetValueForExpressionPathOptions& options, 2067 ExpressionPathAftermath* what_next) 2068{ 2069 ValueObjectSP root = GetSP(); 2070 2071 if (!root.get()) 2072 return ValueObjectSP(); 2073 2074 *first_unparsed = expression_cstr; 2075 2076 while (true) 2077 { 2078 2079 const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr 2080 2081 lldb::clang_type_t root_clang_type = root->GetClangType(); 2082 lldb::clang_type_t pointee_clang_type; 2083 Flags root_clang_type_info,pointee_clang_type_info; 2084 2085 root_clang_type_info = Flags(ClangASTContext::GetTypeInfo(root_clang_type, GetClangAST(), &pointee_clang_type)); 2086 if (pointee_clang_type) 2087 pointee_clang_type_info = Flags(ClangASTContext::GetTypeInfo(pointee_clang_type, GetClangAST(), NULL)); 2088 2089 if (!expression_cstr || *expression_cstr == '\0') 2090 { 2091 *reason_to_stop = ValueObject::eEndOfString; 2092 return root; 2093 } 2094 2095 switch (*expression_cstr) 2096 { 2097 case '-': 2098 { 2099 if (options.m_check_dot_vs_arrow_syntax && 2100 root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) ) // if you are trying to use -> on a non-pointer and I must catch the error 2101 { 2102 *first_unparsed = expression_cstr; 2103 *reason_to_stop = ValueObject::eArrowInsteadOfDot; 2104 *final_result = ValueObject::eInvalid; 2105 return ValueObjectSP(); 2106 } 2107 if (root_clang_type_info.Test(ClangASTContext::eTypeIsObjC) && // if yo are trying to extract an ObjC IVar when this is forbidden 2108 root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) && 2109 options.m_no_fragile_ivar) 2110 { 2111 *first_unparsed = expression_cstr; 2112 *reason_to_stop = ValueObject::eFragileIVarNotAllowed; 2113 *final_result = ValueObject::eInvalid; 2114 return ValueObjectSP(); 2115 } 2116 if (expression_cstr[1] != '>') 2117 { 2118 *first_unparsed = expression_cstr; 2119 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2120 *final_result = ValueObject::eInvalid; 2121 return ValueObjectSP(); 2122 } 2123 expression_cstr++; // skip the - 2124 } 2125 case '.': // or fallthrough from -> 2126 { 2127 if (options.m_check_dot_vs_arrow_syntax && *expression_cstr == '.' && 2128 root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if you are trying to use . on a pointer and I must catch the error 2129 { 2130 *first_unparsed = expression_cstr; 2131 *reason_to_stop = ValueObject::eDotInsteadOfArrow; 2132 *final_result = ValueObject::eInvalid; 2133 return ValueObjectSP(); 2134 } 2135 expression_cstr++; // skip . 2136 const char *next_separator = strpbrk(expression_cstr+1,"-.["); 2137 ConstString child_name; 2138 if (!next_separator) // if no other separator just expand this last layer 2139 { 2140 child_name.SetCString (expression_cstr); 2141 ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true); 2142 2143 if (child_valobj_sp.get()) // we know we are done, so just return 2144 { 2145 *first_unparsed = '\0'; 2146 *reason_to_stop = ValueObject::eEndOfString; 2147 *final_result = ValueObject::ePlain; 2148 return child_valobj_sp; 2149 } 2150 else if (options.m_no_synthetic_children == false) // let's try with synthetic children 2151 { 2152 child_valobj_sp = root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetChildMemberWithName(child_name, true); 2153 } 2154 2155 // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP, 2156 // so we hit the "else" branch, and return an error 2157 if(child_valobj_sp.get()) // if it worked, just return 2158 { 2159 *first_unparsed = '\0'; 2160 *reason_to_stop = ValueObject::eEndOfString; 2161 *final_result = ValueObject::ePlain; 2162 return child_valobj_sp; 2163 } 2164 else 2165 { 2166 *first_unparsed = expression_cstr; 2167 *reason_to_stop = ValueObject::eNoSuchChild; 2168 *final_result = ValueObject::eInvalid; 2169 return ValueObjectSP(); 2170 } 2171 } 2172 else // other layers do expand 2173 { 2174 child_name.SetCStringWithLength(expression_cstr, next_separator - expression_cstr); 2175 ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true); 2176 if (child_valobj_sp.get()) // store the new root and move on 2177 { 2178 root = child_valobj_sp; 2179 *first_unparsed = next_separator; 2180 *final_result = ValueObject::ePlain; 2181 continue; 2182 } 2183 else if (options.m_no_synthetic_children == false) // let's try with synthetic children 2184 { 2185 child_valobj_sp = root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetChildMemberWithName(child_name, true); 2186 } 2187 2188 // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP, 2189 // so we hit the "else" branch, and return an error 2190 if(child_valobj_sp.get()) // if it worked, move on 2191 { 2192 root = child_valobj_sp; 2193 *first_unparsed = next_separator; 2194 *final_result = ValueObject::ePlain; 2195 continue; 2196 } 2197 else 2198 { 2199 *first_unparsed = expression_cstr; 2200 *reason_to_stop = ValueObject::eNoSuchChild; 2201 *final_result = ValueObject::eInvalid; 2202 return ValueObjectSP(); 2203 } 2204 } 2205 break; 2206 } 2207 case '[': 2208 { 2209 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray) && !root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if this is not a T[] nor a T* 2210 { 2211 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // if this is not even a scalar... 2212 { 2213 if (options.m_no_synthetic_children) // ...only chance left is synthetic 2214 { 2215 *first_unparsed = expression_cstr; 2216 *reason_to_stop = ValueObject::eRangeOperatorInvalid; 2217 *final_result = ValueObject::eInvalid; 2218 return ValueObjectSP(); 2219 } 2220 } 2221 else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields 2222 { 2223 *first_unparsed = expression_cstr; 2224 *reason_to_stop = ValueObject::eRangeOperatorNotAllowed; 2225 *final_result = ValueObject::eInvalid; 2226 return ValueObjectSP(); 2227 } 2228 } 2229 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays 2230 { 2231 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2232 { 2233 *first_unparsed = expression_cstr; 2234 *reason_to_stop = ValueObject::eEmptyRangeNotAllowed; 2235 *final_result = ValueObject::eInvalid; 2236 return ValueObjectSP(); 2237 } 2238 else // even if something follows, we cannot expand unbounded ranges, just let the caller do it 2239 { 2240 *first_unparsed = expression_cstr+2; 2241 *reason_to_stop = ValueObject::eArrayRangeOperatorMet; 2242 *final_result = ValueObject::eUnboundedRange; 2243 return root; 2244 } 2245 } 2246 const char *separator_position = ::strchr(expression_cstr+1,'-'); 2247 const char *close_bracket_position = ::strchr(expression_cstr+1,']'); 2248 if (!close_bracket_position) // if there is no ], this is a syntax error 2249 { 2250 *first_unparsed = expression_cstr; 2251 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2252 *final_result = ValueObject::eInvalid; 2253 return ValueObjectSP(); 2254 } 2255 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N] 2256 { 2257 char *end = NULL; 2258 unsigned long index = ::strtoul (expression_cstr+1, &end, 0); 2259 if (!end || end != close_bracket_position) // if something weird is in our way return an error 2260 { 2261 *first_unparsed = expression_cstr; 2262 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2263 *final_result = ValueObject::eInvalid; 2264 return ValueObjectSP(); 2265 } 2266 if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays 2267 { 2268 if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2269 { 2270 *first_unparsed = expression_cstr+2; 2271 *reason_to_stop = ValueObject::eArrayRangeOperatorMet; 2272 *final_result = ValueObject::eUnboundedRange; 2273 return root; 2274 } 2275 else 2276 { 2277 *first_unparsed = expression_cstr; 2278 *reason_to_stop = ValueObject::eEmptyRangeNotAllowed; 2279 *final_result = ValueObject::eInvalid; 2280 return ValueObjectSP(); 2281 } 2282 } 2283 // from here on we do have a valid index 2284 if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2285 { 2286 ValueObjectSP child_valobj_sp = root->GetChildAtIndex(index, true); 2287 if (!child_valobj_sp) 2288 child_valobj_sp = root->GetSyntheticArrayMemberFromArray(index, true); 2289 if (!child_valobj_sp) 2290 if (root->HasSyntheticValue() && root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetNumChildren() > index) 2291 child_valobj_sp = root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetChildAtIndex(index, true); 2292 if (child_valobj_sp) 2293 { 2294 root = child_valobj_sp; 2295 *first_unparsed = end+1; // skip ] 2296 *final_result = ValueObject::ePlain; 2297 continue; 2298 } 2299 else 2300 { 2301 *first_unparsed = expression_cstr; 2302 *reason_to_stop = ValueObject::eNoSuchChild; 2303 *final_result = ValueObject::eInvalid; 2304 return ValueObjectSP(); 2305 } 2306 } 2307 else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) 2308 { 2309 if (*what_next == ValueObject::eDereference && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield 2310 pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) 2311 { 2312 Error error; 2313 root = root->Dereference(error); 2314 if (error.Fail() || !root.get()) 2315 { 2316 *first_unparsed = expression_cstr; 2317 *reason_to_stop = ValueObject::eDereferencingFailed; 2318 *final_result = ValueObject::eInvalid; 2319 return ValueObjectSP(); 2320 } 2321 else 2322 { 2323 *what_next = eNothing; 2324 continue; 2325 } 2326 } 2327 else 2328 { 2329 if (ClangASTType::GetMinimumLanguage(root->GetClangAST(), 2330 root->GetClangType()) == lldb::eLanguageTypeObjC 2331 && 2332 ClangASTContext::IsPointerType(ClangASTType::GetPointeeType(root->GetClangType())) == false 2333 && 2334 root->HasSyntheticValue() 2335 && 2336 options.m_no_synthetic_children == false) 2337 { 2338 root = root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetChildAtIndex(index, true); 2339 } 2340 else 2341 root = root->GetSyntheticArrayMemberFromPointer(index, true); 2342 if (!root.get()) 2343 { 2344 *first_unparsed = expression_cstr; 2345 *reason_to_stop = ValueObject::eNoSuchChild; 2346 *final_result = ValueObject::eInvalid; 2347 return ValueObjectSP(); 2348 } 2349 else 2350 { 2351 *first_unparsed = end+1; // skip ] 2352 *final_result = ValueObject::ePlain; 2353 continue; 2354 } 2355 } 2356 } 2357 else if (ClangASTContext::IsScalarType(root_clang_type)) 2358 { 2359 root = root->GetSyntheticBitFieldChild(index, index, true); 2360 if (!root.get()) 2361 { 2362 *first_unparsed = expression_cstr; 2363 *reason_to_stop = ValueObject::eNoSuchChild; 2364 *final_result = ValueObject::eInvalid; 2365 return ValueObjectSP(); 2366 } 2367 else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing 2368 { 2369 *first_unparsed = end+1; // skip ] 2370 *reason_to_stop = ValueObject::eBitfieldRangeOperatorMet; 2371 *final_result = ValueObject::eBitfield; 2372 return root; 2373 } 2374 } 2375 else if (root->HasSyntheticValue() && options.m_no_synthetic_children == false) 2376 { 2377 root = root->GetSyntheticValue(lldb::eUseSyntheticFilter)->GetChildAtIndex(index, true); 2378 if (!root.get()) 2379 { 2380 *first_unparsed = expression_cstr; 2381 *reason_to_stop = ValueObject::eNoSuchChild; 2382 *final_result = ValueObject::eInvalid; 2383 return ValueObjectSP(); 2384 } 2385 else 2386 { 2387 *first_unparsed = end+1; // skip ] 2388 *final_result = ValueObject::ePlain; 2389 continue; 2390 } 2391 } 2392 else 2393 { 2394 *first_unparsed = expression_cstr; 2395 *reason_to_stop = ValueObject::eNoSuchChild; 2396 *final_result = ValueObject::eInvalid; 2397 return ValueObjectSP(); 2398 } 2399 } 2400 else // we have a low and a high index 2401 { 2402 char *end = NULL; 2403 unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0); 2404 if (!end || end != separator_position) // if something weird is in our way return an error 2405 { 2406 *first_unparsed = expression_cstr; 2407 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2408 *final_result = ValueObject::eInvalid; 2409 return ValueObjectSP(); 2410 } 2411 unsigned long index_higher = ::strtoul (separator_position+1, &end, 0); 2412 if (!end || end != close_bracket_position) // if something weird is in our way return an error 2413 { 2414 *first_unparsed = expression_cstr; 2415 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2416 *final_result = ValueObject::eInvalid; 2417 return ValueObjectSP(); 2418 } 2419 if (index_lower > index_higher) // swap indices if required 2420 { 2421 unsigned long temp = index_lower; 2422 index_lower = index_higher; 2423 index_higher = temp; 2424 } 2425 if (root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // expansion only works for scalars 2426 { 2427 root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true); 2428 if (!root.get()) 2429 { 2430 *first_unparsed = expression_cstr; 2431 *reason_to_stop = ValueObject::eNoSuchChild; 2432 *final_result = ValueObject::eInvalid; 2433 return ValueObjectSP(); 2434 } 2435 else 2436 { 2437 *first_unparsed = end+1; // skip ] 2438 *reason_to_stop = ValueObject::eBitfieldRangeOperatorMet; 2439 *final_result = ValueObject::eBitfield; 2440 return root; 2441 } 2442 } 2443 else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield 2444 *what_next == ValueObject::eDereference && 2445 pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) 2446 { 2447 Error error; 2448 root = root->Dereference(error); 2449 if (error.Fail() || !root.get()) 2450 { 2451 *first_unparsed = expression_cstr; 2452 *reason_to_stop = ValueObject::eDereferencingFailed; 2453 *final_result = ValueObject::eInvalid; 2454 return ValueObjectSP(); 2455 } 2456 else 2457 { 2458 *what_next = ValueObject::eNothing; 2459 continue; 2460 } 2461 } 2462 else 2463 { 2464 *first_unparsed = expression_cstr; 2465 *reason_to_stop = ValueObject::eArrayRangeOperatorMet; 2466 *final_result = ValueObject::eBoundedRange; 2467 return root; 2468 } 2469 } 2470 break; 2471 } 2472 default: // some non-separator is in the way 2473 { 2474 *first_unparsed = expression_cstr; 2475 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2476 *final_result = ValueObject::eInvalid; 2477 return ValueObjectSP(); 2478 break; 2479 } 2480 } 2481 } 2482} 2483 2484int 2485ValueObject::ExpandArraySliceExpression(const char* expression_cstr, 2486 const char** first_unparsed, 2487 lldb::ValueObjectSP root, 2488 lldb::ValueObjectListSP& list, 2489 ExpressionPathScanEndReason* reason_to_stop, 2490 ExpressionPathEndResultType* final_result, 2491 const GetValueForExpressionPathOptions& options, 2492 ExpressionPathAftermath* what_next) 2493{ 2494 if (!root.get()) 2495 return 0; 2496 2497 *first_unparsed = expression_cstr; 2498 2499 while (true) 2500 { 2501 2502 const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr 2503 2504 lldb::clang_type_t root_clang_type = root->GetClangType(); 2505 lldb::clang_type_t pointee_clang_type; 2506 Flags root_clang_type_info,pointee_clang_type_info; 2507 2508 root_clang_type_info = Flags(ClangASTContext::GetTypeInfo(root_clang_type, GetClangAST(), &pointee_clang_type)); 2509 if (pointee_clang_type) 2510 pointee_clang_type_info = Flags(ClangASTContext::GetTypeInfo(pointee_clang_type, GetClangAST(), NULL)); 2511 2512 if (!expression_cstr || *expression_cstr == '\0') 2513 { 2514 *reason_to_stop = ValueObject::eEndOfString; 2515 list->Append(root); 2516 return 1; 2517 } 2518 2519 switch (*expression_cstr) 2520 { 2521 case '[': 2522 { 2523 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray) && !root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if this is not a T[] nor a T* 2524 { 2525 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // if this is not even a scalar, this syntax is just plain wrong! 2526 { 2527 *first_unparsed = expression_cstr; 2528 *reason_to_stop = ValueObject::eRangeOperatorInvalid; 2529 *final_result = ValueObject::eInvalid; 2530 return 0; 2531 } 2532 else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields 2533 { 2534 *first_unparsed = expression_cstr; 2535 *reason_to_stop = ValueObject::eRangeOperatorNotAllowed; 2536 *final_result = ValueObject::eInvalid; 2537 return 0; 2538 } 2539 } 2540 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays 2541 { 2542 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2543 { 2544 *first_unparsed = expression_cstr; 2545 *reason_to_stop = ValueObject::eEmptyRangeNotAllowed; 2546 *final_result = ValueObject::eInvalid; 2547 return 0; 2548 } 2549 else // expand this into list 2550 { 2551 int max_index = root->GetNumChildren() - 1; 2552 for (int index = 0; index < max_index; index++) 2553 { 2554 ValueObjectSP child = 2555 root->GetChildAtIndex(index, true); 2556 list->Append(child); 2557 } 2558 *first_unparsed = expression_cstr+2; 2559 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2560 *final_result = ValueObject::eValueObjectList; 2561 return max_index; // tell me number of items I added to the VOList 2562 } 2563 } 2564 const char *separator_position = ::strchr(expression_cstr+1,'-'); 2565 const char *close_bracket_position = ::strchr(expression_cstr+1,']'); 2566 if (!close_bracket_position) // if there is no ], this is a syntax error 2567 { 2568 *first_unparsed = expression_cstr; 2569 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2570 *final_result = ValueObject::eInvalid; 2571 return 0; 2572 } 2573 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N] 2574 { 2575 char *end = NULL; 2576 unsigned long index = ::strtoul (expression_cstr+1, &end, 0); 2577 if (!end || end != close_bracket_position) // if something weird is in our way return an error 2578 { 2579 *first_unparsed = expression_cstr; 2580 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2581 *final_result = ValueObject::eInvalid; 2582 return 0; 2583 } 2584 if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays 2585 { 2586 if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2587 { 2588 int max_index = root->GetNumChildren() - 1; 2589 for (int index = 0; index < max_index; index++) 2590 { 2591 ValueObjectSP child = 2592 root->GetChildAtIndex(index, true); 2593 list->Append(child); 2594 } 2595 *first_unparsed = expression_cstr+2; 2596 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2597 *final_result = ValueObject::eValueObjectList; 2598 return max_index; // tell me number of items I added to the VOList 2599 } 2600 else 2601 { 2602 *first_unparsed = expression_cstr; 2603 *reason_to_stop = ValueObject::eEmptyRangeNotAllowed; 2604 *final_result = ValueObject::eInvalid; 2605 return 0; 2606 } 2607 } 2608 // from here on we do have a valid index 2609 if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray)) 2610 { 2611 root = root->GetChildAtIndex(index, true); 2612 if (!root.get()) 2613 { 2614 *first_unparsed = expression_cstr; 2615 *reason_to_stop = ValueObject::eNoSuchChild; 2616 *final_result = ValueObject::eInvalid; 2617 return 0; 2618 } 2619 else 2620 { 2621 list->Append(root); 2622 *first_unparsed = end+1; // skip ] 2623 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2624 *final_result = ValueObject::eValueObjectList; 2625 return 1; 2626 } 2627 } 2628 else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) 2629 { 2630 if (*what_next == ValueObject::eDereference && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield 2631 pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) 2632 { 2633 Error error; 2634 root = root->Dereference(error); 2635 if (error.Fail() || !root.get()) 2636 { 2637 *first_unparsed = expression_cstr; 2638 *reason_to_stop = ValueObject::eDereferencingFailed; 2639 *final_result = ValueObject::eInvalid; 2640 return 0; 2641 } 2642 else 2643 { 2644 *what_next = eNothing; 2645 continue; 2646 } 2647 } 2648 else 2649 { 2650 root = root->GetSyntheticArrayMemberFromPointer(index, true); 2651 if (!root.get()) 2652 { 2653 *first_unparsed = expression_cstr; 2654 *reason_to_stop = ValueObject::eNoSuchChild; 2655 *final_result = ValueObject::eInvalid; 2656 return 0; 2657 } 2658 else 2659 { 2660 list->Append(root); 2661 *first_unparsed = end+1; // skip ] 2662 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2663 *final_result = ValueObject::eValueObjectList; 2664 return 1; 2665 } 2666 } 2667 } 2668 else /*if (ClangASTContext::IsScalarType(root_clang_type))*/ 2669 { 2670 root = root->GetSyntheticBitFieldChild(index, index, true); 2671 if (!root.get()) 2672 { 2673 *first_unparsed = expression_cstr; 2674 *reason_to_stop = ValueObject::eNoSuchChild; 2675 *final_result = ValueObject::eInvalid; 2676 return 0; 2677 } 2678 else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing 2679 { 2680 list->Append(root); 2681 *first_unparsed = end+1; // skip ] 2682 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2683 *final_result = ValueObject::eValueObjectList; 2684 return 1; 2685 } 2686 } 2687 } 2688 else // we have a low and a high index 2689 { 2690 char *end = NULL; 2691 unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0); 2692 if (!end || end != separator_position) // if something weird is in our way return an error 2693 { 2694 *first_unparsed = expression_cstr; 2695 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2696 *final_result = ValueObject::eInvalid; 2697 return 0; 2698 } 2699 unsigned long index_higher = ::strtoul (separator_position+1, &end, 0); 2700 if (!end || end != close_bracket_position) // if something weird is in our way return an error 2701 { 2702 *first_unparsed = expression_cstr; 2703 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2704 *final_result = ValueObject::eInvalid; 2705 return 0; 2706 } 2707 if (index_lower > index_higher) // swap indices if required 2708 { 2709 unsigned long temp = index_lower; 2710 index_lower = index_higher; 2711 index_higher = temp; 2712 } 2713 if (root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // expansion only works for scalars 2714 { 2715 root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true); 2716 if (!root.get()) 2717 { 2718 *first_unparsed = expression_cstr; 2719 *reason_to_stop = ValueObject::eNoSuchChild; 2720 *final_result = ValueObject::eInvalid; 2721 return 0; 2722 } 2723 else 2724 { 2725 list->Append(root); 2726 *first_unparsed = end+1; // skip ] 2727 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2728 *final_result = ValueObject::eValueObjectList; 2729 return 1; 2730 } 2731 } 2732 else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield 2733 *what_next == ValueObject::eDereference && 2734 pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) 2735 { 2736 Error error; 2737 root = root->Dereference(error); 2738 if (error.Fail() || !root.get()) 2739 { 2740 *first_unparsed = expression_cstr; 2741 *reason_to_stop = ValueObject::eDereferencingFailed; 2742 *final_result = ValueObject::eInvalid; 2743 return 0; 2744 } 2745 else 2746 { 2747 *what_next = ValueObject::eNothing; 2748 continue; 2749 } 2750 } 2751 else 2752 { 2753 for (unsigned long index = index_lower; 2754 index <= index_higher; index++) 2755 { 2756 ValueObjectSP child = 2757 root->GetChildAtIndex(index, true); 2758 list->Append(child); 2759 } 2760 *first_unparsed = end+1; 2761 *reason_to_stop = ValueObject::eRangeOperatorExpanded; 2762 *final_result = ValueObject::eValueObjectList; 2763 return index_higher-index_lower+1; // tell me number of items I added to the VOList 2764 } 2765 } 2766 break; 2767 } 2768 default: // some non-[ separator, or something entirely wrong, is in the way 2769 { 2770 *first_unparsed = expression_cstr; 2771 *reason_to_stop = ValueObject::eUnexpectedSymbol; 2772 *final_result = ValueObject::eInvalid; 2773 return 0; 2774 break; 2775 } 2776 } 2777 } 2778} 2779 2780void 2781ValueObject::DumpValueObject 2782( 2783 Stream &s, 2784 ValueObject *valobj, 2785 const char *root_valobj_name, 2786 uint32_t ptr_depth, 2787 uint32_t curr_depth, 2788 uint32_t max_depth, 2789 bool show_types, 2790 bool show_location, 2791 bool use_objc, 2792 lldb::DynamicValueType use_dynamic, 2793 bool use_synth, 2794 bool scope_already_checked, 2795 bool flat_output, 2796 uint32_t omit_summary_depth, 2797 bool ignore_cap 2798) 2799{ 2800 if (valobj) 2801 { 2802 bool update_success = valobj->UpdateValueIfNeeded (use_dynamic, true); 2803 2804 if (update_success && use_dynamic != lldb::eNoDynamicValues) 2805 { 2806 ValueObject *dynamic_value = valobj->GetDynamicValue(use_dynamic).get(); 2807 if (dynamic_value) 2808 valobj = dynamic_value; 2809 } 2810 2811 clang_type_t clang_type = valobj->GetClangType(); 2812 2813 const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, NULL, NULL)); 2814 const char *err_cstr = NULL; 2815 const bool has_children = type_flags.Test (ClangASTContext::eTypeHasChildren); 2816 const bool has_value = type_flags.Test (ClangASTContext::eTypeHasValue); 2817 2818 const bool print_valobj = flat_output == false || has_value; 2819 2820 if (print_valobj) 2821 { 2822 if (show_location) 2823 { 2824 s.Printf("%s: ", valobj->GetLocationAsCString()); 2825 } 2826 2827 s.Indent(); 2828 2829 // Always show the type for the top level items. 2830 if (show_types || (curr_depth == 0 && !flat_output)) 2831 { 2832 const char* typeName = valobj->GetTypeName().AsCString("<invalid type>"); 2833 s.Printf("(%s", typeName); 2834 // only show dynamic types if the user really wants to see types 2835 if (show_types && use_dynamic != lldb::eNoDynamicValues && 2836 (/*strstr(typeName, "id") == typeName ||*/ 2837 ClangASTType::GetMinimumLanguage(valobj->GetClangAST(), valobj->GetClangType()) == lldb::eLanguageTypeObjC)) 2838 { 2839 Process* process = valobj->GetUpdatePoint().GetProcessSP().get(); 2840 if (process == NULL) 2841 s.Printf(", dynamic type: unknown) "); 2842 else 2843 { 2844 ObjCLanguageRuntime *runtime = process->GetObjCLanguageRuntime(); 2845 if (runtime == NULL) 2846 s.Printf(", dynamic type: unknown) "); 2847 else 2848 { 2849 ObjCLanguageRuntime::ObjCISA isa = runtime->GetISA(*valobj); 2850 if (!runtime->IsValidISA(isa)) 2851 s.Printf(", dynamic type: unknown) "); 2852 else 2853 s.Printf(", dynamic type: %s) ", 2854 runtime->GetActualTypeName(isa).GetCString()); 2855 } 2856 } 2857 } 2858 else 2859 s.Printf(") "); 2860 } 2861 2862 2863 if (flat_output) 2864 { 2865 // If we are showing types, also qualify the C++ base classes 2866 const bool qualify_cxx_base_classes = show_types; 2867 valobj->GetExpressionPath(s, qualify_cxx_base_classes); 2868 s.PutCString(" ="); 2869 } 2870 else 2871 { 2872 const char *name_cstr = root_valobj_name ? root_valobj_name : valobj->GetName().AsCString(""); 2873 s.Printf ("%s =", name_cstr); 2874 } 2875 2876 if (!scope_already_checked && !valobj->IsInScope()) 2877 { 2878 err_cstr = "out of scope"; 2879 } 2880 } 2881 2882 const char *val_cstr = NULL; 2883 const char *sum_cstr = NULL; 2884 SummaryFormat* entry = valobj->GetSummaryFormat().get(); 2885 2886 if (omit_summary_depth > 0) 2887 entry = NULL; 2888 2889 if (err_cstr == NULL) 2890 { 2891 val_cstr = valobj->GetValueAsCString(); 2892 err_cstr = valobj->GetError().AsCString(); 2893 } 2894 2895 if (err_cstr) 2896 { 2897 s.Printf (" <%s>\n", err_cstr); 2898 } 2899 else 2900 { 2901 const bool is_ref = type_flags.Test (ClangASTContext::eTypeIsReference); 2902 if (print_valobj) 2903 { 2904 2905 sum_cstr = (omit_summary_depth == 0) ? valobj->GetSummaryAsCString() : NULL; 2906 2907 // We must calculate this value in realtime because entry might alter this variable's value 2908 // (e.g. by saying ${var%fmt}) and render precached values useless 2909 if (val_cstr && (!entry || entry->DoesPrintValue() || !sum_cstr)) 2910 s.Printf(" %s", valobj->GetValueAsCString()); 2911 2912 if (sum_cstr) 2913 { 2914 // for some reason, using %@ (ObjC description) in a summary string, makes 2915 // us believe we need to reset ourselves, thus invalidating the content of 2916 // sum_cstr. Thus, IF we had a valid sum_cstr before, but it is now empty 2917 // let us recalculate it! 2918 if (sum_cstr[0] == '\0') 2919 s.Printf(" %s", valobj->GetSummaryAsCString()); 2920 else 2921 s.Printf(" %s", sum_cstr); 2922 } 2923 2924 if (use_objc) 2925 { 2926 const char *object_desc = valobj->GetObjectDescription(); 2927 if (object_desc) 2928 s.Printf(" %s\n", object_desc); 2929 else 2930 s.Printf (" [no Objective-C description available]\n"); 2931 return; 2932 } 2933 } 2934 2935 if (curr_depth < max_depth) 2936 { 2937 // We will show children for all concrete types. We won't show 2938 // pointer contents unless a pointer depth has been specified. 2939 // We won't reference contents unless the reference is the 2940 // root object (depth of zero). 2941 bool print_children = true; 2942 2943 // Use a new temporary pointer depth in case we override the 2944 // current pointer depth below... 2945 uint32_t curr_ptr_depth = ptr_depth; 2946 2947 const bool is_ptr = type_flags.Test (ClangASTContext::eTypeIsPointer); 2948 if (is_ptr || is_ref) 2949 { 2950 // We have a pointer or reference whose value is an address. 2951 // Make sure that address is not NULL 2952 AddressType ptr_address_type; 2953 if (valobj->GetPointerValue (ptr_address_type, true) == 0) 2954 print_children = false; 2955 2956 else if (is_ref && curr_depth == 0) 2957 { 2958 // If this is the root object (depth is zero) that we are showing 2959 // and it is a reference, and no pointer depth has been supplied 2960 // print out what it references. Don't do this at deeper depths 2961 // otherwise we can end up with infinite recursion... 2962 curr_ptr_depth = 1; 2963 } 2964 2965 if (curr_ptr_depth == 0) 2966 print_children = false; 2967 } 2968 2969 if (print_children && (!entry || entry->DoesPrintChildren() || !sum_cstr)) 2970 { 2971 ValueObjectSP synth_valobj = valobj->GetSyntheticValue(use_synth ? 2972 lldb::eUseSyntheticFilter : 2973 lldb::eNoSyntheticFilter); 2974 uint32_t num_children = synth_valobj->GetNumChildren(); 2975 bool print_dotdotdot = false; 2976 if (num_children) 2977 { 2978 if (flat_output) 2979 { 2980 if (print_valobj) 2981 s.EOL(); 2982 } 2983 else 2984 { 2985 if (print_valobj) 2986 s.PutCString(is_ref ? ": {\n" : " {\n"); 2987 s.IndentMore(); 2988 } 2989 2990 uint32_t max_num_children = valobj->GetUpdatePoint().GetTargetSP()->GetMaximumNumberOfChildrenToDisplay(); 2991 2992 if (num_children > max_num_children && !ignore_cap) 2993 { 2994 num_children = max_num_children; 2995 print_dotdotdot = true; 2996 } 2997 2998 for (uint32_t idx=0; idx<num_children; ++idx) 2999 { 3000 ValueObjectSP child_sp(synth_valobj->GetChildAtIndex(idx, true)); 3001 if (child_sp.get()) 3002 { 3003 DumpValueObject (s, 3004 child_sp.get(), 3005 NULL, 3006 (is_ptr || is_ref) ? curr_ptr_depth - 1 : curr_ptr_depth, 3007 curr_depth + 1, 3008 max_depth, 3009 show_types, 3010 show_location, 3011 false, 3012 use_dynamic, 3013 use_synth, 3014 true, 3015 flat_output, 3016 omit_summary_depth > 1 ? omit_summary_depth - 1 : 0, 3017 ignore_cap); 3018 } 3019 } 3020 3021 if (!flat_output) 3022 { 3023 if (print_dotdotdot) 3024 { 3025 valobj->GetUpdatePoint().GetTargetSP()->GetDebugger().GetCommandInterpreter().ChildrenTruncated(); 3026 s.Indent("...\n"); 3027 } 3028 s.IndentLess(); 3029 s.Indent("}\n"); 3030 } 3031 } 3032 else if (has_children) 3033 { 3034 // Aggregate, no children... 3035 if (print_valobj) 3036 s.PutCString(" {}\n"); 3037 } 3038 else 3039 { 3040 if (print_valobj) 3041 s.EOL(); 3042 } 3043 3044 } 3045 else 3046 { 3047 s.EOL(); 3048 } 3049 } 3050 else 3051 { 3052 if (has_children && print_valobj) 3053 { 3054 s.PutCString("{...}\n"); 3055 } 3056 } 3057 } 3058 } 3059} 3060 3061 3062ValueObjectSP 3063ValueObject::CreateConstantValue (const ConstString &name) 3064{ 3065 ValueObjectSP valobj_sp; 3066 3067 if (UpdateValueIfNeeded(false) && m_error.Success()) 3068 { 3069 ExecutionContextScope *exe_scope = GetExecutionContextScope(); 3070 if (exe_scope) 3071 { 3072 ExecutionContext exe_ctx; 3073 exe_scope->CalculateExecutionContext(exe_ctx); 3074 3075 clang::ASTContext *ast = GetClangAST (); 3076 3077 DataExtractor data; 3078 data.SetByteOrder (m_data.GetByteOrder()); 3079 data.SetAddressByteSize(m_data.GetAddressByteSize()); 3080 3081 m_error = m_value.GetValueAsData (&exe_ctx, ast, data, 0, GetModule()); 3082 3083 valobj_sp = ValueObjectConstResult::Create (exe_scope, 3084 ast, 3085 GetClangType(), 3086 name, 3087 data); 3088 } 3089 } 3090 3091 if (!valobj_sp) 3092 { 3093 valobj_sp = ValueObjectConstResult::Create (NULL, m_error); 3094 } 3095 return valobj_sp; 3096} 3097 3098lldb::ValueObjectSP 3099ValueObject::Dereference (Error &error) 3100{ 3101 if (m_deref_valobj) 3102 return m_deref_valobj->GetSP(); 3103 3104 const bool is_pointer_type = IsPointerType(); 3105 if (is_pointer_type) 3106 { 3107 bool omit_empty_base_classes = true; 3108 bool ignore_array_bounds = false; 3109 3110 std::string child_name_str; 3111 uint32_t child_byte_size = 0; 3112 int32_t child_byte_offset = 0; 3113 uint32_t child_bitfield_bit_size = 0; 3114 uint32_t child_bitfield_bit_offset = 0; 3115 bool child_is_base_class = false; 3116 bool child_is_deref_of_parent = false; 3117 const bool transparent_pointers = false; 3118 clang::ASTContext *clang_ast = GetClangAST(); 3119 clang_type_t clang_type = GetClangType(); 3120 clang_type_t child_clang_type; 3121 3122 ExecutionContext exe_ctx; 3123 GetExecutionContextScope()->CalculateExecutionContext (exe_ctx); 3124 3125 child_clang_type = ClangASTContext::GetChildClangTypeAtIndex (&exe_ctx, 3126 clang_ast, 3127 GetName().GetCString(), 3128 clang_type, 3129 0, 3130 transparent_pointers, 3131 omit_empty_base_classes, 3132 ignore_array_bounds, 3133 child_name_str, 3134 child_byte_size, 3135 child_byte_offset, 3136 child_bitfield_bit_size, 3137 child_bitfield_bit_offset, 3138 child_is_base_class, 3139 child_is_deref_of_parent); 3140 if (child_clang_type && child_byte_size) 3141 { 3142 ConstString child_name; 3143 if (!child_name_str.empty()) 3144 child_name.SetCString (child_name_str.c_str()); 3145 3146 m_deref_valobj = new ValueObjectChild (*this, 3147 clang_ast, 3148 child_clang_type, 3149 child_name, 3150 child_byte_size, 3151 child_byte_offset, 3152 child_bitfield_bit_size, 3153 child_bitfield_bit_offset, 3154 child_is_base_class, 3155 child_is_deref_of_parent); 3156 } 3157 } 3158 3159 if (m_deref_valobj) 3160 { 3161 error.Clear(); 3162 return m_deref_valobj->GetSP(); 3163 } 3164 else 3165 { 3166 StreamString strm; 3167 GetExpressionPath(strm, true); 3168 3169 if (is_pointer_type) 3170 error.SetErrorStringWithFormat("dereference failed: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str()); 3171 else 3172 error.SetErrorStringWithFormat("not a pointer type: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str()); 3173 return ValueObjectSP(); 3174 } 3175} 3176 3177lldb::ValueObjectSP 3178ValueObject::AddressOf (Error &error) 3179{ 3180 if (m_addr_of_valobj_sp) 3181 return m_addr_of_valobj_sp; 3182 3183 AddressType address_type = eAddressTypeInvalid; 3184 const bool scalar_is_load_address = false; 3185 lldb::addr_t addr = GetAddressOf (address_type, scalar_is_load_address); 3186 error.Clear(); 3187 if (addr != LLDB_INVALID_ADDRESS) 3188 { 3189 switch (address_type) 3190 { 3191 default: 3192 case eAddressTypeInvalid: 3193 { 3194 StreamString expr_path_strm; 3195 GetExpressionPath(expr_path_strm, true); 3196 error.SetErrorStringWithFormat("'%s' is not in memory", expr_path_strm.GetString().c_str()); 3197 } 3198 break; 3199 3200 case eAddressTypeFile: 3201 case eAddressTypeLoad: 3202 case eAddressTypeHost: 3203 { 3204 clang::ASTContext *ast = GetClangAST(); 3205 clang_type_t clang_type = GetClangType(); 3206 if (ast && clang_type) 3207 { 3208 std::string name (1, '&'); 3209 name.append (m_name.AsCString("")); 3210 m_addr_of_valobj_sp = ValueObjectConstResult::Create (GetExecutionContextScope(), 3211 ast, 3212 ClangASTContext::CreatePointerType (ast, clang_type), 3213 ConstString (name.c_str()), 3214 addr, 3215 eAddressTypeInvalid, 3216 m_data.GetAddressByteSize()); 3217 } 3218 } 3219 break; 3220 } 3221 } 3222 return m_addr_of_valobj_sp; 3223} 3224 3225 3226lldb::ValueObjectSP 3227ValueObject::CastPointerType (const char *name, ClangASTType &clang_ast_type) 3228{ 3229 lldb::ValueObjectSP valobj_sp; 3230 AddressType address_type; 3231 const bool scalar_is_load_address = true; 3232 lldb::addr_t ptr_value = GetPointerValue (address_type, scalar_is_load_address); 3233 3234 if (ptr_value != LLDB_INVALID_ADDRESS) 3235 { 3236 Address ptr_addr (NULL, ptr_value); 3237 3238 valobj_sp = ValueObjectMemory::Create (GetExecutionContextScope(), 3239 name, 3240 ptr_addr, 3241 clang_ast_type); 3242 } 3243 return valobj_sp; 3244} 3245 3246lldb::ValueObjectSP 3247ValueObject::CastPointerType (const char *name, TypeSP &type_sp) 3248{ 3249 lldb::ValueObjectSP valobj_sp; 3250 AddressType address_type; 3251 const bool scalar_is_load_address = true; 3252 lldb::addr_t ptr_value = GetPointerValue (address_type, scalar_is_load_address); 3253 3254 if (ptr_value != LLDB_INVALID_ADDRESS) 3255 { 3256 Address ptr_addr (NULL, ptr_value); 3257 3258 valobj_sp = ValueObjectMemory::Create (GetExecutionContextScope(), 3259 name, 3260 ptr_addr, 3261 type_sp); 3262 } 3263 return valobj_sp; 3264} 3265 3266ValueObject::EvaluationPoint::EvaluationPoint () : 3267 m_thread_id (LLDB_INVALID_UID), 3268 m_mod_id () 3269{ 3270} 3271 3272ValueObject::EvaluationPoint::EvaluationPoint (ExecutionContextScope *exe_scope, bool use_selected): 3273 m_needs_update (true), 3274 m_first_update (true), 3275 m_thread_id (LLDB_INVALID_THREAD_ID), 3276 m_mod_id () 3277 3278{ 3279 ExecutionContext exe_ctx; 3280 ExecutionContextScope *computed_exe_scope = exe_scope; // If use_selected is true, we may find a better scope, 3281 // and if so we want to cache that not the original. 3282 if (exe_scope) 3283 exe_scope->CalculateExecutionContext(exe_ctx); 3284 if (exe_ctx.target != NULL) 3285 { 3286 m_target_sp = exe_ctx.target->GetSP(); 3287 3288 if (exe_ctx.process == NULL) 3289 m_process_sp = exe_ctx.target->GetProcessSP(); 3290 else 3291 m_process_sp = exe_ctx.process->GetSP(); 3292 3293 if (m_process_sp != NULL) 3294 { 3295 m_mod_id = m_process_sp->GetModID(); 3296 3297 Thread *thread = NULL; 3298 3299 if (exe_ctx.thread == NULL) 3300 { 3301 if (use_selected) 3302 { 3303 thread = m_process_sp->GetThreadList().GetSelectedThread().get(); 3304 if (thread) 3305 computed_exe_scope = thread; 3306 } 3307 } 3308 else 3309 thread = exe_ctx.thread; 3310 3311 if (thread != NULL) 3312 { 3313 m_thread_id = thread->GetIndexID(); 3314 if (exe_ctx.frame == NULL) 3315 { 3316 if (use_selected) 3317 { 3318 StackFrame *frame = exe_ctx.thread->GetSelectedFrame().get(); 3319 if (frame) 3320 { 3321 m_stack_id = frame->GetStackID(); 3322 computed_exe_scope = frame; 3323 } 3324 } 3325 } 3326 else 3327 m_stack_id = exe_ctx.frame->GetStackID(); 3328 } 3329 } 3330 } 3331 m_exe_scope = computed_exe_scope; 3332} 3333 3334ValueObject::EvaluationPoint::EvaluationPoint (const ValueObject::EvaluationPoint &rhs) : 3335 m_exe_scope (rhs.m_exe_scope), 3336 m_needs_update(true), 3337 m_first_update(true), 3338 m_target_sp (rhs.m_target_sp), 3339 m_process_sp (rhs.m_process_sp), 3340 m_thread_id (rhs.m_thread_id), 3341 m_stack_id (rhs.m_stack_id), 3342 m_mod_id () 3343{ 3344} 3345 3346ValueObject::EvaluationPoint::~EvaluationPoint () 3347{ 3348} 3349 3350ExecutionContextScope * 3351ValueObject::EvaluationPoint::GetExecutionContextScope () 3352{ 3353 // We have to update before giving out the scope, or we could be handing out stale pointers. 3354 SyncWithProcessState(); 3355 3356 return m_exe_scope; 3357} 3358 3359// This function checks the EvaluationPoint against the current process state. If the current 3360// state matches the evaluation point, or the evaluation point is already invalid, then we return 3361// false, meaning "no change". If the current state is different, we update our state, and return 3362// true meaning "yes, change". If we did see a change, we also set m_needs_update to true, so 3363// future calls to NeedsUpdate will return true. 3364 3365bool 3366ValueObject::EvaluationPoint::SyncWithProcessState() 3367{ 3368 // If we don't have a process nothing can change. 3369 if (!m_process_sp) 3370 { 3371 m_exe_scope = m_target_sp.get(); 3372 return false; 3373 } 3374 3375 // If our stop id is the current stop ID, nothing has changed: 3376 ProcessModID current_mod_id = m_process_sp->GetModID(); 3377 3378 // If the current stop id is 0, either we haven't run yet, or the process state has been cleared. 3379 // In either case, we aren't going to be able to sync with the process state. 3380 if (current_mod_id.GetStopID() == 0) 3381 { 3382 m_exe_scope = m_target_sp.get(); 3383 return false; 3384 } 3385 3386 if (m_mod_id.IsValid()) 3387 { 3388 if (m_mod_id == current_mod_id) 3389 { 3390 // Everything is already up to date in this object, no need do 3391 // update the execution context scope. 3392 return false; 3393 } 3394 m_mod_id = current_mod_id; 3395 m_needs_update = true; 3396 } 3397 m_exe_scope = m_process_sp.get(); 3398 3399 // Something has changed, so we will return true. Now make sure the thread & frame still exist, and if either 3400 // doesn't, mark ourselves as invalid. 3401 3402 if (m_thread_id != LLDB_INVALID_THREAD_ID) 3403 { 3404 Thread *our_thread = m_process_sp->GetThreadList().FindThreadByIndexID (m_thread_id).get(); 3405 if (our_thread == NULL) 3406 { 3407 SetInvalid(); 3408 } 3409 else 3410 { 3411 m_exe_scope = our_thread; 3412 3413 if (m_stack_id.IsValid()) 3414 { 3415 StackFrame *our_frame = our_thread->GetFrameWithStackID (m_stack_id).get(); 3416 if (our_frame == NULL) 3417 SetInvalid(); 3418 else 3419 m_exe_scope = our_frame; 3420 } 3421 } 3422 } 3423 return true; 3424} 3425 3426void 3427ValueObject::EvaluationPoint::SetUpdated () 3428{ 3429 // this will update the execution context scope and the m_mod_id 3430 SyncWithProcessState(); 3431 m_first_update = false; 3432 m_needs_update = false; 3433} 3434 3435 3436bool 3437ValueObject::EvaluationPoint::SetContext (ExecutionContextScope *exe_scope) 3438{ 3439 if (!IsValid()) 3440 return false; 3441 3442 bool needs_update = false; 3443 m_exe_scope = NULL; 3444 3445 // The target has to be non-null, and the 3446 Target *target = exe_scope->CalculateTarget(); 3447 if (target != NULL) 3448 { 3449 Target *old_target = m_target_sp.get(); 3450 assert (target == old_target); 3451 Process *process = exe_scope->CalculateProcess(); 3452 if (process != NULL) 3453 { 3454 // FOR NOW - assume you can't update variable objects across process boundaries. 3455 Process *old_process = m_process_sp.get(); 3456 assert (process == old_process); 3457 ProcessModID current_mod_id = process->GetModID(); 3458 if (m_mod_id != current_mod_id) 3459 { 3460 needs_update = true; 3461 m_mod_id = current_mod_id; 3462 } 3463 // See if we're switching the thread or stack context. If no thread is given, this is 3464 // being evaluated in a global context. 3465 Thread *thread = exe_scope->CalculateThread(); 3466 if (thread != NULL) 3467 { 3468 lldb::user_id_t new_thread_index = thread->GetIndexID(); 3469 if (new_thread_index != m_thread_id) 3470 { 3471 needs_update = true; 3472 m_thread_id = new_thread_index; 3473 m_stack_id.Clear(); 3474 } 3475 3476 StackFrame *new_frame = exe_scope->CalculateStackFrame(); 3477 if (new_frame != NULL) 3478 { 3479 if (new_frame->GetStackID() != m_stack_id) 3480 { 3481 needs_update = true; 3482 m_stack_id = new_frame->GetStackID(); 3483 } 3484 } 3485 else 3486 { 3487 m_stack_id.Clear(); 3488 needs_update = true; 3489 } 3490 } 3491 else 3492 { 3493 // If this had been given a thread, and now there is none, we should update. 3494 // Otherwise we don't have to do anything. 3495 if (m_thread_id != LLDB_INVALID_UID) 3496 { 3497 m_thread_id = LLDB_INVALID_UID; 3498 m_stack_id.Clear(); 3499 needs_update = true; 3500 } 3501 } 3502 } 3503 else 3504 { 3505 // If there is no process, then we don't need to update anything. 3506 // But if we're switching from having a process to not, we should try to update. 3507 if (m_process_sp.get() != NULL) 3508 { 3509 needs_update = true; 3510 m_process_sp.reset(); 3511 m_thread_id = LLDB_INVALID_UID; 3512 m_stack_id.Clear(); 3513 } 3514 } 3515 } 3516 else 3517 { 3518 // If there's no target, nothing can change so we don't need to update anything. 3519 // But if we're switching from having a target to not, we should try to update. 3520 if (m_target_sp.get() != NULL) 3521 { 3522 needs_update = true; 3523 m_target_sp.reset(); 3524 m_process_sp.reset(); 3525 m_thread_id = LLDB_INVALID_UID; 3526 m_stack_id.Clear(); 3527 } 3528 } 3529 if (!m_needs_update) 3530 m_needs_update = needs_update; 3531 3532 return needs_update; 3533} 3534 3535void 3536ValueObject::ClearUserVisibleData() 3537{ 3538 m_location_str.clear(); 3539 m_value_str.clear(); 3540 m_summary_str.clear(); 3541 m_object_desc_str.clear(); 3542} 3543