1 //===-- Type.h --------------------------------------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #ifndef LLDB_SYMBOL_TYPE_H 10 #define LLDB_SYMBOL_TYPE_H 11 12 #include "lldb/Core/Declaration.h" 13 #include "lldb/Symbol/CompilerDecl.h" 14 #include "lldb/Symbol/CompilerType.h" 15 #include "lldb/Utility/ConstString.h" 16 #include "lldb/Utility/UserID.h" 17 #include "lldb/lldb-private.h" 18 19 #include "llvm/ADT/APSInt.h" 20 21 #include <set> 22 23 namespace lldb_private { 24 25 /// CompilerContext allows an array of these items to be passed to perform 26 /// detailed lookups in SymbolVendor and SymbolFile functions. 27 struct CompilerContext { CompilerContextCompilerContext28 CompilerContext(CompilerContextKind t, ConstString n) : kind(t), name(n) {} 29 30 bool operator==(const CompilerContext &rhs) const { 31 return kind == rhs.kind && name == rhs.name; 32 } 33 bool operator!=(const CompilerContext &rhs) const { return !(*this == rhs); } 34 35 void Dump() const; 36 37 CompilerContextKind kind; 38 ConstString name; 39 }; 40 41 /// Match \p context_chain against \p pattern, which may contain "Any" 42 /// kinds. The \p context_chain should *not* contain any "Any" kinds. 43 bool contextMatches(llvm::ArrayRef<CompilerContext> context_chain, 44 llvm::ArrayRef<CompilerContext> pattern); 45 46 class SymbolFileType : public std::enable_shared_from_this<SymbolFileType>, 47 public UserID { 48 public: SymbolFileType(SymbolFile & symbol_file,lldb::user_id_t uid)49 SymbolFileType(SymbolFile &symbol_file, lldb::user_id_t uid) 50 : UserID(uid), m_symbol_file(symbol_file) {} 51 52 SymbolFileType(SymbolFile &symbol_file, const lldb::TypeSP &type_sp); 53 54 ~SymbolFileType() = default; 55 56 Type *operator->() { return GetType(); } 57 58 Type *GetType(); GetSymbolFile()59 SymbolFile &GetSymbolFile() const { return m_symbol_file; } 60 61 protected: 62 SymbolFile &m_symbol_file; 63 lldb::TypeSP m_type_sp; 64 }; 65 66 class Type : public std::enable_shared_from_this<Type>, public UserID { 67 public: 68 enum EncodingDataType { 69 eEncodingInvalid, 70 eEncodingIsUID, ///< This type is the type whose UID is m_encoding_uid 71 eEncodingIsConstUID, ///< This type is the type whose UID is m_encoding_uid 72 /// with the const qualifier added 73 eEncodingIsRestrictUID, ///< This type is the type whose UID is 74 /// m_encoding_uid with the restrict qualifier added 75 eEncodingIsVolatileUID, ///< This type is the type whose UID is 76 /// m_encoding_uid with the volatile qualifier added 77 eEncodingIsTypedefUID, ///< This type is pointer to a type whose UID is 78 /// m_encoding_uid 79 eEncodingIsPointerUID, ///< This type is pointer to a type whose UID is 80 /// m_encoding_uid 81 eEncodingIsLValueReferenceUID, ///< This type is L value reference to a type 82 /// whose UID is m_encoding_uid 83 eEncodingIsRValueReferenceUID, ///< This type is R value reference to a type 84 /// whose UID is m_encoding_uid, 85 eEncodingIsAtomicUID, ///< This type is the type whose UID is 86 /// m_encoding_uid as an atomic type. 87 eEncodingIsSyntheticUID 88 }; 89 90 enum class ResolveState : unsigned char { 91 Unresolved = 0, 92 Forward = 1, 93 Layout = 2, 94 Full = 3 95 }; 96 97 Type(lldb::user_id_t uid, SymbolFile *symbol_file, ConstString name, 98 llvm::Optional<uint64_t> byte_size, SymbolContextScope *context, 99 lldb::user_id_t encoding_uid, EncodingDataType encoding_uid_type, 100 const Declaration &decl, const CompilerType &compiler_qual_type, 101 ResolveState compiler_type_resolve_state, uint32_t opaque_payload = 0); 102 103 // This makes an invalid type. Used for functions that return a Type when 104 // they get an error. 105 Type(); 106 107 void Dump(Stream *s, bool show_context, 108 lldb::DescriptionLevel level = lldb::eDescriptionLevelFull); 109 110 void DumpTypeName(Stream *s); 111 112 /// Since Type instances only keep a "SymbolFile *" internally, other classes 113 /// like TypeImpl need make sure the module is still around before playing 114 /// with 115 /// Type instances. They can store a weak pointer to the Module; 116 lldb::ModuleSP GetModule(); 117 118 /// GetModule may return module for compile unit's object file. 119 /// GetExeModule returns module for executable object file that contains 120 /// compile unit where type was actualy defined. 121 /// GetModule and GetExeModule may return the same value. 122 lldb::ModuleSP GetExeModule(); 123 124 void GetDescription(Stream *s, lldb::DescriptionLevel level, bool show_name, 125 ExecutionContextScope *exe_scope); 126 GetSymbolFile()127 SymbolFile *GetSymbolFile() { return m_symbol_file; } GetSymbolFile()128 const SymbolFile *GetSymbolFile() const { return m_symbol_file; } 129 130 ConstString GetName(); 131 132 llvm::Optional<uint64_t> GetByteSize(ExecutionContextScope *exe_scope); 133 134 uint32_t GetNumChildren(bool omit_empty_base_classes); 135 136 bool IsAggregateType(); 137 IsValidType()138 bool IsValidType() { return m_encoding_uid_type != eEncodingInvalid; } 139 IsTypedef()140 bool IsTypedef() { return m_encoding_uid_type == eEncodingIsTypedefUID; } 141 142 lldb::TypeSP GetTypedefType(); 143 GetName()144 ConstString GetName() const { return m_name; } 145 146 ConstString GetQualifiedName(); 147 148 void DumpValue(ExecutionContext *exe_ctx, Stream *s, 149 const DataExtractor &data, uint32_t data_offset, 150 bool show_type, bool show_summary, bool verbose, 151 lldb::Format format = lldb::eFormatDefault); 152 153 bool DumpValueInMemory(ExecutionContext *exe_ctx, Stream *s, 154 lldb::addr_t address, AddressType address_type, 155 bool show_types, bool show_summary, bool verbose); 156 157 bool ReadFromMemory(ExecutionContext *exe_ctx, lldb::addr_t address, 158 AddressType address_type, DataExtractor &data); 159 160 bool WriteToMemory(ExecutionContext *exe_ctx, lldb::addr_t address, 161 AddressType address_type, DataExtractor &data); 162 163 bool GetIsDeclaration() const; 164 165 void SetIsDeclaration(bool b); 166 167 bool GetIsExternal() const; 168 169 void SetIsExternal(bool b); 170 171 lldb::Format GetFormat(); 172 173 lldb::Encoding GetEncoding(uint64_t &count); 174 GetSymbolContextScope()175 SymbolContextScope *GetSymbolContextScope() { return m_context; } GetSymbolContextScope()176 const SymbolContextScope *GetSymbolContextScope() const { return m_context; } SetSymbolContextScope(SymbolContextScope * context)177 void SetSymbolContextScope(SymbolContextScope *context) { 178 m_context = context; 179 } 180 181 const lldb_private::Declaration &GetDeclaration() const; 182 183 // Get the clang type, and resolve definitions for any 184 // class/struct/union/enum types completely. 185 CompilerType GetFullCompilerType(); 186 187 // Get the clang type, and resolve definitions enough so that the type could 188 // have layout performed. This allows ptrs and refs to 189 // class/struct/union/enum types remain forward declarations. 190 CompilerType GetLayoutCompilerType(); 191 192 // Get the clang type and leave class/struct/union/enum types as forward 193 // declarations if they haven't already been fully defined. 194 CompilerType GetForwardCompilerType(); 195 196 static int Compare(const Type &a, const Type &b); 197 198 // From a fully qualified typename, split the type into the type basename and 199 // the remaining type scope (namespaces/classes). 200 static bool GetTypeScopeAndBasename(const llvm::StringRef& name, 201 llvm::StringRef &scope, 202 llvm::StringRef &basename, 203 lldb::TypeClass &type_class); SetEncodingType(Type * encoding_type)204 void SetEncodingType(Type *encoding_type) { m_encoding_type = encoding_type; } 205 206 uint32_t GetEncodingMask(); 207 208 typedef uint32_t Payload; 209 /// Return the language-specific payload. GetPayload()210 Payload GetPayload() { return m_payload; } 211 /// Return the language-specific payload. SetPayload(Payload opaque_payload)212 void SetPayload(Payload opaque_payload) { m_payload = opaque_payload; } 213 214 protected: 215 ConstString m_name; 216 SymbolFile *m_symbol_file = nullptr; 217 /// The symbol context in which this type is defined. 218 SymbolContextScope *m_context = nullptr; 219 Type *m_encoding_type = nullptr; 220 lldb::user_id_t m_encoding_uid = LLDB_INVALID_UID; 221 EncodingDataType m_encoding_uid_type = eEncodingInvalid; 222 uint64_t m_byte_size : 63; 223 uint64_t m_byte_size_has_value : 1; 224 Declaration m_decl; 225 CompilerType m_compiler_type; 226 ResolveState m_compiler_type_resolve_state = ResolveState::Unresolved; 227 /// Language-specific flags. 228 Payload m_payload; 229 230 Type *GetEncodingType(); 231 232 bool ResolveCompilerType(ResolveState compiler_type_resolve_state); 233 }; 234 235 // the two classes here are used by the public API as a backend to the SBType 236 // and SBTypeList classes 237 238 class TypeImpl { 239 public: 240 TypeImpl() = default; 241 242 ~TypeImpl() = default; 243 244 TypeImpl(const lldb::TypeSP &type_sp); 245 246 TypeImpl(const CompilerType &compiler_type); 247 248 TypeImpl(const lldb::TypeSP &type_sp, const CompilerType &dynamic); 249 250 TypeImpl(const CompilerType &compiler_type, const CompilerType &dynamic); 251 252 void SetType(const lldb::TypeSP &type_sp); 253 254 void SetType(const CompilerType &compiler_type); 255 256 void SetType(const lldb::TypeSP &type_sp, const CompilerType &dynamic); 257 258 void SetType(const CompilerType &compiler_type, const CompilerType &dynamic); 259 260 bool operator==(const TypeImpl &rhs) const; 261 262 bool operator!=(const TypeImpl &rhs) const; 263 264 bool IsValid() const; 265 266 explicit operator bool() const; 267 268 void Clear(); 269 270 lldb::ModuleSP GetModule() const; 271 272 ConstString GetName() const; 273 274 ConstString GetDisplayTypeName() const; 275 276 TypeImpl GetPointerType() const; 277 278 TypeImpl GetPointeeType() const; 279 280 TypeImpl GetReferenceType() const; 281 282 TypeImpl GetTypedefedType() const; 283 284 TypeImpl GetDereferencedType() const; 285 286 TypeImpl GetUnqualifiedType() const; 287 288 TypeImpl GetCanonicalType() const; 289 290 CompilerType GetCompilerType(bool prefer_dynamic); 291 292 TypeSystem *GetTypeSystem(bool prefer_dynamic); 293 294 bool GetDescription(lldb_private::Stream &strm, 295 lldb::DescriptionLevel description_level); 296 297 private: 298 bool CheckModule(lldb::ModuleSP &module_sp) const; 299 bool CheckExeModule(lldb::ModuleSP &module_sp) const; 300 bool CheckModuleCommon(const lldb::ModuleWP &input_module_wp, 301 lldb::ModuleSP &module_sp) const; 302 303 lldb::ModuleWP m_module_wp; 304 lldb::ModuleWP m_exe_module_wp; 305 CompilerType m_static_type; 306 CompilerType m_dynamic_type; 307 }; 308 309 class TypeListImpl { 310 public: TypeListImpl()311 TypeListImpl() : m_content() {} 312 Append(const lldb::TypeImplSP & type)313 void Append(const lldb::TypeImplSP &type) { m_content.push_back(type); } 314 315 class AppendVisitor { 316 public: AppendVisitor(TypeListImpl & type_list)317 AppendVisitor(TypeListImpl &type_list) : m_type_list(type_list) {} 318 operator()319 void operator()(const lldb::TypeImplSP &type) { m_type_list.Append(type); } 320 321 private: 322 TypeListImpl &m_type_list; 323 }; 324 325 void Append(const lldb_private::TypeList &type_list); 326 GetTypeAtIndex(size_t idx)327 lldb::TypeImplSP GetTypeAtIndex(size_t idx) { 328 lldb::TypeImplSP type_sp; 329 if (idx < GetSize()) 330 type_sp = m_content[idx]; 331 return type_sp; 332 } 333 GetSize()334 size_t GetSize() { return m_content.size(); } 335 336 private: 337 std::vector<lldb::TypeImplSP> m_content; 338 }; 339 340 class TypeMemberImpl { 341 public: TypeMemberImpl()342 TypeMemberImpl() 343 : m_type_impl_sp(), m_name() 344 345 {} 346 347 TypeMemberImpl(const lldb::TypeImplSP &type_impl_sp, uint64_t bit_offset, 348 ConstString name, uint32_t bitfield_bit_size = 0, 349 bool is_bitfield = false) m_type_impl_sp(type_impl_sp)350 : m_type_impl_sp(type_impl_sp), m_bit_offset(bit_offset), m_name(name), 351 m_bitfield_bit_size(bitfield_bit_size), m_is_bitfield(is_bitfield) {} 352 TypeMemberImpl(const lldb::TypeImplSP & type_impl_sp,uint64_t bit_offset)353 TypeMemberImpl(const lldb::TypeImplSP &type_impl_sp, uint64_t bit_offset) 354 : m_type_impl_sp(type_impl_sp), m_bit_offset(bit_offset), m_name(), 355 m_bitfield_bit_size(0), m_is_bitfield(false) { 356 if (m_type_impl_sp) 357 m_name = m_type_impl_sp->GetName(); 358 } 359 GetTypeImpl()360 const lldb::TypeImplSP &GetTypeImpl() { return m_type_impl_sp; } 361 GetName()362 ConstString GetName() const { return m_name; } 363 GetBitOffset()364 uint64_t GetBitOffset() const { return m_bit_offset; } 365 GetBitfieldBitSize()366 uint32_t GetBitfieldBitSize() const { return m_bitfield_bit_size; } 367 SetBitfieldBitSize(uint32_t bitfield_bit_size)368 void SetBitfieldBitSize(uint32_t bitfield_bit_size) { 369 m_bitfield_bit_size = bitfield_bit_size; 370 } 371 GetIsBitfield()372 bool GetIsBitfield() const { return m_is_bitfield; } 373 SetIsBitfield(bool is_bitfield)374 void SetIsBitfield(bool is_bitfield) { m_is_bitfield = is_bitfield; } 375 376 protected: 377 lldb::TypeImplSP m_type_impl_sp; 378 uint64_t m_bit_offset = 0; 379 ConstString m_name; 380 uint32_t m_bitfield_bit_size = 0; // Bit size for bitfield members only 381 bool m_is_bitfield = false; 382 }; 383 384 /// 385 /// Sometimes you can find the name of the type corresponding to an object, but 386 /// we don't have debug 387 /// information for it. If that is the case, you can return one of these 388 /// objects, and then if it 389 /// has a full type, you can use that, but if not at least you can print the 390 /// name for informational 391 /// purposes. 392 /// 393 394 class TypeAndOrName { 395 public: 396 TypeAndOrName() = default; 397 TypeAndOrName(lldb::TypeSP &type_sp); 398 TypeAndOrName(const CompilerType &compiler_type); 399 TypeAndOrName(const char *type_str); 400 TypeAndOrName(ConstString &type_const_string); 401 402 bool operator==(const TypeAndOrName &other) const; 403 404 bool operator!=(const TypeAndOrName &other) const; 405 406 ConstString GetName() const; 407 GetCompilerType()408 CompilerType GetCompilerType() const { return m_compiler_type; } 409 410 void SetName(ConstString type_name); 411 412 void SetName(const char *type_name_cstr); 413 414 void SetTypeSP(lldb::TypeSP type_sp); 415 416 void SetCompilerType(CompilerType compiler_type); 417 418 bool IsEmpty() const; 419 420 bool HasName() const; 421 422 bool HasCompilerType() const; 423 HasType()424 bool HasType() const { return HasCompilerType(); } 425 426 void Clear(); 427 428 explicit operator bool() { return !IsEmpty(); } 429 430 private: 431 CompilerType m_compiler_type; 432 ConstString m_type_name; 433 }; 434 435 class TypeMemberFunctionImpl { 436 public: TypeMemberFunctionImpl()437 TypeMemberFunctionImpl() : m_type(), m_decl(), m_name() {} 438 TypeMemberFunctionImpl(const CompilerType & type,const CompilerDecl & decl,const std::string & name,const lldb::MemberFunctionKind & kind)439 TypeMemberFunctionImpl(const CompilerType &type, const CompilerDecl &decl, 440 const std::string &name, 441 const lldb::MemberFunctionKind &kind) 442 : m_type(type), m_decl(decl), m_name(name), m_kind(kind) {} 443 444 bool IsValid(); 445 446 ConstString GetName() const; 447 448 ConstString GetMangledName() const; 449 450 CompilerType GetType() const; 451 452 CompilerType GetReturnType() const; 453 454 size_t GetNumArguments() const; 455 456 CompilerType GetArgumentAtIndex(size_t idx) const; 457 458 lldb::MemberFunctionKind GetKind() const; 459 460 bool GetDescription(Stream &stream); 461 462 protected: 463 std::string GetPrintableTypeName(); 464 465 private: 466 CompilerType m_type; 467 CompilerDecl m_decl; 468 ConstString m_name; 469 lldb::MemberFunctionKind m_kind = lldb::eMemberFunctionKindUnknown; 470 }; 471 472 class TypeEnumMemberImpl { 473 public: TypeEnumMemberImpl()474 TypeEnumMemberImpl() : m_integer_type_sp(), m_name("<invalid>"), m_value() {} 475 476 TypeEnumMemberImpl(const lldb::TypeImplSP &integer_type_sp, 477 ConstString name, const llvm::APSInt &value); 478 479 TypeEnumMemberImpl(const TypeEnumMemberImpl &rhs) = default; 480 481 TypeEnumMemberImpl &operator=(const TypeEnumMemberImpl &rhs); 482 IsValid()483 bool IsValid() { return m_valid; } 484 GetName()485 ConstString GetName() const { return m_name; } 486 GetIntegerType()487 const lldb::TypeImplSP &GetIntegerType() const { return m_integer_type_sp; } 488 GetValueAsUnsigned()489 uint64_t GetValueAsUnsigned() const { return m_value.getZExtValue(); } 490 GetValueAsSigned()491 int64_t GetValueAsSigned() const { return m_value.getSExtValue(); } 492 493 protected: 494 lldb::TypeImplSP m_integer_type_sp; 495 ConstString m_name; 496 llvm::APSInt m_value; 497 bool m_valid = false; 498 }; 499 500 class TypeEnumMemberListImpl { 501 public: TypeEnumMemberListImpl()502 TypeEnumMemberListImpl() : m_content() {} 503 Append(const lldb::TypeEnumMemberImplSP & type)504 void Append(const lldb::TypeEnumMemberImplSP &type) { 505 m_content.push_back(type); 506 } 507 508 void Append(const lldb_private::TypeEnumMemberListImpl &type_list); 509 GetTypeEnumMemberAtIndex(size_t idx)510 lldb::TypeEnumMemberImplSP GetTypeEnumMemberAtIndex(size_t idx) { 511 lldb::TypeEnumMemberImplSP enum_member; 512 if (idx < GetSize()) 513 enum_member = m_content[idx]; 514 return enum_member; 515 } 516 GetSize()517 size_t GetSize() { return m_content.size(); } 518 519 private: 520 std::vector<lldb::TypeEnumMemberImplSP> m_content; 521 }; 522 523 } // namespace lldb_private 524 525 #endif // LLDB_SYMBOL_TYPE_H 526