1 //===-- Type.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 // Other libraries and framework includes 11 12 #include "lldb/Core/DataExtractor.h" 13 #include "lldb/Core/DataBufferHeap.h" 14 #include "lldb/Core/Module.h" 15 #include "lldb/Core/Scalar.h" 16 #include "lldb/Core/StreamString.h" 17 18 #include "lldb/Symbol/ClangASTType.h" 19 #include "lldb/Symbol/ClangASTContext.h" 20 #include "lldb/Symbol/ObjectFile.h" 21 #include "lldb/Symbol/SymbolContextScope.h" 22 #include "lldb/Symbol/SymbolFile.h" 23 #include "lldb/Symbol/SymbolVendor.h" 24 #include "lldb/Symbol/Type.h" 25 #include "lldb/Symbol/TypeList.h" 26 27 #include "lldb/Target/ExecutionContext.h" 28 #include "lldb/Target/Process.h" 29 #include "lldb/Target/Target.h" 30 31 #include "llvm/ADT/StringRef.h" 32 33 using namespace lldb; 34 using namespace lldb_private; 35 36 Type * 37 SymbolFileType::GetType () 38 { 39 if (!m_type_sp) 40 { 41 Type *resolved_type = m_symbol_file.ResolveTypeUID (GetID()); 42 if (resolved_type) 43 m_type_sp = resolved_type->shared_from_this(); 44 } 45 return m_type_sp.get(); 46 } 47 48 49 Type::Type 50 ( 51 lldb::user_id_t uid, 52 SymbolFile* symbol_file, 53 const ConstString &name, 54 uint64_t byte_size, 55 SymbolContextScope *context, 56 user_id_t encoding_uid, 57 EncodingDataType encoding_uid_type, 58 const Declaration& decl, 59 clang_type_t clang_type, 60 ResolveState clang_type_resolve_state 61 ) : 62 std::enable_shared_from_this<Type> (), 63 UserID (uid), 64 m_name (name), 65 m_symbol_file (symbol_file), 66 m_context (context), 67 m_encoding_type (NULL), 68 m_encoding_uid (encoding_uid), 69 m_encoding_uid_type (encoding_uid_type), 70 m_byte_size (byte_size), 71 m_decl (decl), 72 m_clang_type (clang_type) 73 { 74 m_flags.clang_type_resolve_state = (clang_type ? clang_type_resolve_state : eResolveStateUnresolved); 75 m_flags.is_complete_objc_class = false; 76 } 77 78 Type::Type () : 79 std::enable_shared_from_this<Type> (), 80 UserID (0), 81 m_name ("<INVALID TYPE>"), 82 m_symbol_file (NULL), 83 m_context (NULL), 84 m_encoding_type (NULL), 85 m_encoding_uid (LLDB_INVALID_UID), 86 m_encoding_uid_type (eEncodingInvalid), 87 m_byte_size (0), 88 m_decl (), 89 m_clang_type (NULL) 90 { 91 m_flags.clang_type_resolve_state = eResolveStateUnresolved; 92 m_flags.is_complete_objc_class = false; 93 } 94 95 96 Type::Type (const Type &rhs) : 97 std::enable_shared_from_this<Type> (rhs), 98 UserID (rhs), 99 m_name (rhs.m_name), 100 m_symbol_file (rhs.m_symbol_file), 101 m_context (rhs.m_context), 102 m_encoding_type (rhs.m_encoding_type), 103 m_encoding_uid (rhs.m_encoding_uid), 104 m_encoding_uid_type (rhs.m_encoding_uid_type), 105 m_byte_size (rhs.m_byte_size), 106 m_decl (rhs.m_decl), 107 m_clang_type (rhs.m_clang_type), 108 m_flags (rhs.m_flags) 109 { 110 } 111 112 const Type& 113 Type::operator= (const Type& rhs) 114 { 115 if (this != &rhs) 116 { 117 } 118 return *this; 119 } 120 121 122 void 123 Type::GetDescription (Stream *s, lldb::DescriptionLevel level, bool show_name) 124 { 125 *s << "id = " << (const UserID&)*this; 126 127 // Call the name accessor to make sure we resolve the type name 128 if (show_name) 129 { 130 const ConstString &type_name = GetName(); 131 if (type_name) 132 { 133 *s << ", name = \"" << type_name << '"'; 134 ConstString qualified_type_name (GetQualifiedName()); 135 if (qualified_type_name != type_name) 136 { 137 *s << ", qualified = \"" << qualified_type_name << '"'; 138 } 139 } 140 } 141 142 // Call the get byte size accesor so we resolve our byte size 143 if (GetByteSize()) 144 s->Printf(", byte-size = %" PRIu64, m_byte_size); 145 bool show_fullpaths = (level == lldb::eDescriptionLevelVerbose); 146 m_decl.Dump(s, show_fullpaths); 147 148 if (m_clang_type) 149 { 150 *s << ", clang_type = \""; 151 ClangASTType::DumpTypeDescription (GetClangAST(), m_clang_type, s); 152 *s << '"'; 153 } 154 else if (m_encoding_uid != LLDB_INVALID_UID) 155 { 156 s->Printf(", type_uid = 0x%8.8" PRIx64, m_encoding_uid); 157 switch (m_encoding_uid_type) 158 { 159 case eEncodingInvalid: break; 160 case eEncodingIsUID: s->PutCString(" (unresolved type)"); break; 161 case eEncodingIsConstUID: s->PutCString(" (unresolved const type)"); break; 162 case eEncodingIsRestrictUID: s->PutCString(" (unresolved restrict type)"); break; 163 case eEncodingIsVolatileUID: s->PutCString(" (unresolved volatile type)"); break; 164 case eEncodingIsTypedefUID: s->PutCString(" (unresolved typedef)"); break; 165 case eEncodingIsPointerUID: s->PutCString(" (unresolved pointer)"); break; 166 case eEncodingIsLValueReferenceUID: s->PutCString(" (unresolved L value reference)"); break; 167 case eEncodingIsRValueReferenceUID: s->PutCString(" (unresolved R value reference)"); break; 168 case eEncodingIsSyntheticUID: s->PutCString(" (synthetic type)"); break; 169 } 170 } 171 } 172 173 174 void 175 Type::Dump (Stream *s, bool show_context) 176 { 177 s->Printf("%p: ", this); 178 s->Indent(); 179 *s << "Type" << (const UserID&)*this << ' '; 180 if (m_name) 181 *s << ", name = \"" << m_name << "\""; 182 183 if (m_byte_size != 0) 184 s->Printf(", size = %" PRIu64, m_byte_size); 185 186 if (show_context && m_context != NULL) 187 { 188 s->PutCString(", context = ( "); 189 m_context->DumpSymbolContext(s); 190 s->PutCString(" )"); 191 } 192 193 bool show_fullpaths = false; 194 m_decl.Dump (s,show_fullpaths); 195 196 if (m_clang_type) 197 { 198 *s << ", clang_type = " << m_clang_type << ' '; 199 200 ClangASTType::DumpTypeDescription (GetClangAST(), m_clang_type, s); 201 } 202 else if (m_encoding_uid != LLDB_INVALID_UID) 203 { 204 *s << ", type_data = " << (uint64_t)m_encoding_uid; 205 switch (m_encoding_uid_type) 206 { 207 case eEncodingInvalid: break; 208 case eEncodingIsUID: s->PutCString(" (unresolved type)"); break; 209 case eEncodingIsConstUID: s->PutCString(" (unresolved const type)"); break; 210 case eEncodingIsRestrictUID: s->PutCString(" (unresolved restrict type)"); break; 211 case eEncodingIsVolatileUID: s->PutCString(" (unresolved volatile type)"); break; 212 case eEncodingIsTypedefUID: s->PutCString(" (unresolved typedef)"); break; 213 case eEncodingIsPointerUID: s->PutCString(" (unresolved pointer)"); break; 214 case eEncodingIsLValueReferenceUID: s->PutCString(" (unresolved L value reference)"); break; 215 case eEncodingIsRValueReferenceUID: s->PutCString(" (unresolved R value reference)"); break; 216 case eEncodingIsSyntheticUID: s->PutCString(" (synthetic type)"); break; 217 } 218 } 219 220 // 221 // if (m_access) 222 // s->Printf(", access = %u", m_access); 223 s->EOL(); 224 } 225 226 const ConstString & 227 Type::GetName() 228 { 229 if (!m_name) 230 { 231 if (ResolveClangType(eResolveStateForward)) 232 m_name = ClangASTType::GetConstTypeName (GetClangASTContext ().getASTContext(), m_clang_type); 233 } 234 return m_name; 235 } 236 237 void 238 Type::DumpTypeName(Stream *s) 239 { 240 GetName().Dump(s, "<invalid-type-name>"); 241 } 242 243 244 void 245 Type::DumpValue 246 ( 247 ExecutionContext *exe_ctx, 248 Stream *s, 249 const DataExtractor &data, 250 uint32_t data_byte_offset, 251 bool show_types, 252 bool show_summary, 253 bool verbose, 254 lldb::Format format 255 ) 256 { 257 if (ResolveClangType(eResolveStateForward)) 258 { 259 if (show_types) 260 { 261 s->PutChar('('); 262 if (verbose) 263 s->Printf("Type{0x%8.8" PRIx64 "} ", GetID()); 264 DumpTypeName (s); 265 s->PutCString(") "); 266 } 267 268 ClangASTType::DumpValue (GetClangAST (), 269 m_clang_type, 270 exe_ctx, 271 s, 272 format == lldb::eFormatDefault ? GetFormat() : format, 273 data, 274 data_byte_offset, 275 GetByteSize(), 276 0, // Bitfield bit size 277 0, // Bitfield bit offset 278 show_types, 279 show_summary, 280 verbose, 281 0); 282 } 283 } 284 285 Type * 286 Type::GetEncodingType () 287 { 288 if (m_encoding_type == NULL && m_encoding_uid != LLDB_INVALID_UID) 289 m_encoding_type = m_symbol_file->ResolveTypeUID(m_encoding_uid); 290 return m_encoding_type; 291 } 292 293 294 295 uint64_t 296 Type::GetByteSize() 297 { 298 if (m_byte_size == 0) 299 { 300 switch (m_encoding_uid_type) 301 { 302 case eEncodingInvalid: 303 case eEncodingIsSyntheticUID: 304 break; 305 case eEncodingIsUID: 306 case eEncodingIsConstUID: 307 case eEncodingIsRestrictUID: 308 case eEncodingIsVolatileUID: 309 case eEncodingIsTypedefUID: 310 { 311 Type *encoding_type = GetEncodingType (); 312 if (encoding_type) 313 m_byte_size = encoding_type->GetByteSize(); 314 if (m_byte_size == 0) 315 { 316 uint32_t bit_width = ClangASTType::GetClangTypeBitWidth (GetClangAST(), GetClangLayoutType()); 317 m_byte_size = (bit_width + 7 ) / 8; 318 } 319 } 320 break; 321 322 // If we are a pointer or reference, then this is just a pointer size; 323 case eEncodingIsPointerUID: 324 case eEncodingIsLValueReferenceUID: 325 case eEncodingIsRValueReferenceUID: 326 m_byte_size = m_symbol_file->GetClangASTContext().GetPointerBitSize() / 8; 327 break; 328 } 329 } 330 return m_byte_size; 331 } 332 333 334 uint32_t 335 Type::GetNumChildren (bool omit_empty_base_classes) 336 { 337 if (ResolveClangType(eResolveStateForward)) 338 { 339 return ClangASTContext::GetNumChildren (m_symbol_file->GetClangASTContext().getASTContext(), 340 m_clang_type, 341 omit_empty_base_classes); 342 } 343 return 0; 344 } 345 346 bool 347 Type::IsAggregateType () 348 { 349 if (ResolveClangType(eResolveStateForward)) 350 return ClangASTContext::IsAggregateType (m_clang_type); 351 return false; 352 } 353 354 lldb::TypeSP 355 Type::GetTypedefType() 356 { 357 lldb::TypeSP type_sp; 358 if (IsTypedef()) 359 { 360 Type *typedef_type = m_symbol_file->ResolveTypeUID(m_encoding_uid); 361 if (typedef_type) 362 type_sp = typedef_type->shared_from_this(); 363 } 364 return type_sp; 365 } 366 367 368 369 lldb::Format 370 Type::GetFormat () 371 { 372 // Make sure we resolve our type if it already hasn't been. 373 if (!ResolveClangType(eResolveStateForward)) 374 return lldb::eFormatInvalid; 375 return ClangASTType::GetFormat (m_clang_type); 376 } 377 378 379 380 lldb::Encoding 381 Type::GetEncoding (uint64_t &count) 382 { 383 // Make sure we resolve our type if it already hasn't been. 384 if (!ResolveClangType(eResolveStateForward)) 385 return lldb::eEncodingInvalid; 386 387 return ClangASTType::GetEncoding (m_clang_type, count); 388 } 389 390 391 392 bool 393 Type::DumpValueInMemory 394 ( 395 ExecutionContext *exe_ctx, 396 Stream *s, 397 lldb::addr_t address, 398 AddressType address_type, 399 bool show_types, 400 bool show_summary, 401 bool verbose 402 ) 403 { 404 if (address != LLDB_INVALID_ADDRESS) 405 { 406 DataExtractor data; 407 Target *target = NULL; 408 if (exe_ctx) 409 target = exe_ctx->GetTargetPtr(); 410 if (target) 411 data.SetByteOrder (target->GetArchitecture().GetByteOrder()); 412 if (ReadFromMemory (exe_ctx, address, address_type, data)) 413 { 414 DumpValue(exe_ctx, s, data, 0, show_types, show_summary, verbose); 415 return true; 416 } 417 } 418 return false; 419 } 420 421 422 bool 423 Type::ReadFromMemory (ExecutionContext *exe_ctx, lldb::addr_t addr, AddressType address_type, DataExtractor &data) 424 { 425 if (address_type == eAddressTypeFile) 426 { 427 // Can't convert a file address to anything valid without more 428 // context (which Module it came from) 429 return false; 430 } 431 432 const uint64_t byte_size = GetByteSize(); 433 if (data.GetByteSize() < byte_size) 434 { 435 lldb::DataBufferSP data_sp(new DataBufferHeap (byte_size, '\0')); 436 data.SetData(data_sp); 437 } 438 439 uint8_t* dst = (uint8_t*)data.PeekData(0, byte_size); 440 if (dst != NULL) 441 { 442 if (address_type == eAddressTypeHost) 443 { 444 // The address is an address in this process, so just copy it 445 if (addr == 0) 446 return false; 447 memcpy (dst, (uint8_t*)NULL + addr, byte_size); 448 return true; 449 } 450 else 451 { 452 if (exe_ctx) 453 { 454 Process *process = exe_ctx->GetProcessPtr(); 455 if (process) 456 { 457 Error error; 458 return exe_ctx->GetProcessPtr()->ReadMemory(addr, dst, byte_size, error) == byte_size; 459 } 460 } 461 } 462 } 463 return false; 464 } 465 466 467 bool 468 Type::WriteToMemory (ExecutionContext *exe_ctx, lldb::addr_t addr, AddressType address_type, DataExtractor &data) 469 { 470 return false; 471 } 472 473 474 TypeList* 475 Type::GetTypeList() 476 { 477 return GetSymbolFile()->GetTypeList(); 478 } 479 480 const Declaration & 481 Type::GetDeclaration () const 482 { 483 return m_decl; 484 } 485 486 bool 487 Type::ResolveClangType (ResolveState clang_type_resolve_state) 488 { 489 Type *encoding_type = NULL; 490 if (m_clang_type == NULL) 491 { 492 encoding_type = GetEncodingType(); 493 if (encoding_type) 494 { 495 switch (m_encoding_uid_type) 496 { 497 case eEncodingIsUID: 498 if (encoding_type->ResolveClangType(clang_type_resolve_state)) 499 { 500 m_clang_type = encoding_type->m_clang_type; 501 m_flags.clang_type_resolve_state = encoding_type->m_flags.clang_type_resolve_state; 502 } 503 break; 504 505 case eEncodingIsConstUID: 506 m_clang_type = ClangASTContext::AddConstModifier (encoding_type->GetClangForwardType()); 507 break; 508 509 case eEncodingIsRestrictUID: 510 m_clang_type = ClangASTContext::AddRestrictModifier (encoding_type->GetClangForwardType()); 511 break; 512 513 case eEncodingIsVolatileUID: 514 m_clang_type = ClangASTContext::AddVolatileModifier (encoding_type->GetClangForwardType()); 515 break; 516 517 case eEncodingIsTypedefUID: 518 m_clang_type = CreateClangTypedefType (this, encoding_type); 519 // Clear the name so it can get fully qualified in case the 520 // typedef is in a namespace. 521 m_name.Clear(); 522 break; 523 524 case eEncodingIsPointerUID: 525 m_clang_type = CreateClangPointerType (encoding_type); 526 break; 527 528 case eEncodingIsLValueReferenceUID: 529 m_clang_type = CreateClangLValueReferenceType (encoding_type); 530 break; 531 532 case eEncodingIsRValueReferenceUID: 533 m_clang_type = CreateClangRValueReferenceType (encoding_type); 534 break; 535 536 default: 537 assert(!"Unhandled encoding_data_type."); 538 break; 539 } 540 } 541 else 542 { 543 // We have no encoding type, return void? 544 clang_type_t void_clang_type = GetClangASTContext().GetBuiltInType_void(); 545 switch (m_encoding_uid_type) 546 { 547 case eEncodingIsUID: 548 m_clang_type = void_clang_type; 549 break; 550 551 case eEncodingIsConstUID: 552 m_clang_type = ClangASTContext::AddConstModifier (void_clang_type); 553 break; 554 555 case eEncodingIsRestrictUID: 556 m_clang_type = ClangASTContext::AddRestrictModifier (void_clang_type); 557 break; 558 559 case eEncodingIsVolatileUID: 560 m_clang_type = ClangASTContext::AddVolatileModifier (void_clang_type); 561 break; 562 563 case eEncodingIsTypedefUID: 564 m_clang_type = GetClangASTContext().CreateTypedefType (m_name.AsCString(), void_clang_type, NULL); 565 break; 566 567 case eEncodingIsPointerUID: 568 m_clang_type = GetClangASTContext().CreatePointerType (void_clang_type); 569 break; 570 571 case eEncodingIsLValueReferenceUID: 572 m_clang_type = GetClangASTContext().CreateLValueReferenceType (void_clang_type); 573 break; 574 575 case eEncodingIsRValueReferenceUID: 576 m_clang_type = GetClangASTContext().CreateRValueReferenceType (void_clang_type); 577 break; 578 579 default: 580 assert(!"Unhandled encoding_data_type."); 581 break; 582 } 583 } 584 } 585 586 // Check if we have a forward reference to a class/struct/union/enum? 587 if (m_clang_type && m_flags.clang_type_resolve_state < clang_type_resolve_state) 588 { 589 m_flags.clang_type_resolve_state = eResolveStateFull; 590 if (!ClangASTType::IsDefined (m_clang_type)) 591 { 592 // We have a forward declaration, we need to resolve it to a complete 593 // definition. 594 m_symbol_file->ResolveClangOpaqueTypeDefinition (m_clang_type); 595 } 596 } 597 598 // If we have an encoding type, then we need to make sure it is 599 // resolved appropriately. 600 if (m_encoding_uid != LLDB_INVALID_UID) 601 { 602 if (encoding_type == NULL) 603 encoding_type = GetEncodingType(); 604 if (encoding_type) 605 { 606 ResolveState encoding_clang_type_resolve_state = clang_type_resolve_state; 607 608 if (clang_type_resolve_state == eResolveStateLayout) 609 { 610 switch (m_encoding_uid_type) 611 { 612 case eEncodingIsPointerUID: 613 case eEncodingIsLValueReferenceUID: 614 case eEncodingIsRValueReferenceUID: 615 encoding_clang_type_resolve_state = eResolveStateForward; 616 break; 617 default: 618 break; 619 } 620 } 621 encoding_type->ResolveClangType (encoding_clang_type_resolve_state); 622 } 623 } 624 return m_clang_type != NULL; 625 } 626 uint32_t 627 Type::GetEncodingMask () 628 { 629 uint32_t encoding_mask = 1u << m_encoding_uid_type; 630 Type *encoding_type = GetEncodingType(); 631 assert (encoding_type != this); 632 if (encoding_type) 633 encoding_mask |= encoding_type->GetEncodingMask (); 634 return encoding_mask; 635 } 636 637 clang_type_t 638 Type::GetClangFullType () 639 { 640 ResolveClangType(eResolveStateFull); 641 return m_clang_type; 642 } 643 644 clang_type_t 645 Type::GetClangLayoutType () 646 { 647 ResolveClangType(eResolveStateLayout); 648 return m_clang_type; 649 } 650 651 clang_type_t 652 Type::GetClangForwardType () 653 { 654 ResolveClangType (eResolveStateForward); 655 return m_clang_type; 656 } 657 658 clang::ASTContext * 659 Type::GetClangAST () 660 { 661 return GetClangASTContext().getASTContext(); 662 } 663 664 ClangASTContext & 665 Type::GetClangASTContext () 666 { 667 return m_symbol_file->GetClangASTContext(); 668 } 669 670 int 671 Type::Compare(const Type &a, const Type &b) 672 { 673 // Just compare the UID values for now... 674 lldb::user_id_t a_uid = a.GetID(); 675 lldb::user_id_t b_uid = b.GetID(); 676 if (a_uid < b_uid) 677 return -1; 678 if (a_uid > b_uid) 679 return 1; 680 return 0; 681 // if (a.getQualType() == b.getQualType()) 682 // return 0; 683 } 684 685 686 void * 687 Type::CreateClangPointerType (Type *type) 688 { 689 assert(type); 690 return GetClangASTContext().CreatePointerType(type->GetClangForwardType()); 691 } 692 693 void * 694 Type::CreateClangTypedefType (Type *typedef_type, Type *base_type) 695 { 696 assert(typedef_type && base_type); 697 return GetClangASTContext().CreateTypedefType (typedef_type->GetName().AsCString(), 698 base_type->GetClangForwardType(), 699 typedef_type->GetSymbolFile()->GetClangDeclContextContainingTypeUID(typedef_type->GetID())); 700 } 701 702 void * 703 Type::CreateClangLValueReferenceType (Type *type) 704 { 705 assert(type); 706 return GetClangASTContext().CreateLValueReferenceType(type->GetClangForwardType()); 707 } 708 709 void * 710 Type::CreateClangRValueReferenceType (Type *type) 711 { 712 assert(type); 713 return GetClangASTContext().CreateRValueReferenceType (type->GetClangForwardType()); 714 } 715 716 bool 717 Type::IsRealObjCClass() 718 { 719 // For now we are just skipping ObjC classes that get made by hand from the runtime, because 720 // those don't have any information. We could extend this to only return true for "full 721 // definitions" if we can figure that out. 722 723 if (ClangASTContext::IsObjCClassType(m_clang_type) && GetByteSize() != 0) 724 return true; 725 else 726 return false; 727 } 728 729 ConstString 730 Type::GetQualifiedName () 731 { 732 ConstString qualified_name (ClangASTType::GetTypeNameForOpaqueQualType (GetClangASTContext ().getASTContext(), GetClangForwardType()).c_str()); 733 return qualified_name; 734 } 735 736 737 bool 738 Type::GetTypeScopeAndBasename (const char* &name_cstr, 739 std::string &scope, 740 std::string &basename, 741 TypeClass &type_class) 742 { 743 // Protect against null c string. 744 745 type_class = eTypeClassAny; 746 747 if (name_cstr && name_cstr[0]) 748 { 749 llvm::StringRef name_strref(name_cstr); 750 if (name_strref.startswith("struct ")) 751 { 752 name_cstr += 7; 753 type_class = eTypeClassStruct; 754 } 755 else if (name_strref.startswith("class ")) 756 { 757 name_cstr += 6; 758 type_class = eTypeClassClass; 759 } 760 else if (name_strref.startswith("union ")) 761 { 762 name_cstr += 6; 763 type_class = eTypeClassUnion; 764 } 765 else if (name_strref.startswith("enum ")) 766 { 767 name_cstr += 5; 768 type_class = eTypeClassEnumeration; 769 } 770 else if (name_strref.startswith("typedef ")) 771 { 772 name_cstr += 8; 773 type_class = eTypeClassTypedef; 774 } 775 const char *basename_cstr = name_cstr; 776 const char* namespace_separator = ::strstr (basename_cstr, "::"); 777 if (namespace_separator) 778 { 779 const char* template_arg_char = ::strchr (basename_cstr, '<'); 780 while (namespace_separator != NULL) 781 { 782 if (template_arg_char && namespace_separator > template_arg_char) // but namespace'd template arguments are still good to go 783 break; 784 basename_cstr = namespace_separator + 2; 785 namespace_separator = strstr(basename_cstr, "::"); 786 } 787 if (basename_cstr > name_cstr) 788 { 789 scope.assign (name_cstr, basename_cstr - name_cstr); 790 basename.assign (basename_cstr); 791 return true; 792 } 793 } 794 } 795 return false; 796 } 797 798 799 800 801 TypeAndOrName::TypeAndOrName () : m_type_sp(), m_type_name() 802 { 803 804 } 805 806 TypeAndOrName::TypeAndOrName (TypeSP &in_type_sp) : m_type_sp(in_type_sp) 807 { 808 if (in_type_sp) 809 m_type_name = in_type_sp->GetName(); 810 } 811 812 TypeAndOrName::TypeAndOrName (const char *in_type_str) : m_type_name(in_type_str) 813 { 814 } 815 816 TypeAndOrName::TypeAndOrName (const TypeAndOrName &rhs) : m_type_sp (rhs.m_type_sp), m_type_name (rhs.m_type_name) 817 { 818 819 } 820 821 TypeAndOrName::TypeAndOrName (ConstString &in_type_const_string) : m_type_name (in_type_const_string) 822 { 823 } 824 825 TypeAndOrName & 826 TypeAndOrName::operator= (const TypeAndOrName &rhs) 827 { 828 if (this != &rhs) 829 { 830 m_type_name = rhs.m_type_name; 831 m_type_sp = rhs.m_type_sp; 832 } 833 return *this; 834 } 835 836 bool 837 TypeAndOrName::operator==(const TypeAndOrName &other) const 838 { 839 if (m_type_sp != other.m_type_sp) 840 return false; 841 if (m_type_name != other.m_type_name) 842 return false; 843 return true; 844 } 845 846 bool 847 TypeAndOrName::operator!=(const TypeAndOrName &other) const 848 { 849 if (m_type_sp != other.m_type_sp) 850 return true; 851 if (m_type_name != other.m_type_name) 852 return true; 853 return false; 854 } 855 856 ConstString 857 TypeAndOrName::GetName () const 858 { 859 if (m_type_sp) 860 return m_type_sp->GetName(); 861 else 862 return m_type_name; 863 } 864 865 void 866 TypeAndOrName::SetName (const ConstString &type_name) 867 { 868 m_type_name = type_name; 869 } 870 871 void 872 TypeAndOrName::SetName (const char *type_name_cstr) 873 { 874 m_type_name.SetCString (type_name_cstr); 875 } 876 877 void 878 TypeAndOrName::SetTypeSP (lldb::TypeSP type_sp) 879 { 880 m_type_sp = type_sp; 881 if (type_sp) 882 m_type_name = type_sp->GetName(); 883 } 884 885 bool 886 TypeAndOrName::IsEmpty() 887 { 888 if (m_type_name || m_type_sp) 889 return false; 890 else 891 return true; 892 } 893 894 void 895 TypeAndOrName::Clear () 896 { 897 m_type_name.Clear(); 898 m_type_sp.reset(); 899 } 900 901 bool 902 TypeAndOrName::HasName () 903 { 904 return (bool)m_type_name; 905 } 906 907 bool 908 TypeAndOrName::HasTypeSP () 909 { 910 return m_type_sp.get() != NULL; 911 } 912 913 TypeImpl::TypeImpl(const lldb_private::ClangASTType& clang_ast_type) : 914 m_clang_ast_type(clang_ast_type.GetASTContext(), clang_ast_type.GetOpaqueQualType()), 915 m_type_sp() 916 {} 917 918 TypeImpl::TypeImpl(const lldb::TypeSP& type) : 919 m_clang_ast_type(type->GetClangAST(), type->GetClangFullType()), 920 m_type_sp(type) 921 { 922 } 923 924 void 925 TypeImpl::SetType (const lldb::TypeSP &type_sp) 926 { 927 if (type_sp) 928 { 929 m_clang_ast_type.SetClangType (type_sp->GetClangAST(), type_sp->GetClangFullType()); 930 m_type_sp = type_sp; 931 } 932 else 933 { 934 m_clang_ast_type.Clear(); 935 m_type_sp.reset(); 936 } 937 } 938 939 TypeImpl& 940 TypeImpl::operator = (const TypeImpl& rhs) 941 { 942 if (*this != rhs) 943 { 944 m_clang_ast_type = rhs.m_clang_ast_type; 945 m_type_sp = rhs.m_type_sp; 946 } 947 return *this; 948 } 949 950 clang::ASTContext* 951 TypeImpl::GetASTContext() 952 { 953 if (!IsValid()) 954 return NULL; 955 956 return m_clang_ast_type.GetASTContext(); 957 } 958 959 lldb::clang_type_t 960 TypeImpl::GetOpaqueQualType() 961 { 962 if (!IsValid()) 963 return NULL; 964 965 return m_clang_ast_type.GetOpaqueQualType(); 966 } 967 968 bool 969 TypeImpl::GetDescription (lldb_private::Stream &strm, 970 lldb::DescriptionLevel description_level) 971 { 972 if (m_clang_ast_type.IsValid()) 973 { 974 ClangASTType::DumpTypeDescription (m_clang_ast_type.GetASTContext(), 975 m_clang_ast_type.GetOpaqueQualType(), 976 &strm); 977 } 978 else 979 { 980 strm.PutCString ("No value"); 981 } 982 return true; 983 } 984 985