Index: lldb/include/lldb/Core/Module.h =================================================================== --- lldb/include/lldb/Core/Module.h +++ lldb/include/lldb/Core/Module.h @@ -811,7 +811,7 @@ bool GetIsDynamicLinkEditor(); - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language); // Special error functions that can do printf style formatting that will Index: lldb/include/lldb/Symbol/CompilerType.h =================================================================== --- lldb/include/lldb/Symbol/CompilerType.h +++ lldb/include/lldb/Symbol/CompilerType.h @@ -15,6 +15,7 @@ #include "lldb/lldb-private.h" #include "llvm/ADT/APSInt.h" +#include "llvm/Support/Casting.h" namespace lldb_private { @@ -38,7 +39,8 @@ /// implementation. /// /// \see lldb_private::TypeSystemClang::GetType(clang::QualType) - CompilerType(TypeSystem *type_system, lldb::opaque_compiler_type_t type) + CompilerType(lldb::TypeSystemWP *type_system, + lldb::opaque_compiler_type_t type) : m_type(type), m_type_system(type_system) { assert(Verify() && "verification failed"); } @@ -161,7 +163,39 @@ /// Accessors. /// \{ - TypeSystem *GetTypeSystem() const { return m_type_system; } + + /// This is a minimal wrapper of a TypeSystem shared pointer as + /// returned by CompilerType. + class ManagedTypeSystem { + lldb::TypeSystemSP m_typesystem_sp = nullptr; + + public: + ManagedTypeSystem() = default; + ManagedTypeSystem(lldb::TypeSystemSP typesystem_sp) + : m_typesystem_sp(typesystem_sp) {} + template TypeSystemType *dyn_cast_or_null() { + if (!m_typesystem_sp) + return nullptr; + return llvm::dyn_cast_or_null(m_typesystem_sp.get()); + } + operator bool() const { return (bool)m_typesystem_sp; } + bool operator==(const ManagedTypeSystem &other) const; + /// Only to be used in a one-off situations like + /// if (typesystem && typesystem->method()) + /// Do not store this pointer! + TypeSystem *operator->() const; + lldb::TypeSystemSP GetSharedPointer() const { return m_typesystem_sp; } + lldb::TypeSystemWP *GetCanonicalWP() const; + }; + + CompilerType(ManagedTypeSystem type_system, lldb::opaque_compiler_type_t type) + : m_type(type), m_type_system(type_system.GetCanonicalWP()) { + assert(Verify() && "verification failed"); + } + + /// Returns a shared pointer to the type system. The + /// ManagedTypeSystem can be compared for equality. + ManagedTypeSystem GetTypeSystem() const; ConstString GetTypeName() const; @@ -176,7 +210,7 @@ lldb::TypeClass GetTypeClass() const; - void SetCompilerType(TypeSystem *type_system, + void SetCompilerType(lldb::TypeSystemWP *type_system, lldb::opaque_compiler_type_t type); unsigned GetTypeQualifiers() const; @@ -422,7 +456,7 @@ #endif lldb::opaque_compiler_type_t m_type = nullptr; - TypeSystem *m_type_system = nullptr; + lldb::TypeSystemWP *m_type_system = nullptr; }; bool operator==(const CompilerType &lhs, const CompilerType &rhs); Index: lldb/include/lldb/Symbol/SymbolFile.h =================================================================== --- lldb/include/lldb/Symbol/SymbolFile.h +++ lldb/include/lldb/Symbol/SymbolFile.h @@ -310,7 +310,7 @@ virtual void PreloadSymbols(); - virtual llvm::Expected + virtual llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) = 0; virtual CompilerDeclContext @@ -465,7 +465,7 @@ uint32_t GetNumCompileUnits() override; lldb::CompUnitSP GetCompileUnitAtIndex(uint32_t idx) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; void Dump(Stream &s) override; Index: lldb/include/lldb/Symbol/SymbolFileOnDemand.h =================================================================== --- lldb/include/lldb/Symbol/SymbolFileOnDemand.h +++ lldb/include/lldb/Symbol/SymbolFileOnDemand.h @@ -164,7 +164,7 @@ lldb::TypeClass type_mask, lldb_private::TypeList &type_list) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; lldb_private::CompilerDeclContext FindNamespace( Index: lldb/include/lldb/Symbol/TaggedASTType.h =================================================================== --- lldb/include/lldb/Symbol/TaggedASTType.h +++ lldb/include/lldb/Symbol/TaggedASTType.h @@ -20,7 +20,8 @@ TaggedASTType(const CompilerType &compiler_type) : CompilerType(compiler_type) {} - TaggedASTType(lldb::opaque_compiler_type_t type, TypeSystem *type_system) + TaggedASTType(lldb::opaque_compiler_type_t type, + lldb::TypeSystemWP *type_system) : CompilerType(type_system, type) {} TaggedASTType(const TaggedASTType &tw) : CompilerType(tw) {} Index: lldb/include/lldb/Symbol/Type.h =================================================================== --- lldb/include/lldb/Symbol/Type.h +++ lldb/include/lldb/Symbol/Type.h @@ -295,7 +295,7 @@ CompilerType GetCompilerType(bool prefer_dynamic); - TypeSystem *GetTypeSystem(bool prefer_dynamic); + CompilerType::ManagedTypeSystem GetTypeSystem(bool prefer_dynamic); bool GetDescription(lldb_private::Stream &strm, lldb::DescriptionLevel description_level); Index: lldb/include/lldb/Symbol/TypeSystem.h =================================================================== --- lldb/include/lldb/Symbol/TypeSystem.h +++ lldb/include/lldb/Symbol/TypeSystem.h @@ -10,12 +10,12 @@ #define LLDB_SYMBOL_TYPESYSTEM_H #include -#include #include #include #include "llvm/ADT/APFloat.h" #include "llvm/ADT/APSInt.h" +#include "llvm/ADT/DenseMap.h" #include "llvm/ADT/SmallBitVector.h" #include "llvm/Support/Casting.h" #include "llvm/Support/Error.h" @@ -85,8 +85,12 @@ static lldb::TypeSystemSP CreateInstance(lldb::LanguageType language, Target *target); - // Free up any resources associated with this TypeSystem. Done before - // removing all the TypeSystems from the TypeSystemMap. + /// For use in CompilerType and other places that need to hold on to + /// a TypeSystem. + lldb::TypeSystemWP *GetCanonicalWP() const; + + /// Free up any resources associated with this TypeSystem. Done before + /// removing all the TypeSystems from the TypeSystemMap. virtual void Finalize() {} virtual DWARFASTParser *GetDWARFParser() { return nullptr; } @@ -509,7 +513,10 @@ // meaningless type itself, instead preferring to use the dynamic type virtual bool IsMeaninglessWithoutDynamicResolution(void *type); + /// Only to be used by TypeSystemMap and various unit tests. + void SetCanonicalWP(lldb::TypeSystemWP *wp) { m_canonical_wp = wp; } protected: + lldb::TypeSystemWP *m_canonical_wp = nullptr; SymbolFile *m_sym_file = nullptr; }; @@ -524,39 +531,54 @@ // Iterate through all of the type systems that are created. Return true from // callback to keep iterating, false to stop iterating. - void ForEach(std::function const &callback); + void ForEach(std::function const &callback); - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language, Module *module, bool can_create); - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language, Target *target, bool can_create); protected: - typedef std::map collection; + struct TypeSystemEntry { + /// The primary owner of the type system. Not accessible from the + /// outside. + lldb::TypeSystemSP sp; + /// A canoncial pointer to a weak pointer to the type system. This + /// allows CompilerType to store the weak pointer in a single + /// pointer-sized field. This field is never a nullptr. + lldb::TypeSystemWP *wp_ptr; + }; + + /// Return a canonical weak pointer for type_system. + static TypeSystemEntry GetTypeSystemEntry(lldb::TypeSystemSP type_system); + + typedef llvm::DenseMap collection; mutable std::mutex m_mutex; ///< A mutex to keep this object happy in - ///multi-threaded environments. + /// multi-threaded environments. collection m_map; bool m_clear_in_progress = false; private: typedef llvm::function_ref CreateCallback; /// Finds the type system for the given language. If no type system could be - /// found for a language and a CreateCallback was provided, the value returned - /// by the callback will be treated as the TypeSystem for the language. + /// found for a language and a CreateCallback was provided, the value + /// returned by the callback will be treated as the TypeSystem for the + /// language. /// /// \param language The language for which the type system should be found. /// \param create_callback A callback that will be called if no previously /// created TypeSystem that fits the given language /// could found. Can be omitted if a non-existent - /// type system should be treated as an error instead. + /// type system should be treated as an error + /// instead. /// \return The found type system or an error. - llvm::Expected GetTypeSystemForLanguage( + llvm::Expected GetTypeSystemForLanguage( lldb::LanguageType language, llvm::Optional create_callback = llvm::None); -}; + }; } // namespace lldb_private Index: lldb/include/lldb/Target/Target.h =================================================================== --- lldb/include/lldb/Target/Target.h +++ lldb/include/lldb/Target/Target.h @@ -1119,11 +1119,12 @@ PathMappingList &GetImageSearchPathList(); - llvm::Expected + llvm::Expected GetScratchTypeSystemForLanguage(lldb::LanguageType language, bool create_on_demand = true); - std::vector GetScratchTypeSystems(bool create_on_demand = true); + std::vector + GetScratchTypeSystems(bool create_on_demand = true); PersistentExpressionState * GetPersistentExpressionStateForLanguage(lldb::LanguageType language); Index: lldb/include/lldb/lldb-enumerations.h =================================================================== --- lldb/include/lldb/lldb-enumerations.h +++ lldb/include/lldb/lldb-enumerations.h @@ -9,6 +9,7 @@ #ifndef LLDB_LLDB_ENUMERATIONS_H #define LLDB_LLDB_ENUMERATIONS_H +#include #include #ifndef SWIG @@ -433,7 +434,7 @@ /// specification for ease of use and consistency. /// The enum -> string code is in Language.cpp, don't change this /// table without updating that code as well. -enum LanguageType { +enum LanguageType : uint16_t { eLanguageTypeUnknown = 0x0000, ///< Unknown or invalid language value. eLanguageTypeC89 = 0x0001, ///< ISO C:1989. eLanguageTypeC = 0x0002, ///< Non-standardized C, such as K&R. Index: lldb/include/lldb/lldb-forward.h =================================================================== --- lldb/include/lldb/lldb-forward.h +++ lldb/include/lldb/lldb-forward.h @@ -432,6 +432,7 @@ typedef std::shared_ptr TypeEnumMemberImplSP; typedef std::shared_ptr TypeFilterImplSP; typedef std::shared_ptr TypeSystemSP; +typedef std::weak_ptr TypeSystemWP; typedef std::shared_ptr TypeFormatImplSP; typedef std::shared_ptr TypeNameSpecifierImplSP; Index: lldb/source/API/SBModule.cpp =================================================================== --- lldb/source/API/SBModule.cpp +++ lldb/source/API/SBModule.cpp @@ -450,9 +450,12 @@ module_sp->GetTypeSystemForLanguage(eLanguageTypeC); if (auto err = type_system_or_err.takeError()) { llvm::consumeError(std::move(err)); - return SBType(); + return {}; } - sb_type = SBType(type_system_or_err->GetBuiltinTypeByName(name)); + if (auto ts = *type_system_or_err) + sb_type = SBType(ts->GetBuiltinTypeByName(name)); + else + return {}; } } return sb_type; @@ -468,7 +471,8 @@ if (auto err = type_system_or_err.takeError()) { llvm::consumeError(std::move(err)); } else { - return SBType(type_system_or_err->GetBasicTypeFromAST(type)); + if (auto ts = *type_system_or_err) + return SBType(ts->GetBasicTypeFromAST(type)); } } return SBType(); @@ -494,10 +498,12 @@ if (auto err = type_system_or_err.takeError()) { llvm::consumeError(std::move(err)); } else { - CompilerType compiler_type = - type_system_or_err->GetBuiltinTypeByName(name); - if (compiler_type) - retval.Append(SBType(compiler_type)); + if (auto ts = *type_system_or_err) { + CompilerType compiler_type = + ts->GetBuiltinTypeByName(name); + if (compiler_type) + retval.Append(SBType(compiler_type)); + } } } else { for (size_t idx = 0; idx < type_list.GetSize(); idx++) { Index: lldb/source/API/SBTarget.cpp =================================================================== --- lldb/source/API/SBTarget.cpp +++ lldb/source/API/SBTarget.cpp @@ -1779,8 +1779,9 @@ // No matches, search for basic typename matches for (auto *type_system : target_sp->GetScratchTypeSystems()) - if (auto type = type_system->GetBuiltinTypeByName(const_typename)) - return SBType(type); + if (auto ts = type_system->lock()) + if (auto type = ts->GetBuiltinTypeByName(const_typename)) + return SBType(type); } return SBType(); @@ -1791,9 +1792,10 @@ TargetSP target_sp(GetSP()); if (target_sp) { - for (auto *type_system : target_sp->GetScratchTypeSystems()) - if (auto compiler_type = type_system->GetBasicTypeFromAST(type)) - return SBType(compiler_type); + for (auto &type_system : target_sp->GetScratchTypeSystems()) + if (auto ts = type_system->lock()) + if (auto compiler_type = ts->GetBasicTypeFromAST(type)) + return SBType(compiler_type); } return SBType(); } @@ -1832,10 +1834,10 @@ if (sb_type_list.GetSize() == 0) { // No matches, search for basic typename matches - for (auto *type_system : target_sp->GetScratchTypeSystems()) - if (auto compiler_type = - type_system->GetBuiltinTypeByName(const_typename)) - sb_type_list.Append(SBType(compiler_type)); + for (auto &type_system : target_sp->GetScratchTypeSystems()) + if (auto ts = type_system->lock()) + if (auto compiler_type = ts->GetBuiltinTypeByName(const_typename)) + sb_type_list.Append(SBType(compiler_type)); } } return sb_type_list; Index: lldb/source/API/SBType.cpp =================================================================== --- lldb/source/API/SBType.cpp +++ lldb/source/API/SBType.cpp @@ -28,9 +28,7 @@ SBType::SBType() { LLDB_INSTRUMENT_VA(this); } -SBType::SBType(const CompilerType &type) - : m_opaque_sp(new TypeImpl( - CompilerType(type.GetTypeSystem(), type.GetOpaqueQualType()))) {} +SBType::SBType(const CompilerType &type) : m_opaque_sp(new TypeImpl(type)) {} SBType::SBType(const lldb::TypeSP &type_sp) : m_opaque_sp(new TypeImpl(type_sp)) {} @@ -364,8 +362,8 @@ LLDB_INSTRUMENT_VA(this, basic_type); if (IsValid() && m_opaque_sp->IsValid()) - return SBType( - m_opaque_sp->GetTypeSystem(false)->GetBasicTypeFromAST(basic_type)); + if (auto ts = m_opaque_sp->GetTypeSystem(false)) + return SBType(ts->GetBasicTypeFromAST(basic_type)); return SBType(); } Index: lldb/source/Breakpoint/Watchpoint.cpp =================================================================== --- lldb/source/Breakpoint/Watchpoint.cpp +++ lldb/source/Breakpoint/Watchpoint.cpp @@ -43,8 +43,12 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Watchpoints), std::move(err), "Failed to set type."); } else { - m_type = type_system_or_err->GetBuiltinTypeForEncodingAndBitSize( - eEncodingUint, 8 * size); + if (auto ts = *type_system_or_err) + m_type = + ts->GetBuiltinTypeForEncodingAndBitSize(eEncodingUint, 8 * size); + else + LLDB_LOG_ERROR(GetLog(LLDBLog::Watchpoints), std::move(err), + "Failed to set type. Typesystem is no longer live."); } } Index: lldb/source/Commands/CommandObjectTarget.cpp =================================================================== --- lldb/source/Commands/CommandObjectTarget.cpp +++ lldb/source/Commands/CommandObjectTarget.cpp @@ -5093,8 +5093,10 @@ protected: bool DoExecute(Args &command, CommandReturnObject &result) override { // Go over every scratch TypeSystem and dump to the command output. - for (TypeSystem *ts : GetSelectedTarget().GetScratchTypeSystems()) - ts->Dump(result.GetOutputStream().AsRawOstream()); + for (lldb::TypeSystemWP *ts_wp : + GetSelectedTarget().GetScratchTypeSystems()) + if (auto ts = ts_wp->lock()) + ts->Dump(result.GetOutputStream().AsRawOstream()); result.SetStatus(eReturnStatusSuccessFinishResult); return result.Succeeded(); Index: lldb/source/Core/DumpDataExtractor.cpp =================================================================== --- lldb/source/Core/DumpDataExtractor.cpp +++ lldb/source/Core/DumpDataExtractor.cpp @@ -319,12 +319,16 @@ static const llvm::fltSemantics &GetFloatSemantics(const TargetSP &target_sp, size_t byte_size) { - if (target_sp) { - if (auto type_system_or_err = - target_sp->GetScratchTypeSystemForLanguage(eLanguageTypeC)) - return type_system_or_err->GetFloatTypeSemantics(byte_size); - else + while (target_sp) { + auto type_system_or_err = + target_sp->GetScratchTypeSystemForLanguage(eLanguageTypeC); + if (!type_system_or_err) { llvm::consumeError(type_system_or_err.takeError()); + break; + } + if (auto ts = *type_system_or_err) + return ts->GetFloatTypeSemantics(byte_size); + break; } // No target, just make a reasonable guess switch(byte_size) { Index: lldb/source/Core/Module.cpp =================================================================== --- lldb/source/Core/Module.cpp +++ lldb/source/Core/Module.cpp @@ -364,7 +364,7 @@ } } -llvm::Expected +llvm::Expected Module::GetTypeSystemForLanguage(LanguageType language) { return m_type_system_map.GetTypeSystemForLanguage(language, this, true); } Index: lldb/source/Core/ValueObjectMemory.cpp =================================================================== --- lldb/source/Core/ValueObjectMemory.cpp +++ lldb/source/Core/ValueObjectMemory.cpp @@ -83,8 +83,7 @@ : ValueObject(exe_scope, manager), m_address(address), m_type_sp(), m_compiler_type(ast_type) { // Do not attempt to construct one of these objects with no variable! - assert(m_compiler_type.GetTypeSystem()); - assert(m_compiler_type.GetOpaqueQualType()); + assert(m_compiler_type.IsValid()); TargetSP target_sp(GetTargetSP()); Index: lldb/source/Core/ValueObjectRegister.cpp =================================================================== --- lldb/source/Core/ValueObjectRegister.cpp +++ lldb/source/Core/ValueObjectRegister.cpp @@ -206,9 +206,9 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Types), std::move(err), "Unable to get CompilerType from TypeSystem"); } else { - m_compiler_type = - type_system_or_err->GetBuiltinTypeForEncodingAndBitSize( - m_reg_info.encoding, m_reg_info.byte_size * 8); + if (auto ts = *type_system_or_err) + m_compiler_type = ts->GetBuiltinTypeForEncodingAndBitSize( + m_reg_info.encoding, m_reg_info.byte_size * 8); } } } Index: lldb/source/DataFormatters/VectorType.cpp =================================================================== --- lldb/source/DataFormatters/VectorType.cpp +++ lldb/source/DataFormatters/VectorType.cpp @@ -23,8 +23,10 @@ static CompilerType GetCompilerTypeForFormat(lldb::Format format, CompilerType element_type, - TypeSystem *type_system) { + TypeSystemSP type_system) { lldbassert(type_system && "type_system needs to be not NULL"); + if (!type_system) + return {}; switch (format) { case lldb::eFormatAddressInfo: @@ -219,8 +221,9 @@ CompilerType parent_type(m_backend.GetCompilerType()); CompilerType element_type; parent_type.IsVectorType(&element_type); - m_child_type = ::GetCompilerTypeForFormat(m_parent_format, element_type, - parent_type.GetTypeSystem()); + m_child_type = ::GetCompilerTypeForFormat( + m_parent_format, element_type, + parent_type.GetTypeSystem().GetSharedPointer()); m_num_children = ::CalculateNumChildren(parent_type, m_child_type); m_item_format = GetItemFormatForFormat(m_parent_format, m_child_type); return false; Index: lldb/source/Expression/Materializer.cpp =================================================================== --- lldb/source/Expression/Materializer.cpp +++ lldb/source/Expression/Materializer.cpp @@ -1023,8 +1023,15 @@ llvm::toString(std::move(error)).c_str()); return; } + auto ts = *type_system_or_err; + if (!ts) { + err.SetErrorStringWithFormat("Couldn't dematerialize a result variable: " + "couldn't corresponding type system is " + "no longer live."); + return; + } PersistentExpressionState *persistent_state = - type_system_or_err->GetPersistentExpressionState(); + ts->GetPersistentExpressionState(); if (!persistent_state) { err.SetErrorString("Couldn't dematerialize a result variable: " Index: lldb/source/Plugins/ABI/PowerPC/ABISysV_ppc64.cpp =================================================================== --- lldb/source/Plugins/ABI/PowerPC/ABISysV_ppc64.cpp +++ lldb/source/Plugins/ABI/PowerPC/ABISysV_ppc64.cpp @@ -809,8 +809,8 @@ // case 3: get from GPRs // first, check if this is a packed struct or not - TypeSystemClang *ast = - llvm::dyn_cast(m_type.GetTypeSystem()); + auto ts = m_type.GetTypeSystem(); + TypeSystemClang *ast = ts.dyn_cast_or_null(); if (ast) { clang::RecordDecl *record_decl = TypeSystemClang::GetAsRecordDecl(m_type); Index: lldb/source/Plugins/ABI/X86/ABISysV_x86_64.cpp =================================================================== --- lldb/source/Plugins/ABI/X86/ABISysV_x86_64.cpp +++ lldb/source/Plugins/ABI/X86/ABISysV_x86_64.cpp @@ -638,12 +638,12 @@ bool is_memory = true; std::vector aggregate_field_offsets; std::vector aggregate_compiler_types; - if (return_compiler_type.GetTypeSystem()->CanPassInRegisters( - return_compiler_type) && - *bit_width <= 128 && - FlattenAggregateType(thread, exe_ctx, return_compiler_type, - 0, aggregate_field_offsets, - aggregate_compiler_types)) { + auto ts = return_compiler_type.GetTypeSystem(); + if (ts && ts->CanPassInRegisters(return_compiler_type) && + *bit_width <= 128 && + FlattenAggregateType(thread, exe_ctx, return_compiler_type, 0, + aggregate_field_offsets, + aggregate_compiler_types)) { ByteOrder byte_order = target->GetArchitecture().GetByteOrder(); WritableDataBufferSP data_sp(new DataBufferHeap(16, 0)); DataExtractor return_ext(data_sp, byte_order, Index: lldb/source/Plugins/ExpressionParser/Clang/ClangASTImporter.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangASTImporter.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangASTImporter.cpp @@ -33,8 +33,8 @@ const CompilerType &src_type) { clang::ASTContext &dst_clang_ast = dst_ast.getASTContext(); - TypeSystemClang *src_ast = - llvm::dyn_cast_or_null(src_type.GetTypeSystem()); + auto ts = src_type.GetTypeSystem(); + TypeSystemClang *src_ast = ts.dyn_cast_or_null(); if (!src_ast) return CompilerType(); @@ -59,7 +59,7 @@ lldb::opaque_compiler_type_t dst_clang_type = ret_or_error->getAsOpaquePtr(); if (dst_clang_type) - return CompilerType(&dst_ast, dst_clang_type); + return CompilerType(dst_ast.GetCanonicalWP(), dst_clang_type); return CompilerType(); } @@ -305,8 +305,10 @@ const CompilerType &src_type) { Log *log = GetLog(LLDBLog::Expressions); - TypeSystemClang *src_ctxt = - llvm::cast(src_type.GetTypeSystem()); + auto ts = src_type.GetTypeSystem(); + TypeSystemClang *src_ctxt = ts.dyn_cast_or_null(); + if (!src_ctxt) + return {}; LLDB_LOG(log, " [ClangASTImporter] DeportType called on ({0}Type*){1} " Index: lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangASTSource.cpp @@ -1733,10 +1733,10 @@ } CompilerType ClangASTSource::GuardedCopyType(const CompilerType &src_type) { - TypeSystemClang *src_ast = - llvm::dyn_cast_or_null(src_type.GetTypeSystem()); - if (src_ast == nullptr) - return CompilerType(); + auto ts = src_type.GetTypeSystem(); + auto src_ast = ts.dyn_cast_or_null(); + if (!src_ast) + return {}; QualType copied_qual_type = ClangUtil::GetQualType( m_ast_importer_sp->CopyType(*m_clang_ast_context, src_type)); @@ -1745,7 +1745,7 @@ copied_qual_type->getCanonicalTypeInternal().isNull()) // this shouldn't happen, but we're hardening because the AST importer // seems to be generating bad types on occasion. - return CompilerType(); + return {}; return m_clang_ast_context->GetType(copied_qual_type); } Index: lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionDeclMap.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionDeclMap.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionDeclMap.cpp @@ -206,7 +206,8 @@ TypeSystemClang &source, TypeFromParser parser_type) { assert(&target == GetScratchContext(*m_target)); - assert((TypeSystem *)&source == parser_type.GetTypeSystem()); + assert((TypeSystem *)&source == + parser_type.GetTypeSystem().GetSharedPointer().get()); assert(&source.getASTContext() == m_ast_context); return TypeFromUser(m_ast_importer_sp->DeportType(target, parser_type)); @@ -218,9 +219,8 @@ bool is_result, bool is_lvalue) { assert(m_parser_vars.get()); - - TypeSystemClang *ast = - llvm::dyn_cast_or_null(parser_type.GetTypeSystem()); + auto ts = parser_type.GetTypeSystem(); + TypeSystemClang *ast = ts.dyn_cast_or_null(); if (ast == nullptr) return false; @@ -847,8 +847,9 @@ QualType class_qual_type(class_decl->getTypeForDecl(), 0); - TypeFromUser class_user_type(class_qual_type.getAsOpaquePtr(), - function_decl_ctx.GetTypeSystem()); + TypeFromUser class_user_type( + class_qual_type.getAsOpaquePtr(), + function_decl_ctx.GetTypeSystem()->GetCanonicalWP()); LLDB_LOG(log, " CEDM::FEVD Adding type for $__lldb_class: {0}", class_qual_type.getAsString()); @@ -936,8 +937,9 @@ return; // This is unlikely, but we have seen crashes where this // occurred - TypeFromUser class_user_type(QualType(interface_type, 0).getAsOpaquePtr(), - function_decl_ctx.GetTypeSystem()); + TypeFromUser class_user_type( + QualType(interface_type, 0).getAsOpaquePtr(), + function_decl_ctx.GetTypeSystem()->GetCanonicalWP()); LLDB_LOG(log, " FEVD[{0}] Adding type for $__lldb_objc_class: {1}", ClangUtil::ToString(interface_type)); @@ -1501,8 +1503,9 @@ return false; } - TypeSystemClang *clang_ast = llvm::dyn_cast_or_null( - var_type->GetForwardCompilerType().GetTypeSystem()); + auto ts = var_type->GetForwardCompilerType().GetTypeSystem(); + TypeSystemClang *clang_ast = + ts.dyn_cast_or_null(); if (!clang_ast) { LLDB_LOG(log, "Skipped a definition because it has no Clang AST"); @@ -1621,8 +1624,9 @@ TypeFromUser user_type = valobj->GetCompilerType(); + auto ts = user_type.GetTypeSystem(); TypeSystemClang *clang_ast = - llvm::dyn_cast_or_null(user_type.GetTypeSystem()); + ts.dyn_cast_or_null(); if (!clang_ast) { LLDB_LOG(log, "Skipped a definition because it has no Clang AST"); Index: lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.h =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.h +++ lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.h @@ -177,7 +177,8 @@ class LLDBPreprocessorCallbacks; LLDBPreprocessorCallbacks *m_pp_callbacks; ///< Called when the preprocessor ///encounters module imports - std::unique_ptr m_ast_context; + std::shared_ptr m_ast_context; + std::weak_ptr m_ast_context_wp; std::vector m_include_directories; /// File name used for the user expression. Index: lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangExpressionParser.cpp @@ -701,8 +701,10 @@ m_compiler->createASTContext(); clang::ASTContext &ast_context = m_compiler->getASTContext(); - m_ast_context = std::make_unique( + m_ast_context = std::make_shared( "Expression ASTContext for '" + m_filename + "'", ast_context); + m_ast_context_wp = m_ast_context; + m_ast_context->SetCanonicalWP(&m_ast_context_wp); std::string module_name("$__lldb_module"); Index: lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangModulesDeclVendor.cpp @@ -125,7 +125,8 @@ ImportedModuleSet m_user_imported_modules; // We assume that every ASTContext has an TypeSystemClang, so we also store // a custom TypeSystemClang for our internal ASTContext. - std::unique_ptr m_ast_context; + std::shared_ptr m_ast_context; + std::weak_ptr m_ast_context_wp; }; } // anonymous namespace @@ -190,8 +191,10 @@ // Initialize our TypeSystemClang. m_ast_context = - std::make_unique("ClangModulesDeclVendor ASTContext", + std::make_shared("ClangModulesDeclVendor ASTContext", m_compiler_instance->getASTContext()); + m_ast_context_wp = m_ast_context; + m_ast_context->SetCanonicalWP(&m_ast_context_wp); } void ClangModulesDeclVendorImpl::ReportModuleExportsHelper( Index: lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.h =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.h +++ lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.h @@ -97,7 +97,7 @@ /// The persistent decl. clang::NamedDecl *m_decl = nullptr; /// The TypeSystemClang for the ASTContext of m_decl. - TypeSystemClang *m_context = nullptr; + lldb::TypeSystemWP *m_context = nullptr; }; typedef llvm::DenseMap PersistentDeclMap; Index: lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangPersistentVariables.cpp @@ -87,12 +87,12 @@ void ClangPersistentVariables::RegisterPersistentDecl(ConstString name, clang::NamedDecl *decl, TypeSystemClang *ctx) { - PersistentDecl p = {decl, ctx}; + PersistentDecl p = {decl, ctx->GetCanonicalWP()}; m_persistent_decls.insert(std::make_pair(name.GetCString(), p)); if (clang::EnumDecl *enum_decl = llvm::dyn_cast(decl)) { for (clang::EnumConstantDecl *enumerator_decl : enum_decl->enumerators()) { - p = {enumerator_decl, ctx}; + p = {enumerator_decl, ctx->GetCanonicalWP()}; m_persistent_decls.insert(std::make_pair( ConstString(enumerator_decl->getNameAsString()).GetCString(), p)); } Index: lldb/source/Plugins/ExpressionParser/Clang/ClangUtil.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/ClangUtil.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/ClangUtil.cpp @@ -19,7 +19,7 @@ if (!ct) return false; - if (llvm::dyn_cast_or_null(ct.GetTypeSystem()) == nullptr) + if (!ct.GetTypeSystem().dyn_cast_or_null()) return false; if (!ct.GetOpaqueQualType()) @@ -54,7 +54,8 @@ QualType qual_type(GetQualType(ct)); qual_type.removeLocalFastQualifiers(); - return CompilerType(ct.GetTypeSystem(), qual_type.getAsOpaquePtr()); + return CompilerType(ct.GetTypeSystem().GetCanonicalWP(), + qual_type.getAsOpaquePtr()); } clang::TagDecl *ClangUtil::GetAsTagDecl(const CompilerType &type) { Index: lldb/source/Plugins/ExpressionParser/Clang/NameSearchContext.cpp =================================================================== --- lldb/source/Plugins/ExpressionParser/Clang/NameSearchContext.cpp +++ lldb/source/Plugins/ExpressionParser/Clang/NameSearchContext.cpp @@ -19,8 +19,8 @@ if (!type.IsValid()) return nullptr; - TypeSystemClang *lldb_ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + TypeSystemClang *lldb_ast = ts.dyn_cast_or_null(); if (!lldb_ast) return nullptr; @@ -46,8 +46,8 @@ if (m_function_types.count(type)) return nullptr; - TypeSystemClang *lldb_ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + TypeSystemClang *lldb_ast = ts.dyn_cast_or_null(); if (!lldb_ast) return nullptr; Index: lldb/source/Plugins/Language/CPlusPlus/BlockPointer.cpp =================================================================== --- lldb/source/Plugins/Language/CPlusPlus/BlockPointer.cpp +++ lldb/source/Plugins/Language/CPlusPlus/BlockPointer.cpp @@ -49,8 +49,10 @@ return; } - TypeSystemClang *clang_ast_context = - llvm::cast(block_pointer_type.GetTypeSystem()); + auto ts = block_pointer_type.GetTypeSystem(); + auto clang_ast_context = ts.dyn_cast_or_null(); + if (!clang_ast_context) + return; std::shared_ptr clang_ast_importer; auto *state = target_sp->GetPersistentExpressionStateForLanguage( Index: lldb/source/Plugins/Language/CPlusPlus/Coroutines.cpp =================================================================== --- lldb/source/Plugins/Language/CPlusPlus/Coroutines.cpp +++ lldb/source/Plugins/Language/CPlusPlus/Coroutines.cpp @@ -100,8 +100,8 @@ if (!ptr_sp) return false; - TypeSystemClang *ast_ctx = llvm::dyn_cast_or_null( - valobj_sp->GetCompilerType().GetTypeSystem()); + auto ts = valobj_sp->GetCompilerType().GetTypeSystem(); + TypeSystemClang *ast_ctx = ts.dyn_cast_or_null(); if (!ast_ctx) return false; Index: lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp =================================================================== --- lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp +++ lldb/source/Plugins/Language/CPlusPlus/LibCxx.cpp @@ -291,8 +291,8 @@ auto addr(m_pair_ptr->GetValueAsUnsigned(LLDB_INVALID_ADDRESS)); m_pair_ptr = nullptr; if (addr && addr != LLDB_INVALID_ADDRESS) { - TypeSystemClang *ast_ctx = - llvm::dyn_cast_or_null(pair_type.GetTypeSystem()); + auto ts = pair_type.GetTypeSystem(); + auto ast_ctx = ts.dyn_cast_or_null(); if (!ast_ctx) return false; @@ -460,8 +460,8 @@ if (addr == 0 || addr == LLDB_INVALID_ADDRESS) return false; - TypeSystemClang *ast_ctx = - llvm::dyn_cast_or_null(pair_type.GetTypeSystem()); + auto ts = pair_type.GetTypeSystem(); + auto ast_ctx = ts.dyn_cast_or_null(); if (!ast_ctx) return false; Index: lldb/source/Plugins/Language/CPlusPlus/LibCxxMap.cpp =================================================================== --- lldb/source/Plugins/Language/CPlusPlus/LibCxxMap.cpp +++ lldb/source/Plugins/Language/CPlusPlus/LibCxxMap.cpp @@ -249,7 +249,7 @@ static ConstString g_tree_("__tree_"); static ConstString g_pair3("__pair3_"); - if (m_element_type.GetOpaqueQualType() && m_element_type.GetTypeSystem()) + if (m_element_type.IsValid()) return true; m_element_type.Clear(); ValueObjectSP deref; @@ -295,8 +295,8 @@ UINT32_MAX) { m_skip_size = bit_offset / 8u; } else { - TypeSystemClang *ast_ctx = - llvm::dyn_cast_or_null(node_type.GetTypeSystem()); + auto ts = node_type.GetTypeSystem(); + TypeSystemClang *ast_ctx = ts.dyn_cast_or_null(); if (!ast_ctx) return; CompilerType tree_node_type = ast_ctx->CreateStructForIdentifier( Index: lldb/source/Plugins/Language/ObjC/CoreMedia.cpp =================================================================== --- lldb/source/Plugins/Language/ObjC/CoreMedia.cpp +++ lldb/source/Plugins/Language/ObjC/CoreMedia.cpp @@ -25,7 +25,9 @@ if (!type.IsValid()) return false; - TypeSystem *type_system = type.GetTypeSystem(); + auto type_system = type.GetTypeSystem(); + if (!type_system) + return false; // fetch children by offset to compensate for potential lack of debug info auto int64_ty = type_system->GetBuiltinTypeForEncodingAndBitSize(eEncodingSint, 64); Index: lldb/source/Plugins/Language/ObjC/NSArray.cpp =================================================================== --- lldb/source/Plugins/Language/ObjC/NSArray.cpp +++ lldb/source/Plugins/Language/ObjC/NSArray.cpp @@ -467,7 +467,7 @@ *valobj_sp->GetExecutionContextRef().GetTargetSP()); if (clang_ast_context) m_id_type = CompilerType( - clang_ast_context, + clang_ast_context->GetCanonicalWP(), clang_ast_context->getASTContext().ObjCBuiltinIdTy.getAsOpaquePtr()); if (valobj_sp->GetProcessSP()) m_ptr_size = valobj_sp->GetProcessSP()->GetAddressByteSize(); Index: lldb/source/Plugins/Language/ObjC/NSIndexPath.cpp =================================================================== --- lldb/source/Plugins/Language/ObjC/NSIndexPath.cpp +++ lldb/source/Plugins/Language/ObjC/NSIndexPath.cpp @@ -49,7 +49,7 @@ bool Update() override { m_impl.Clear(); - TypeSystem *type_system = m_backend.GetCompilerType().GetTypeSystem(); + auto type_system = m_backend.GetCompilerType().GetTypeSystem(); if (!type_system) return false; Index: lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.h =================================================================== --- lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.h +++ lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.h @@ -37,7 +37,8 @@ bool FinishDecl(clang::ObjCInterfaceDecl *decl); ObjCLanguageRuntime &m_runtime; - TypeSystemClang m_ast_ctx; + std::shared_ptr m_ast_ctx; + std::weak_ptr m_ast_ctx_wp; ObjCLanguageRuntime::EncodingToTypeSP m_type_realizer_sp; AppleObjCExternalASTSource *m_external_source; Index: lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.cpp =================================================================== --- lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.cpp +++ lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCDeclVendor.cpp @@ -120,7 +120,7 @@ void StartTranslationUnit(clang::ASTConsumer *Consumer) override { clang::TranslationUnitDecl *translation_unit_decl = - m_decl_vendor.m_ast_ctx.getASTContext().getTranslationUnitDecl(); + m_decl_vendor.m_ast_ctx->getASTContext().getTranslationUnitDecl(); translation_unit_decl->setHasExternalVisibleStorage(); translation_unit_decl->setHasExternalLexicalStorage(); } @@ -131,14 +131,16 @@ AppleObjCDeclVendor::AppleObjCDeclVendor(ObjCLanguageRuntime &runtime) : ClangDeclVendor(eAppleObjCDeclVendor), m_runtime(runtime), - m_ast_ctx( - "AppleObjCDeclVendor AST", - runtime.GetProcess()->GetTarget().GetArchitecture().GetTriple()), m_type_realizer_sp(m_runtime.GetEncodingToType()) { + m_ast_ctx = std::make_shared( + "AppleObjCDeclVendor AST", + runtime.GetProcess()->GetTarget().GetArchitecture().GetTriple()); + m_ast_ctx_wp = m_ast_ctx; + m_ast_ctx->SetCanonicalWP(&m_ast_ctx_wp); m_external_source = new AppleObjCExternalASTSource(*this); llvm::IntrusiveRefCntPtr external_source_owning_ptr( m_external_source); - m_ast_ctx.getASTContext().setExternalSource(external_source_owning_ptr); + m_ast_ctx->getASTContext().setExternalSource(external_source_owning_ptr); } clang::ObjCInterfaceDecl * @@ -148,7 +150,7 @@ if (iter != m_isa_to_interface.end()) return iter->second; - clang::ASTContext &ast_ctx = m_ast_ctx.getASTContext(); + clang::ASTContext &ast_ctx = m_ast_ctx->getASTContext(); ObjCLanguageRuntime::ClassDescriptorSP descriptor = m_runtime.GetClassDescriptorFromISA(isa); @@ -167,7 +169,7 @@ ClangASTMetadata meta_data; meta_data.SetISAPtr(isa); - m_ast_ctx.SetMetadata(new_iface_decl, meta_data); + m_ast_ctx->SetMetadata(new_iface_decl, meta_data); new_iface_decl->setHasExternalVisibleStorage(); new_iface_decl->setHasExternalLexicalStorage(); @@ -398,7 +400,7 @@ Log *log( GetLog(LLDBLog::Expressions)); // FIXME - a more appropriate log channel? - ClangASTMetadata *metadata = m_ast_ctx.GetMetadata(interface_decl); + ClangASTMetadata *metadata = m_ast_ctx->GetMetadata(interface_decl); ObjCLanguageRuntime::ObjCISA objc_isa = 0; if (metadata) objc_isa = metadata->GetISAPtr(); @@ -428,7 +430,7 @@ return; FinishDecl(superclass_decl); - clang::ASTContext &context = m_ast_ctx.getASTContext(); + clang::ASTContext &context = m_ast_ctx->getASTContext(); interface_decl->setSuperClass(context.getTrivialTypeSourceInfo( context.getObjCInterfaceType(superclass_decl))); }; @@ -441,7 +443,7 @@ ObjCRuntimeMethodType method_type(types); clang::ObjCMethodDecl *method_decl = method_type.BuildMethod( - m_ast_ctx, interface_decl, name, true, m_type_realizer_sp); + *m_ast_ctx, interface_decl, name, true, m_type_realizer_sp); LLDB_LOGF(log, "[ AOTV::FD] Instance method [%s] [%s]", name, types); @@ -459,7 +461,7 @@ ObjCRuntimeMethodType method_type(types); clang::ObjCMethodDecl *method_decl = method_type.BuildMethod( - m_ast_ctx, interface_decl, name, false, m_type_realizer_sp); + *m_ast_ctx, interface_decl, name, false, m_type_realizer_sp); LLDB_LOGF(log, "[ AOTV::FD] Class method [%s] [%s]", name, types); @@ -482,14 +484,14 @@ name, type, offset_ptr); CompilerType ivar_type = m_runtime.GetEncodingToType()->RealizeType( - m_ast_ctx, type, for_expression); + *m_ast_ctx, type, for_expression); if (ivar_type.IsValid()) { clang::TypeSourceInfo *const type_source_info = nullptr; const bool is_synthesized = false; clang::ObjCIvarDecl *ivar_decl = clang::ObjCIvarDecl::Create( - m_ast_ctx.getASTContext(), interface_decl, clang::SourceLocation(), - clang::SourceLocation(), &m_ast_ctx.getASTContext().Idents.get(name), + m_ast_ctx->getASTContext(), interface_decl, clang::SourceLocation(), + clang::SourceLocation(), &m_ast_ctx->getASTContext().Idents.get(name), ClangUtil::GetQualType(ivar_type), type_source_info, // TypeSourceInfo * clang::ObjCIvarDecl::Public, nullptr, is_synthesized); @@ -541,7 +543,7 @@ do { // See if the type is already in our ASTContext. - clang::ASTContext &ast_ctx = m_ast_ctx.getASTContext(); + clang::ASTContext &ast_ctx = m_ast_ctx->getASTContext(); clang::IdentifierInfo &identifier_info = ast_ctx.Idents.get(name.GetStringRef()); @@ -559,7 +561,7 @@ ast_ctx.getObjCInterfaceType(result_iface_decl); uint64_t isa_value = LLDB_INVALID_ADDRESS; - ClangASTMetadata *metadata = m_ast_ctx.GetMetadata(result_iface_decl); + ClangASTMetadata *metadata = m_ast_ctx->GetMetadata(result_iface_decl); if (metadata) isa_value = metadata->GetISAPtr(); @@ -568,7 +570,7 @@ result_iface_type.getAsString(), isa_value); } - decls.push_back(m_ast_ctx.GetCompilerDecl(result_iface_decl)); + decls.push_back(m_ast_ctx->GetCompilerDecl(result_iface_decl)); ret++; break; } else { @@ -609,7 +611,7 @@ new_iface_type.getAsString(), (uint64_t)isa); } - decls.push_back(m_ast_ctx.GetCompilerDecl(iface_decl)); + decls.push_back(m_ast_ctx->GetCompilerDecl(iface_decl)); ret++; break; } while (false); Index: lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTypeEncodingParser.cpp =================================================================== --- lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTypeEncodingParser.cpp +++ lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTypeEncodingParser.cpp @@ -24,10 +24,14 @@ AppleObjCTypeEncodingParser::AppleObjCTypeEncodingParser( ObjCLanguageRuntime &runtime) : ObjCLanguageRuntime::EncodingToType(), m_runtime(runtime) { - if (!m_scratch_ast_ctx_up) - m_scratch_ast_ctx_up = std::make_unique( - "AppleObjCTypeEncodingParser ASTContext", - runtime.GetProcess()->GetTarget().GetArchitecture().GetTriple()); + if (m_scratch_ast_ctx_sp) + return; + + m_scratch_ast_ctx_sp = std::make_shared( + "AppleObjCTypeEncodingParser ASTContext", + runtime.GetProcess()->GetTarget().GetArchitecture().GetTriple()); + m_scratch_ast_ctx_wp = m_scratch_ast_ctx_sp; + m_scratch_ast_ctx_sp->SetCanonicalWP(&m_scratch_ast_ctx_wp); } std::string AppleObjCTypeEncodingParser::ReadStructName(StringLexer &type) { @@ -155,7 +159,8 @@ if (!type.NextIf(_C_ARY_E)) return clang::QualType(); CompilerType array_type(ast_ctx.CreateArrayType( - CompilerType(&ast_ctx, element_type.getAsOpaquePtr()), size, false)); + CompilerType(ast_ctx.GetCanonicalWP(), element_type.getAsOpaquePtr()), + size, false)); return ClangUtil::GetQualType(array_type); } Index: lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.h =================================================================== --- lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.h +++ lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.h @@ -158,7 +158,8 @@ virtual CompilerType RealizeType(const char *name, bool for_expression); protected: - std::unique_ptr m_scratch_ast_ctx_up; + std::shared_ptr m_scratch_ast_ctx_sp; + std::weak_ptr m_scratch_ast_ctx_wp; }; class ObjCExceptionPrecondition : public BreakpointPrecondition { Index: lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.cpp =================================================================== --- lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.cpp +++ lldb/source/Plugins/LanguageRuntime/ObjC/ObjCLanguageRuntime.cpp @@ -330,8 +330,8 @@ CompilerType ObjCLanguageRuntime::EncodingToType::RealizeType(const char *name, bool for_expression) { - if (m_scratch_ast_ctx_up) - return RealizeType(*m_scratch_ast_ctx_up, name, for_expression); + if (m_scratch_ast_ctx_sp) + return RealizeType(*m_scratch_ast_ctx_sp, name, for_expression); return CompilerType(); } Index: lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.h =================================================================== --- lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.h +++ lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.h @@ -60,7 +60,10 @@ std::vector m_supported_architectures; private: - std::unique_ptr m_type_system_up; + std::mutex m_mutex; + TypeSystemClang *m_type_system; + lldb::TypeSystemSP m_type_system_sp; + lldb::TypeSystemWP m_type_system_wp; }; } // namespace platform_freebsd Index: lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.cpp =================================================================== --- lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.cpp +++ lldb/source/Plugins/Platform/FreeBSD/PlatformFreeBSD.cpp @@ -187,9 +187,16 @@ } CompilerType PlatformFreeBSD::GetSiginfoType(const llvm::Triple &triple) { - if (!m_type_system_up) - m_type_system_up.reset(new TypeSystemClang("siginfo", triple)); - TypeSystemClang *ast = m_type_system_up.get(); + { + std::lock_guard guard(m_mutex); + if (!m_type_system_sp) { + m_type_system = new TypeSystemClang("siginfo", triple); + m_type_system_sp.reset(m_type_system); + m_type_system_wp = m_type_system_sp; + m_type_system->SetCanonicalWP(&m_type_system_wp); + } + } + TypeSystemClang *ast = m_type_system; // generic types CompilerType int_type = ast->GetBasicType(eBasicTypeInt); Index: lldb/source/Plugins/Platform/Linux/PlatformLinux.h =================================================================== --- lldb/source/Plugins/Platform/Linux/PlatformLinux.h +++ lldb/source/Plugins/Platform/Linux/PlatformLinux.h @@ -65,7 +65,10 @@ std::vector m_supported_architectures; private: - std::unique_ptr m_type_system_up; + std::mutex m_mutex; + TypeSystemClang *m_type_system; + lldb::TypeSystemSP m_type_system_sp; + lldb::TypeSystemWP m_type_system_wp; }; } // namespace platform_linux Index: lldb/source/Plugins/Platform/Linux/PlatformLinux.cpp =================================================================== --- lldb/source/Plugins/Platform/Linux/PlatformLinux.cpp +++ lldb/source/Plugins/Platform/Linux/PlatformLinux.cpp @@ -312,9 +312,16 @@ } CompilerType PlatformLinux::GetSiginfoType(const llvm::Triple &triple) { - if (!m_type_system_up) - m_type_system_up.reset(new TypeSystemClang("siginfo", triple)); - TypeSystemClang *ast = m_type_system_up.get(); + { + std::lock_guard guard(m_mutex); + if (!m_type_system_sp) { + m_type_system = new TypeSystemClang("siginfo", triple); + m_type_system_sp.reset(m_type_system); + m_type_system_wp = m_type_system_sp; + m_type_system->SetCanonicalWP(&m_type_system_wp); + } + } + TypeSystemClang *ast = m_type_system; bool si_errno_then_code = true; Index: lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.h =================================================================== --- lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.h +++ lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.h @@ -62,7 +62,10 @@ std::vector m_supported_architectures; private: - std::unique_ptr m_type_system_up; + std::mutex m_mutex; + TypeSystemClang *m_type_system; + lldb::TypeSystemSP m_type_system_sp; + lldb::TypeSystemWP m_type_system_wp; }; } // namespace platform_netbsd Index: lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.cpp =================================================================== --- lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.cpp +++ lldb/source/Plugins/Platform/NetBSD/PlatformNetBSD.cpp @@ -206,9 +206,16 @@ } CompilerType PlatformNetBSD::GetSiginfoType(const llvm::Triple &triple) { - if (!m_type_system_up) - m_type_system_up.reset(new TypeSystemClang("siginfo", triple)); - TypeSystemClang *ast = m_type_system_up.get(); + { + std::lock_guard guard(m_mutex); + if (!m_type_system_sp) { + m_type_system = new TypeSystemClang("siginfo", triple); + m_type_system_sp.reset(m_type_system); + m_type_system_wp = m_type_system_sp; + m_type_system->SetCanonicalWP(&m_type_system_wp); + } + } + TypeSystemClang *ast = m_type_system; // generic types CompilerType int_type = ast->GetBasicType(eBasicTypeInt); Index: lldb/source/Plugins/Process/Utility/InferiorCallPOSIX.cpp =================================================================== --- lldb/source/Plugins/Process/Utility/InferiorCallPOSIX.cpp +++ lldb/source/Plugins/Process/Utility/InferiorCallPOSIX.cpp @@ -88,9 +88,11 @@ llvm::consumeError(type_system_or_err.takeError()); return false; } + auto ts = *type_system_or_err; + if (!ts) + return false; CompilerType void_ptr_type = - type_system_or_err->GetBasicTypeFromAST(eBasicTypeVoid) - .GetPointerType(); + ts->GetBasicTypeFromAST(eBasicTypeVoid).GetPointerType(); const ArchSpec arch = process->GetTarget().GetArchitecture(); MmapArgList args = process->GetTarget().GetPlatform()->GetMmapArgumentList( Index: lldb/source/Plugins/SymbolFile/Breakpad/SymbolFileBreakpad.h =================================================================== --- lldb/source/Plugins/SymbolFile/Breakpad/SymbolFileBreakpad.h +++ lldb/source/Plugins/SymbolFile/Breakpad/SymbolFileBreakpad.h @@ -126,7 +126,7 @@ llvm::DenseSet &searched_symbol_files, TypeMap &types) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override { return llvm::make_error( "SymbolFileBreakpad does not support GetTypeSystemForLanguage", Index: lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp +++ lldb/source/Plugins/SymbolFile/DWARF/DWARFASTParserClang.cpp @@ -223,8 +223,10 @@ lldbassert(started && "Unable to start a class type definition."); TypeSystemClang::CompleteTagDeclarationDefinition(type); const clang::TagDecl *td = ClangUtil::GetAsTagDecl(type); - auto &ts = llvm::cast(*type.GetTypeSystem()); - ts.GetMetadata(td)->SetIsForcefullyCompleted(); + auto ts_sp = type.GetTypeSystem(); + auto ts = ts_sp.dyn_cast_or_null(); + if (ts) + ts->GetMetadata(td)->SetIsForcefullyCompleted(); } /// Complete a type from debug info, or mark it as forcefully completed if @@ -814,8 +816,9 @@ CompilerType enumerator_clang_type; CompilerType clang_type; - clang_type.SetCompilerType( - &m_ast, dwarf->GetForwardDeclDieToClangType().lookup(die.GetDIE())); + clang_type = + CompilerType(m_ast.GetCanonicalWP(), + dwarf->GetForwardDeclDieToClangType().lookup(die.GetDIE())); if (!clang_type) { if (attrs.type.IsValid()) { Type *enumerator_type = @@ -1383,9 +1386,8 @@ const lldb::ModuleSP &module_sp, std::vector> &base_classes, ClangASTImporter::LayoutInfo &layout_info) { - - TypeSystemClang *ast = - llvm::dyn_cast_or_null(class_clang_type.GetTypeSystem()); + auto ts = class_clang_type.GetTypeSystem(); + TypeSystemClang *ast = ts.dyn_cast_or_null(); if (ast == nullptr) return; @@ -1751,8 +1753,9 @@ assert(tag_decl_kind != -1); (void)tag_decl_kind; bool clang_type_was_created = false; - clang_type.SetCompilerType( - &m_ast, dwarf->GetForwardDeclDieToClangType().lookup(die.GetDIE())); + clang_type = + CompilerType(m_ast.GetCanonicalWP(), + dwarf->GetForwardDeclDieToClangType().lookup(die.GetDIE())); if (!clang_type) { clang::DeclContext *decl_ctx = GetClangDeclContextContainingDIE(die, nullptr); @@ -2672,7 +2675,12 @@ const CompilerType &int_type, const DWARFFormValue &form_value) const { clang::QualType qt = ClangUtil::GetQualType(int_type); assert(qt->isIntegralOrEnumerationType()); - TypeSystemClang &ts = *llvm::cast(int_type.GetTypeSystem()); + auto ts_sp = int_type.GetTypeSystem(); + TypeSystemClang *ts_ptr = ts_sp.dyn_cast_or_null(); + if (!ts_ptr) + return llvm::createStringError(llvm::inconvertibleErrorCode(), + "TypeSystem not clang"); + TypeSystemClang &ts = *ts_ptr; clang::ASTContext &ast = ts.getASTContext(); const unsigned type_bits = ast.getIntWidth(qt); @@ -3007,8 +3015,8 @@ FieldInfo last_field_info; ModuleSP module_sp = parent_die.GetDWARF()->GetObjectFile()->GetModule(); - TypeSystemClang *ast = - llvm::dyn_cast_or_null(class_clang_type.GetTypeSystem()); + auto ts = class_clang_type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (ast == nullptr) return false; Index: lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h =================================================================== --- lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h +++ lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.h @@ -210,7 +210,7 @@ lldb::TypeClass type_mask, lldb_private::TypeList &type_list) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; lldb_private::CompilerDeclContext FindNamespace( @@ -300,8 +300,7 @@ lldb_private::FileSpec GetFile(DWARFUnit &unit, size_t file_idx); - static llvm::Expected - GetTypeSystem(DWARFUnit &unit); + static llvm::Expected GetTypeSystem(DWARFUnit &unit); static DWARFASTParser *GetDWARFParser(DWARFUnit &unit); Index: lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp +++ lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARF.cpp @@ -432,16 +432,16 @@ return m_unique_ast_type_map; } -llvm::Expected +llvm::Expected SymbolFileDWARF::GetTypeSystemForLanguage(LanguageType language) { if (SymbolFileDWARFDebugMap *debug_map_symfile = GetDebugMapSymfile()) return debug_map_symfile->GetTypeSystemForLanguage(language); auto type_system_or_err = m_objfile_sp->GetModule()->GetTypeSystemForLanguage(language); - if (type_system_or_err) { - type_system_or_err->SetSymbolFile(this); - } + if (type_system_or_err) + if (auto ts = *type_system_or_err) + ts->SetSymbolFile(this); return type_system_or_err; } @@ -830,7 +830,10 @@ "Unable to parse function"); return nullptr; } - DWARFASTParser *dwarf_ast = type_system_or_err->GetDWARFParser(); + auto ts = *type_system_or_err; + if (!ts) + return nullptr; + DWARFASTParser *dwarf_ast = ts->GetDWARFParser(); if (!dwarf_ast) return nullptr; @@ -876,7 +879,12 @@ return ConstString(); } - DWARFASTParser *dwarf_ast = type_system_or_err->GetDWARFParser(); + auto ts = *type_system_or_err; + if (!ts) { + LLDB_LOG(GetLog(LLDBLog::Symbols), "Type system no longer live"); + return ConstString(); + } + DWARFASTParser *dwarf_ast = ts->GetDWARFParser(); if (!dwarf_ast) return ConstString(); @@ -1556,10 +1564,8 @@ compiler_type_no_qualifiers.GetOpaqueQualType())) { return true; } - TypeSystem *type_system = compiler_type.GetTypeSystem(); - - TypeSystemClang *clang_type_system = - llvm::dyn_cast_or_null(type_system); + auto type_system = compiler_type.GetTypeSystem(); + auto clang_type_system = type_system.dyn_cast_or_null(); if (!clang_type_system) return false; DWARFASTParserClang *ast_parser = @@ -1569,9 +1575,8 @@ bool SymbolFileDWARF::CompleteType(CompilerType &compiler_type) { std::lock_guard guard(GetModuleMutex()); - - TypeSystemClang *clang_type_system = - llvm::dyn_cast_or_null(compiler_type.GetTypeSystem()); + auto ts = compiler_type.GetTypeSystem(); + TypeSystemClang *clang_type_system = ts.dyn_cast_or_null(); if (clang_type_system) { DWARFASTParserClang *ast_parser = static_cast(clang_type_system->GetDWARFParser()); @@ -2150,7 +2155,7 @@ return false; } - if (decl_ctx_type_system == &type_system_or_err.get()) + if (decl_ctx_type_system == type_system_or_err->get()) return true; // The type systems match, return true // The namespace AST was valid, and it does not match... @@ -2908,7 +2913,7 @@ // use this to ensure any matches we find are in a language that this // type system supports const LanguageType language = dwarf_decl_ctx.GetLanguage(); - TypeSystem *type_system = nullptr; + TypeSystemSP type_system = nullptr; if (language != eLanguageTypeUnknown) { auto type_system_or_err = GetTypeSystemForLanguage(language); if (auto err = type_system_or_err.takeError()) { @@ -2916,7 +2921,7 @@ "Cannot get TypeSystem for language {}", Language::GetNameForLanguageType(language)); } else { - type_system = &type_system_or_err.get(); + type_system = *type_system_or_err; } } @@ -3012,8 +3017,11 @@ "Unable to parse type"); return {}; } + auto ts = *type_system_or_err; + if (!ts) + return {}; - DWARFASTParser *dwarf_ast = type_system_or_err->GetDWARFParser(); + DWARFASTParser *dwarf_ast = ts->GetDWARFParser(); if (!dwarf_ast) return {}; @@ -4021,8 +4029,8 @@ auto ts_or_err = GetTypeSystemForLanguage(eLanguageTypeC_plus_plus); if (!ts_or_err) return; - TypeSystemClang *clang = - llvm::dyn_cast_or_null(&ts_or_err.get()); + auto ts = *ts_or_err; + TypeSystemClang *clang = llvm::dyn_cast_or_null(ts.get()); if (!clang) return; clang->Dump(s.AsRawOstream()); @@ -4065,7 +4073,8 @@ return m_dwp_symfile; } -llvm::Expected SymbolFileDWARF::GetTypeSystem(DWARFUnit &unit) { +llvm::Expected +SymbolFileDWARF::GetTypeSystem(DWARFUnit &unit) { return unit.GetSymbolFileDWARF().GetTypeSystemForLanguage(GetLanguage(unit)); } @@ -4076,7 +4085,9 @@ "Unable to get DWARFASTParser"); return nullptr; } - return type_system_or_err->GetDWARFParser(); + if (auto ts = *type_system_or_err) + return ts->GetDWARFParser(); + return nullptr; } CompilerDecl SymbolFileDWARF::GetDecl(const DWARFDIE &die) { Index: lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h =================================================================== --- lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h +++ lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.h @@ -34,7 +34,7 @@ void GetObjCMethods(lldb_private::ConstString class_name, llvm::function_ref callback) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; DWARFDIE Index: lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.cpp +++ lldb/source/Plugins/SymbolFile/DWARF/SymbolFileDWARFDwo.cpp @@ -118,7 +118,7 @@ die, type_name, must_be_implementation); } -llvm::Expected +llvm::Expected SymbolFileDWARFDwo::GetTypeSystemForLanguage(LanguageType language) { return GetBaseSymbolFile().GetTypeSystemForLanguage(language); } Index: lldb/source/Plugins/SymbolFile/NativePDB/PdbAstBuilder.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/NativePDB/PdbAstBuilder.cpp +++ lldb/source/Plugins/SymbolFile/NativePDB/PdbAstBuilder.cpp @@ -1428,7 +1428,7 @@ } CompilerType PdbAstBuilder::ToCompilerType(clang::QualType qt) { - return {&m_clang, qt.getAsOpaquePtr()}; + return {m_clang.GetCanonicalWP(), qt.getAsOpaquePtr()}; } CompilerDeclContext Index: lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h =================================================================== --- lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h +++ lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.h @@ -148,7 +148,7 @@ llvm::DenseSet &searched_symbol_files, TypeMap &types) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; CompilerDeclContext Index: lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp +++ lldb/source/Plugins/SymbolFile/NativePDB/SymbolFileNativePDB.cpp @@ -354,7 +354,8 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Symbols), std::move(err), "Failed to initialize"); } else { - ts_or_err->SetSymbolFile(this); + if (auto ts = *ts_or_err) + ts->SetSymbolFile(this); BuildParentMap(); } } @@ -383,7 +384,10 @@ auto ts_or_err = GetTypeSystemForLanguage(comp_unit->GetLanguage()); if (auto err = ts_or_err.takeError()) return *child_block; - PdbAstBuilder* ast_builder = ts_or_err->GetNativePDBParser(); + auto ts = *ts_or_err; + if (!ts) + return *child_block; + PdbAstBuilder* ast_builder = ts->GetNativePDBParser(); switch (sym.kind()) { case S_GPROC32: @@ -502,7 +506,10 @@ auto ts_or_err = GetTypeSystemForLanguage(comp_unit.GetLanguage()); if (auto err = ts_or_err.takeError()) return func_sp; - ts_or_err->GetNativePDBParser()->GetOrCreateFunctionDecl(func_id); + auto ts = *ts_or_err; + if (!ts) + return func_sp; + ts->GetNativePDBParser()->GetOrCreateFunctionDecl(func_id); return func_sp; } @@ -798,7 +805,11 @@ auto ts_or_err = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); if (auto err = ts_or_err.takeError()) return nullptr; - PdbAstBuilder* ast_builder = ts_or_err->GetNativePDBParser(); + auto ts = *ts_or_err; + if (!ts) + return nullptr; + + PdbAstBuilder* ast_builder = ts->GetNativePDBParser(); clang::QualType qt = ast_builder->GetOrCreateType(best_decl_id); if (qt.isNull()) return nullptr; @@ -895,7 +906,11 @@ auto ts_or_err = GetTypeSystemForLanguage(comp_unit->GetLanguage()); if (auto err = ts_or_err.takeError()) return nullptr; - ts_or_err->GetNativePDBParser()->GetOrCreateVariableDecl(var_id); + auto ts = *ts_or_err; + if (!ts) + return nullptr; + + ts->GetNativePDBParser()->GetOrCreateVariableDecl(var_id); ModuleSP module_sp = GetObjectFile()->GetModule(); DWARFExpressionList location( @@ -1625,8 +1640,8 @@ auto ts_or_err = GetTypeSystemForLanguage(eLanguageTypeC_plus_plus); if (!ts_or_err) return; - TypeSystemClang *clang = - llvm::dyn_cast_or_null(&ts_or_err.get()); + auto ts = *ts_or_err; + TypeSystemClang *clang = llvm::dyn_cast_or_null(ts.get()); if (!clang) return; clang->GetNativePDBParser()->Dump(s); @@ -1838,7 +1853,11 @@ auto ts_or_err = GetTypeSystemForLanguage(comp_unit_sp->GetLanguage()); if (auto err = ts_or_err.takeError()) return nullptr; - ts_or_err->GetNativePDBParser()->GetOrCreateVariableDecl(scope_id, var_id); + auto ts = *ts_or_err; + if (!ts) + return nullptr; + + ts->GetNativePDBParser()->GetOrCreateVariableDecl(scope_id, var_id); } m_local_variables[toOpaqueUid(var_id)] = var_sp; return var_sp; @@ -1864,7 +1883,11 @@ auto ts_or_err = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); if (auto err = ts_or_err.takeError()) return nullptr; - ts_or_err->GetNativePDBParser()->GetOrCreateTypedefDecl(id); + auto ts = *ts_or_err; + if (!ts) + return nullptr; + + ts->GetNativePDBParser()->GetOrCreateTypedefDecl(id); Declaration decl; return std::make_shared( @@ -2001,7 +2024,11 @@ auto ts_or_err = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); if (auto err = ts_or_err.takeError()) return CompilerDecl(); - if (auto decl = ts_or_err->GetNativePDBParser()->GetOrCreateDeclForUid(uid)) + auto ts = *ts_or_err; + if (!ts) + return {}; + + if (auto decl = ts->GetNativePDBParser()->GetOrCreateDeclForUid(uid)) return *decl; return CompilerDecl(); } @@ -2011,7 +2038,11 @@ auto ts_or_err = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); if (auto err = ts_or_err.takeError()) return {}; - PdbAstBuilder *ast_builder = ts_or_err->GetNativePDBParser(); + auto ts = *ts_or_err; + if (!ts) + return {}; + + PdbAstBuilder *ast_builder = ts->GetNativePDBParser(); clang::DeclContext *context = ast_builder->GetOrCreateDeclContextForUid(PdbSymUid(uid)); if (!context) @@ -2025,7 +2056,11 @@ auto ts_or_err = GetTypeSystemForLanguage(lldb::eLanguageTypeC_plus_plus); if (auto err = ts_or_err.takeError()) return CompilerDeclContext(); - PdbAstBuilder *ast_builder = ts_or_err->GetNativePDBParser(); + auto ts = *ts_or_err; + if (!ts) + return {}; + + PdbAstBuilder *ast_builder = ts->GetNativePDBParser(); clang::DeclContext *context = ast_builder->GetParentDeclContext(PdbSymUid(uid)); if (!context) return CompilerDeclContext(); @@ -2063,9 +2098,8 @@ bool SymbolFileNativePDB::CompleteType(CompilerType &compiler_type) { std::lock_guard guard(GetModuleMutex()); - - TypeSystemClang *clang_type_system = - llvm::dyn_cast_or_null(compiler_type.GetTypeSystem()); + auto ts = compiler_type.GetTypeSystem(); + auto clang_type_system = ts.dyn_cast_or_null(); if (!clang_type_system) return false; @@ -2090,13 +2124,13 @@ return {}; } -llvm::Expected +llvm::Expected SymbolFileNativePDB::GetTypeSystemForLanguage(lldb::LanguageType language) { auto type_system_or_err = m_objfile_sp->GetModule()->GetTypeSystemForLanguage(language); - if (type_system_or_err) { - type_system_or_err->SetSymbolFile(this); - } + if (type_system_or_err) + if (auto ts = *type_system_or_err) + ts->SetSymbolFile(this); return type_system_or_err; } Index: lldb/source/Plugins/SymbolFile/PDB/PDBASTParser.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/PDB/PDBASTParser.cpp +++ lldb/source/Plugins/SymbolFile/PDB/PDBASTParser.cpp @@ -120,24 +120,31 @@ return clang_ast.GetBasicType(eBasicTypeBool); case PDB_BuiltinType::Long: if (width == ast.getTypeSize(ast.LongTy)) - return CompilerType(&clang_ast, ast.LongTy.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.LongTy.getAsOpaquePtr()); if (width == ast.getTypeSize(ast.LongLongTy)) - return CompilerType(&clang_ast, ast.LongLongTy.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.LongLongTy.getAsOpaquePtr()); break; case PDB_BuiltinType::ULong: if (width == ast.getTypeSize(ast.UnsignedLongTy)) - return CompilerType(&clang_ast, ast.UnsignedLongTy.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.UnsignedLongTy.getAsOpaquePtr()); if (width == ast.getTypeSize(ast.UnsignedLongLongTy)) - return CompilerType(&clang_ast, ast.UnsignedLongLongTy.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.UnsignedLongLongTy.getAsOpaquePtr()); break; case PDB_BuiltinType::WCharT: if (width == ast.getTypeSize(ast.WCharTy)) - return CompilerType(&clang_ast, ast.WCharTy.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.WCharTy.getAsOpaquePtr()); break; case PDB_BuiltinType::Char16: - return CompilerType(&clang_ast, ast.Char16Ty.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.Char16Ty.getAsOpaquePtr()); case PDB_BuiltinType::Char32: - return CompilerType(&clang_ast, ast.Char32Ty.getAsOpaquePtr()); + return CompilerType(clang_ast.GetCanonicalWP(), + ast.Char32Ty.getAsOpaquePtr()); case PDB_BuiltinType::Float: // Note: types `long double` and `double` have same bit size in MSVC and // there is no information in the PDB to distinguish them. So when falling Index: lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.h =================================================================== --- lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.h +++ lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.h @@ -153,7 +153,7 @@ lldb::TypeClass type_mask, lldb_private::TypeList &type_list) override; - llvm::Expected + llvm::Expected GetTypeSystemForLanguage(lldb::LanguageType language) override; lldb_private::CompilerDeclContext FindNamespace( Index: lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp =================================================================== --- lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp +++ lldb/source/Plugins/SymbolFile/PDB/SymbolFilePDB.cpp @@ -318,8 +318,9 @@ return nullptr; } + auto ts = *type_system_or_err; TypeSystemClang *clang_type_system = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_type_system) return nullptr; clang_type_system->GetPDBParser()->GetDeclForSymbol(pdb_func); @@ -568,8 +569,9 @@ return nullptr; } + auto ts = *type_system_or_err; TypeSystemClang *clang_type_system = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_type_system) return nullptr; PDBASTParser *pdb = clang_type_system->GetPDBParser(); @@ -604,9 +606,9 @@ "Unable to get dynamic array info for UID"); return false; } - + auto ts = *type_system_or_err; TypeSystemClang *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return false; @@ -626,9 +628,9 @@ "Unable to get decl for UID"); return CompilerDecl(); } - + auto ts = *type_system_or_err; TypeSystemClang *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return CompilerDecl(); @@ -657,8 +659,9 @@ return CompilerDeclContext(); } + auto ts = *type_system_or_err; TypeSystemClang *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return CompilerDeclContext(); @@ -687,8 +690,9 @@ return CompilerDeclContext(); } + auto ts = *type_system_or_err; TypeSystemClang *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return CompilerDeclContext(); @@ -716,8 +720,9 @@ return; } + auto ts = *type_system_or_err; TypeSystemClang *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return; @@ -1464,8 +1469,9 @@ return; } - auto *clang_type_system = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + auto ts = *type_system_or_err; + TypeSystemClang *clang_type_system = + llvm::dyn_cast_or_null(ts.get()); if (!clang_type_system) return; clang_type_system->Dump(s.AsRawOstream()); @@ -1656,12 +1662,13 @@ } } -llvm::Expected +llvm::Expected SymbolFilePDB::GetTypeSystemForLanguage(lldb::LanguageType language) { auto type_system_or_err = m_objfile_sp->GetModule()->GetTypeSystemForLanguage(language); if (type_system_or_err) { - type_system_or_err->SetSymbolFile(this); + if (auto ts = *type_system_or_err) + ts->SetSymbolFile(this); } return type_system_or_err; } @@ -1675,8 +1682,9 @@ return nullptr; } + auto ts = *type_system_or_err; auto *clang_type_system = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_type_system) return nullptr; @@ -1694,9 +1702,9 @@ "Unable to find namespace {}", name.AsCString()); return CompilerDeclContext(); } - + auto ts = *type_system_or_err; auto *clang_type_system = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + llvm::dyn_cast_or_null(ts.get()); if (!clang_type_system) return CompilerDeclContext(); @@ -1990,7 +1998,7 @@ return false; } - if (decl_ctx_type_system == &type_system_or_err.get()) + if (decl_ctx_type_system == type_system_or_err->get()) return true; // The type systems match, return true return false; Index: lldb/source/Plugins/SystemRuntime/MacOSX/AppleGetItemInfoHandler.cpp =================================================================== --- lldb/source/Plugins/SystemRuntime/MacOSX/AppleGetItemInfoHandler.cpp +++ lldb/source/Plugins/SystemRuntime/MacOSX/AppleGetItemInfoHandler.cpp @@ -162,11 +162,15 @@ eLanguageTypeC); if (auto err = type_system_or_err.takeError()) { LLDB_LOG_ERROR(log, std::move(err), - "Error inseting get-item-info function"); + "Error inserting get-item-info function"); return args_addr; } + auto ts = *type_system_or_err; + if (!ts) + return args_addr; + CompilerType get_item_info_return_type = - type_system_or_err->GetBasicTypeFromAST(eBasicTypeVoid) + ts->GetBasicTypeFromAST(eBasicTypeVoid) .GetPointerType(); Status error; @@ -174,7 +178,7 @@ get_item_info_return_type, get_item_info_arglist, thread.shared_from_this(), error); if (error.Fail() || get_item_info_caller == nullptr) { - LLDB_LOGF(log, "Error Inserting get-item-info function: \"%s\".", + LLDB_LOGF(log, "Error inserting get-item-info function: \"%s\".", error.AsCString()); return args_addr; } Index: lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h =================================================================== --- lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h +++ lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h @@ -13,7 +13,6 @@ #include #include -#include #include #include #include @@ -241,7 +240,7 @@ // Check that the type actually belongs to this TypeSystemClang. assert(qt->getAsTagDecl() == nullptr || &qt->getAsTagDecl()->getASTContext() == &getASTContext()); - return CompilerType(this, qt.getAsOpaquePtr()); + return CompilerType(GetCanonicalWP(), qt.getAsOpaquePtr()); } CompilerType GetTypeForDecl(clang::NamedDecl *decl); @@ -271,9 +270,10 @@ clang::NamedDecl *named_decl = *result.begin(); if (const RecordDeclType *record_decl = llvm::dyn_cast(named_decl)) - compiler_type.SetCompilerType( - this, clang::QualType(record_decl->getTypeForDecl(), 0) - .getAsOpaquePtr()); + compiler_type = + CompilerType(GetCanonicalWP(), + clang::QualType(record_decl->getTypeForDecl(), 0) + .getAsOpaquePtr()); } } @@ -1234,7 +1234,9 @@ /// Map from IsolatedASTKind to their actual TypeSystemClang instance. /// This map is lazily filled with sub-ASTs and should be accessed via /// `GetSubAST` (which lazily fills this map). - std::unordered_map> + llvm::DenseMap, + std::unique_ptr>>> m_isolated_asts; }; Index: lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp =================================================================== --- lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp +++ lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp @@ -1,4 +1,4 @@ -//===-- TypeSystemClang.cpp -----------------------------------------------===// +//===-- TypeSystemClang.cpp -----------------------------------------------==='// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. @@ -935,7 +935,7 @@ GetOpaqueCompilerType(&ast, basic_type); if (clang_type) - return CompilerType(this, clang_type); + return CompilerType(GetCanonicalWP(), clang_type); return CompilerType(); } @@ -1169,9 +1169,9 @@ bool TypeSystemClang::AreTypesSame(CompilerType type1, CompilerType type2, bool ignore_qualifiers) { - TypeSystemClang *ast = - llvm::dyn_cast_or_null(type1.GetTypeSystem()); - if (!ast || ast != type2.GetTypeSystem()) + auto type1_ts = type1.GetTypeSystem(); + TypeSystemClang *ast = type1_ts.dyn_cast_or_null(); + if (!ast || type1_ts != type2.GetTypeSystem()) return false; if (type1.GetOpaqueQualType() == type2.GetOpaqueQualType()) @@ -2857,9 +2857,9 @@ case clang::Type::ConstantArray: if (element_type_ptr) element_type_ptr->SetCompilerType( - this, llvm::cast(qual_type) - ->getElementType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getElementType() + .getAsOpaquePtr()); if (size) *size = llvm::cast(qual_type) ->getSize() @@ -2871,9 +2871,9 @@ case clang::Type::IncompleteArray: if (element_type_ptr) element_type_ptr->SetCompilerType( - this, llvm::cast(qual_type) - ->getElementType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getElementType() + .getAsOpaquePtr()); if (size) *size = 0; if (is_incomplete) @@ -2883,9 +2883,9 @@ case clang::Type::VariableArray: if (element_type_ptr) element_type_ptr->SetCompilerType( - this, llvm::cast(qual_type) - ->getElementType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getElementType() + .getAsOpaquePtr()); if (size) *size = 0; if (is_incomplete) @@ -2895,9 +2895,10 @@ case clang::Type::DependentSizedArray: if (element_type_ptr) element_type_ptr->SetCompilerType( - this, llvm::cast(qual_type) - ->getElementType() - .getAsOpaquePtr()); + GetCanonicalWP(), + llvm::cast(qual_type) + ->getElementType() + .getAsOpaquePtr()); if (size) *size = 0; if (is_incomplete) @@ -2938,7 +2939,8 @@ *size = ext_vector_type->getNumElements(); if (element_type) *element_type = - CompilerType(this, ext_vector_type->getElementType().getAsOpaquePtr()); + CompilerType(GetCanonicalWP(), + ext_vector_type->getElementType().getAsOpaquePtr()); } return true; } @@ -3105,7 +3107,8 @@ ++num_fields; } if (base_type_ptr) - *base_type_ptr = CompilerType(this, base_qual_type.getAsOpaquePtr()); + *base_type_ptr = + CompilerType(GetCanonicalWP(), base_qual_type.getAsOpaquePtr()); return num_fields; } } @@ -3139,7 +3142,7 @@ llvm::dyn_cast(qual_type.getTypePtr()); if (func) { if (index < func->getNumParams()) - return CompilerType(this, func->getParamType(index).getAsOpaquePtr()); + return CompilerType(GetCanonicalWP(), func->getParamType(index).getAsOpaquePtr()); } } return CompilerType(); @@ -3182,8 +3185,8 @@ qual_type->castAs(); QualType pointee_type = block_pointer_type->getPointeeType(); QualType function_pointer_type = m_ast_up->getPointerType(pointee_type); - *function_pointer_type_ptr = - CompilerType(this, function_pointer_type.getAsOpaquePtr()); + *function_pointer_type_ptr = CompilerType( + GetCanonicalWP(), function_pointer_type.getAsOpaquePtr()); } return true; } @@ -3288,20 +3291,21 @@ case clang::Type::ObjCObjectPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), + llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; case clang::Type::BlockPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; case clang::Type::Pointer: if (pointee_type) - pointee_type->SetCompilerType(this, + pointee_type->SetCompilerType(GetCanonicalWP(), llvm::cast(qual_type) ->getPointeeType() .getAsOpaquePtr()); @@ -3309,9 +3313,9 @@ case clang::Type::MemberPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; default: break; @@ -3340,19 +3344,21 @@ case clang::Type::ObjCObjectPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType().getAsOpaquePtr()); + GetCanonicalWP(), + llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; case clang::Type::BlockPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; case clang::Type::Pointer: if (pointee_type) - pointee_type->SetCompilerType(this, + pointee_type->SetCompilerType(GetCanonicalWP(), llvm::cast(qual_type) ->getPointeeType() .getAsOpaquePtr()); @@ -3360,23 +3366,23 @@ case clang::Type::MemberPointer: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; case clang::Type::LValueReference: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->desugar() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->desugar() + .getAsOpaquePtr()); return true; case clang::Type::RValueReference: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->desugar() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->desugar() + .getAsOpaquePtr()); return true; default: break; @@ -3398,18 +3404,18 @@ case clang::Type::LValueReference: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->desugar() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->desugar() + .getAsOpaquePtr()); if (is_rvalue) *is_rvalue = false; return true; case clang::Type::RValueReference: if (pointee_type) pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->desugar() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->desugar() + .getAsOpaquePtr()); if (is_rvalue) *is_rvalue = true; return true; @@ -3563,7 +3569,7 @@ llvm::cast(qual_type)->getKind() == clang::BuiltinType::ObjCId) { if (dynamic_pointee_type) - dynamic_pointee_type->SetCompilerType(this, type); + dynamic_pointee_type->SetCompilerType(GetCanonicalWP(), type); return true; } break; @@ -3581,9 +3587,10 @@ } if (dynamic_pointee_type) dynamic_pointee_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), + llvm::cast(qual_type) + ->getPointeeType() + .getAsOpaquePtr()); return true; } break; @@ -3618,7 +3625,7 @@ case clang::BuiltinType::Void: if (dynamic_pointee_type) dynamic_pointee_type->SetCompilerType( - this, pointee_qual_type.getAsOpaquePtr()); + GetCanonicalWP(), pointee_qual_type.getAsOpaquePtr()); return true; default: break; @@ -3650,7 +3657,7 @@ if (success) { if (dynamic_pointee_type) dynamic_pointee_type->SetCompilerType( - this, pointee_qual_type.getAsOpaquePtr()); + GetCanonicalWP(), pointee_qual_type.getAsOpaquePtr()); return true; } } @@ -3662,7 +3669,7 @@ if (check_objc) { if (dynamic_pointee_type) dynamic_pointee_type->SetCompilerType( - this, pointee_qual_type.getAsOpaquePtr()); + GetCanonicalWP(), pointee_qual_type.getAsOpaquePtr()); return true; } break; @@ -3759,7 +3766,7 @@ class_type_ptr->Clear(); else class_type_ptr->SetCompilerType( - type.GetTypeSystem(), + type.GetTypeSystem().GetCanonicalWP(), clang::QualType(obj_pointer_type->getInterfaceType(), 0) .getAsOpaquePtr()); } @@ -3849,14 +3856,15 @@ case clang::BuiltinType::ObjCClass: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, getASTContext().ObjCBuiltinClassTy.getAsOpaquePtr()); + GetCanonicalWP(), + getASTContext().ObjCBuiltinClassTy.getAsOpaquePtr()); builtin_type_flags |= eTypeIsPointer | eTypeIsObjC; break; case clang::BuiltinType::ObjCSel: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, getASTContext().CharTy.getAsOpaquePtr()); + GetCanonicalWP(), getASTContext().CharTy.getAsOpaquePtr()); builtin_type_flags |= eTypeIsPointer | eTypeIsObjC; break; @@ -3899,7 +3907,7 @@ case clang::Type::BlockPointer: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, qual_type->getPointeeType().getAsOpaquePtr()); + GetCanonicalWP(), qual_type->getPointeeType().getAsOpaquePtr()); return eTypeIsPointer | eTypeHasChildren | eTypeIsBlock; case clang::Type::Complex: { @@ -3923,9 +3931,9 @@ case clang::Type::VariableArray: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, llvm::cast(qual_type.getTypePtr()) - ->getElementType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type.getTypePtr()) + ->getElementType() + .getAsOpaquePtr()); return eTypeHasChildren | eTypeIsArray; case clang::Type::DependentName: @@ -3938,10 +3946,10 @@ case clang::Type::Enum: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, llvm::cast(qual_type) - ->getDecl() - ->getIntegerType() - .getAsOpaquePtr()); + GetCanonicalWP(), llvm::cast(qual_type) + ->getDecl() + ->getIntegerType() + .getAsOpaquePtr()); return eTypeIsEnumeration | eTypeHasValue; case clang::Type::FunctionProto: @@ -3955,9 +3963,10 @@ case clang::Type::RValueReference: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, llvm::cast(qual_type.getTypePtr()) - ->getPointeeType() - .getAsOpaquePtr()); + GetCanonicalWP(), + llvm::cast(qual_type.getTypePtr()) + ->getPointeeType() + .getAsOpaquePtr()); return eTypeHasChildren | eTypeIsReference | eTypeHasValue; case clang::Type::MemberPointer: @@ -3966,7 +3975,7 @@ case clang::Type::ObjCObjectPointer: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, qual_type->getPointeeType().getAsOpaquePtr()); + GetCanonicalWP(), qual_type->getPointeeType().getAsOpaquePtr()); return eTypeHasChildren | eTypeIsObjC | eTypeIsClass | eTypeIsPointer | eTypeHasValue; @@ -3978,7 +3987,7 @@ case clang::Type::Pointer: if (pointee_or_element_clang_type) pointee_or_element_clang_type->SetCompilerType( - this, qual_type->getPointeeType().getAsOpaquePtr()); + GetCanonicalWP(), qual_type->getPointeeType().getAsOpaquePtr()); return eTypeHasChildren | eTypeIsPointer | eTypeHasValue; case clang::Type::Record: @@ -5782,9 +5791,10 @@ objc_interface_type->getDecl(); if (class_interface_decl) { return CompilerType( - this, GetObjCFieldAtIndex(&getASTContext(), class_interface_decl, - idx, name, bit_offset_ptr, - bitfield_bit_size_ptr, is_bitfield_ptr)); + GetCanonicalWP(), + GetObjCFieldAtIndex(&getASTContext(), class_interface_decl, idx, + name, bit_offset_ptr, bitfield_bit_size_ptr, + is_bitfield_ptr)); } } break; @@ -5800,9 +5810,10 @@ clang::ObjCInterfaceDecl *class_interface_decl = objc_class_type->getInterface(); return CompilerType( - this, GetObjCFieldAtIndex(&getASTContext(), class_interface_decl, - idx, name, bit_offset_ptr, - bitfield_bit_size_ptr, is_bitfield_ptr)); + GetCanonicalWP(), + GetObjCFieldAtIndex(&getASTContext(), class_interface_decl, idx, + name, bit_offset_ptr, bitfield_bit_size_ptr, + is_bitfield_ptr)); } } break; @@ -7285,7 +7296,7 @@ CompilerType TypeSystemClang::GetTypeForFormatters(void *type) { if (type) - return ClangUtil::RemoveFastQualifiers(CompilerType(this, type)); + return ClangUtil::RemoveFastQualifiers(CompilerType(GetCanonicalWP(), type)); return CompilerType(); } @@ -7339,8 +7350,8 @@ uint32_t bitfield_bit_size) { if (!type.IsValid() || !field_clang_type.IsValid()) return nullptr; - TypeSystemClang *ast = - llvm::dyn_cast_or_null(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return nullptr; clang::ASTContext &clang_ast = ast->getASTContext(); @@ -7433,7 +7444,8 @@ if (!type) return; - TypeSystemClang *ast = llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return; @@ -7539,8 +7551,8 @@ void TypeSystemClang::SetIsPacked(const CompilerType &type) { if (type) { - TypeSystemClang *ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (ast) { clang::RecordDecl *record_decl = GetAsRecordDecl(type); @@ -7559,7 +7571,8 @@ if (!type.IsValid() || !var_type.IsValid()) return nullptr; - TypeSystemClang *ast = llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return nullptr; @@ -7871,8 +7884,8 @@ bool TypeSystemClang::SetObjCSuperClass( const CompilerType &type, const CompilerType &superclass_clang_type) { - TypeSystemClang *ast = - llvm::dyn_cast_or_null(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return false; clang::ASTContext &clang_ast = ast->getASTContext(); @@ -7900,7 +7913,8 @@ if (!type || !property_clang_type.IsValid() || property_name == nullptr || property_name[0] == '\0') return false; - TypeSystemClang *ast = llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return false; clang::ASTContext &clang_ast = ast->getASTContext(); @@ -8119,8 +8133,8 @@ if (class_interface_decl == nullptr) return nullptr; - TypeSystemClang *lldb_ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto lldb_ast = ts.dyn_cast_or_null(); if (lldb_ast == nullptr) return nullptr; clang::ASTContext &ast = lldb_ast->getASTContext(); @@ -8323,8 +8337,8 @@ if (qual_type.isNull()) return false; - TypeSystemClang *lldb_ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto lldb_ast = ts.dyn_cast_or_null(); if (lldb_ast == nullptr) return false; @@ -8408,7 +8422,8 @@ if (!enum_type || ConstString(name).IsEmpty()) return nullptr; - lldbassert(enum_type.GetTypeSystem() == static_cast(this)); + lldbassert(enum_type.GetTypeSystem().GetSharedPointer().get() == + static_cast(this)); lldb::opaque_compiler_type_t enum_opaque_compiler_type = enum_type.GetOpaqueQualType(); @@ -8475,8 +8490,8 @@ const CompilerType &pointee_type) { if (type && pointee_type.IsValid() && type.GetTypeSystem() == pointee_type.GetTypeSystem()) { - TypeSystemClang *ast = - llvm::dyn_cast(type.GetTypeSystem()); + auto ts = type.GetTypeSystem(); + auto ast = ts.dyn_cast_or_null(); if (!ast) return CompilerType(); return ast->GetType(ast->getASTContext().getMemberPointerType( @@ -9172,7 +9187,7 @@ StreamFile s(stdout, false); DumpTypeDescription(type, &s, level); - CompilerType ct(this, type); + CompilerType ct(GetCanonicalWP(), type); const clang::Type *clang_type = ClangUtil::GetQualType(ct).getTypePtr(); ClangASTMetadata *metadata = GetMetadata(clang_type); if (metadata) { @@ -9886,13 +9901,16 @@ "Couldn't get scratch TypeSystemClang"); return nullptr; } - ScratchTypeSystemClang &scratch_ast = - llvm::cast(type_system_or_err.get()); + auto ts = *type_system_or_err; + ScratchTypeSystemClang *scratch_ast = + llvm::dyn_cast_or_null(ts.get()); + if (!scratch_ast) + return nullptr; // If no dedicated sub-AST was requested, just return the main AST. if (ast_kind == DefaultAST) - return &scratch_ast; + return scratch_ast; // Search the sub-ASTs. - return &scratch_ast.GetIsolatedAST(*ast_kind); + return &scratch_ast->GetIsolatedAST(*ast_kind); } /// Returns a human-readable name that uniquely identifiers the sub-AST kind. @@ -9914,7 +9932,7 @@ typedef std::pair KeyAndTS; std::vector sorted_typesystems; for (const auto &a : m_isolated_asts) - sorted_typesystems.emplace_back(a.first, a.second.get()); + sorted_typesystems.emplace_back(a.first, a.second.first.get()); llvm::stable_sort(sorted_typesystems, llvm::less_first()); // Dump each sub-AST too. @@ -9977,7 +9995,7 @@ importer.ForgetSource(&getASTContext(), src_ctx); // Remove it as a source from all created sub-ASTs. for (const auto &a : m_isolated_asts) - importer.ForgetSource(&a.second->getASTContext(), src_ctx); + importer.ForgetSource(&a.second.first->getASTContext(), src_ctx); } std::unique_ptr ScratchTypeSystemClang::CreateASTSource() { @@ -9999,12 +10017,14 @@ ScratchTypeSystemClang::IsolatedASTKind feature) { auto found_ast = m_isolated_asts.find(feature); if (found_ast != m_isolated_asts.end()) - return *found_ast->second; + return *found_ast->second.first; // Couldn't find the requested sub-AST, so create it now. - std::unique_ptr new_ast; - new_ast.reset(new SpecializedScratchAST(GetSpecializedASTName(feature), - m_triple, CreateASTSource())); - m_isolated_asts[feature] = std::move(new_ast); - return *m_isolated_asts[feature]; + std::shared_ptr new_ast_sp = + std::make_shared(GetSpecializedASTName(feature), + m_triple, CreateASTSource()); + auto new_ast_up = std::make_unique>(new_ast_sp); + new_ast_sp->SetCanonicalWP(new_ast_up.get()); + m_isolated_asts[feature] = {new_ast_sp, std::move(new_ast_up)}; + return *m_isolated_asts[feature].first; } Index: lldb/source/Symbol/CompilerType.cpp =================================================================== --- lldb/source/Symbol/CompilerType.cpp +++ lldb/source/Symbol/CompilerType.cpp @@ -30,26 +30,30 @@ bool CompilerType::IsAggregateType() const { if (IsValid()) - return m_type_system->IsAggregateType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsAggregateType(m_type); return false; } bool CompilerType::IsAnonymousType() const { if (IsValid()) - return m_type_system->IsAnonymousType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsAnonymousType(m_type); return false; } bool CompilerType::IsScopedEnumerationType() const { if (IsValid()) - return m_type_system->IsScopedEnumerationType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsScopedEnumerationType(m_type); return false; } bool CompilerType::IsArrayType(CompilerType *element_type_ptr, uint64_t *size, bool *is_incomplete) const { if (IsValid()) - return m_type_system->IsArrayType(m_type, element_type_ptr, size, + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsArrayType(m_type, element_type_ptr, size, is_incomplete); if (element_type_ptr) @@ -64,43 +68,50 @@ bool CompilerType::IsVectorType(CompilerType *element_type, uint64_t *size) const { if (IsValid()) - return m_type_system->IsVectorType(m_type, element_type, size); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsVectorType(m_type, element_type, size); return false; } bool CompilerType::IsRuntimeGeneratedType() const { if (IsValid()) - return m_type_system->IsRuntimeGeneratedType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsRuntimeGeneratedType(m_type); return false; } bool CompilerType::IsCharType() const { if (IsValid()) - return m_type_system->IsCharType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsCharType(m_type); return false; } bool CompilerType::IsCompleteType() const { if (IsValid()) - return m_type_system->IsCompleteType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsCompleteType(m_type); return false; } bool CompilerType::IsConst() const { if (IsValid()) - return m_type_system->IsConst(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsConst(m_type); return false; } bool CompilerType::IsCStringType(uint32_t &length) const { if (IsValid()) - return m_type_system->IsCStringType(m_type, length); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsCStringType(m_type, length); return false; } bool CompilerType::IsFunctionType() const { if (IsValid()) - return m_type_system->IsFunctionType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsFunctionType(m_type); return false; } @@ -108,45 +119,52 @@ uint32_t CompilerType::IsHomogeneousAggregate(CompilerType *base_type_ptr) const { if (IsValid()) - return m_type_system->IsHomogeneousAggregate(m_type, base_type_ptr); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsHomogeneousAggregate(m_type, base_type_ptr); return 0; } size_t CompilerType::GetNumberOfFunctionArguments() const { if (IsValid()) - return m_type_system->GetNumberOfFunctionArguments(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumberOfFunctionArguments(m_type); return 0; } CompilerType CompilerType::GetFunctionArgumentAtIndex(const size_t index) const { if (IsValid()) - return m_type_system->GetFunctionArgumentAtIndex(m_type, index); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFunctionArgumentAtIndex(m_type, index); return CompilerType(); } bool CompilerType::IsFunctionPointerType() const { if (IsValid()) - return m_type_system->IsFunctionPointerType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsFunctionPointerType(m_type); return false; } bool CompilerType::IsBlockPointerType( CompilerType *function_pointer_type_ptr) const { if (IsValid()) - return m_type_system->IsBlockPointerType(m_type, function_pointer_type_ptr); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsBlockPointerType(m_type, function_pointer_type_ptr); return false; } bool CompilerType::IsIntegerType(bool &is_signed) const { if (IsValid()) - return m_type_system->IsIntegerType(m_type, is_signed); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsIntegerType(m_type, is_signed); return false; } bool CompilerType::IsEnumerationType(bool &is_signed) const { if (IsValid()) - return m_type_system->IsEnumerationType(m_type, is_signed); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsEnumerationType(m_type, is_signed); return false; } @@ -156,13 +174,15 @@ bool CompilerType::IsBooleanType() const { if (IsValid()) - return m_type_system->IsBooleanType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsBooleanType(m_type); return false; } bool CompilerType::IsPointerType(CompilerType *pointee_type) const { if (IsValid()) { - return m_type_system->IsPointerType(m_type, pointee_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsPointerType(m_type, pointee_type); } if (pointee_type) pointee_type->Clear(); @@ -171,7 +191,8 @@ bool CompilerType::IsPointerOrReferenceType(CompilerType *pointee_type) const { if (IsValid()) { - return m_type_system->IsPointerOrReferenceType(m_type, pointee_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsPointerOrReferenceType(m_type, pointee_type); } if (pointee_type) pointee_type->Clear(); @@ -181,7 +202,8 @@ bool CompilerType::IsReferenceType(CompilerType *pointee_type, bool *is_rvalue) const { if (IsValid()) { - return m_type_system->IsReferenceType(m_type, pointee_type, is_rvalue); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsReferenceType(m_type, pointee_type, is_rvalue); } if (pointee_type) pointee_type->Clear(); @@ -190,14 +212,16 @@ bool CompilerType::ShouldTreatScalarValueAsAddress() const { if (IsValid()) - return m_type_system->ShouldTreatScalarValueAsAddress(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->ShouldTreatScalarValueAsAddress(m_type); return false; } bool CompilerType::IsFloatingPointType(uint32_t &count, bool &is_complex) const { if (IsValid()) { - return m_type_system->IsFloatingPointType(m_type, count, is_complex); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsFloatingPointType(m_type, count, is_complex); } count = 0; is_complex = false; @@ -206,13 +230,15 @@ bool CompilerType::IsDefined() const { if (IsValid()) - return m_type_system->IsDefined(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsDefined(m_type); return true; } bool CompilerType::IsPolymorphicClass() const { if (IsValid()) { - return m_type_system->IsPolymorphicClass(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsPolymorphicClass(m_type); } return false; } @@ -221,28 +247,31 @@ bool check_cplusplus, bool check_objc) const { if (IsValid()) - return m_type_system->IsPossibleDynamicType(m_type, dynamic_pointee_type, + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsPossibleDynamicType(m_type, dynamic_pointee_type, check_cplusplus, check_objc); return false; } bool CompilerType::IsScalarType() const { - if (!IsValid()) - return false; - - return m_type_system->IsScalarType(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsScalarType(m_type); + return false; } bool CompilerType::IsTypedefType() const { - if (!IsValid()) - return false; - return m_type_system->IsTypedefType(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsTypedefType(m_type); + return false; } bool CompilerType::IsVoidType() const { - if (!IsValid()) - return false; - return m_type_system->IsVoidType(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsVoidType(m_type); + return false; } bool CompilerType::IsPointerToScalarType() const { @@ -260,62 +289,68 @@ } bool CompilerType::IsBeingDefined() const { - if (!IsValid()) - return false; - return m_type_system->IsBeingDefined(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsBeingDefined(m_type); + return false; } // Type Completion bool CompilerType::GetCompleteType() const { - if (!IsValid()) - return false; - return m_type_system->GetCompleteType(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetCompleteType(m_type); + return false; } // AST related queries size_t CompilerType::GetPointerByteSize() const { if (m_type_system) - return m_type_system->GetPointerByteSize(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetPointerByteSize(); return 0; } ConstString CompilerType::GetTypeName() const { if (IsValid()) { - return m_type_system->GetTypeName(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeName(m_type); } return ConstString(""); } ConstString CompilerType::GetDisplayTypeName() const { if (IsValid()) - return m_type_system->GetDisplayTypeName(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetDisplayTypeName(m_type); return ConstString(""); } uint32_t CompilerType::GetTypeInfo( CompilerType *pointee_or_element_compiler_type) const { - if (!IsValid()) - return 0; - - return m_type_system->GetTypeInfo(m_type, pointee_or_element_compiler_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeInfo(m_type, + pointee_or_element_compiler_type); + return 0; } lldb::LanguageType CompilerType::GetMinimumLanguage() { - if (!IsValid()) - return lldb::eLanguageTypeC; - - return m_type_system->GetMinimumLanguage(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetMinimumLanguage(m_type); + return lldb::eLanguageTypeC; } lldb::TypeClass CompilerType::GetTypeClass() const { - if (!IsValid()) - return lldb::eTypeClassInvalid; - - return m_type_system->GetTypeClass(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeClass(m_type); + return lldb::eTypeClassInvalid; } -void CompilerType::SetCompilerType(TypeSystem *type_system, +void CompilerType::SetCompilerType(lldb::TypeSystemWP *type_system, lldb::opaque_compiler_type_t type) { m_type_system = type_system; m_type = type; @@ -323,7 +358,8 @@ unsigned CompilerType::GetTypeQualifiers() const { if (IsValid()) - return m_type_system->GetTypeQualifiers(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeQualifiers(m_type); return 0; } @@ -332,146 +368,160 @@ CompilerType CompilerType::GetArrayElementType(ExecutionContextScope *exe_scope) const { if (IsValid()) { - return m_type_system->GetArrayElementType(m_type, exe_scope); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetArrayElementType(m_type, exe_scope); } return CompilerType(); } CompilerType CompilerType::GetArrayType(uint64_t size) const { if (IsValid()) { - return m_type_system->GetArrayType(m_type, size); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetArrayType(m_type, size); } return CompilerType(); } CompilerType CompilerType::GetCanonicalType() const { if (IsValid()) - return m_type_system->GetCanonicalType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetCanonicalType(m_type); return CompilerType(); } CompilerType CompilerType::GetFullyUnqualifiedType() const { if (IsValid()) - return m_type_system->GetFullyUnqualifiedType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFullyUnqualifiedType(m_type); return CompilerType(); } CompilerType CompilerType::GetEnumerationIntegerType() const { if (IsValid()) - return m_type_system->GetEnumerationIntegerType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetEnumerationIntegerType(m_type); return CompilerType(); } int CompilerType::GetFunctionArgumentCount() const { if (IsValid()) { - return m_type_system->GetFunctionArgumentCount(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFunctionArgumentCount(m_type); } return -1; } CompilerType CompilerType::GetFunctionArgumentTypeAtIndex(size_t idx) const { if (IsValid()) { - return m_type_system->GetFunctionArgumentTypeAtIndex(m_type, idx); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFunctionArgumentTypeAtIndex(m_type, idx); } return CompilerType(); } CompilerType CompilerType::GetFunctionReturnType() const { if (IsValid()) { - return m_type_system->GetFunctionReturnType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFunctionReturnType(m_type); } return CompilerType(); } size_t CompilerType::GetNumMemberFunctions() const { if (IsValid()) { - return m_type_system->GetNumMemberFunctions(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumMemberFunctions(m_type); } return 0; } TypeMemberFunctionImpl CompilerType::GetMemberFunctionAtIndex(size_t idx) { if (IsValid()) { - return m_type_system->GetMemberFunctionAtIndex(m_type, idx); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetMemberFunctionAtIndex(m_type, idx); } return TypeMemberFunctionImpl(); } CompilerType CompilerType::GetNonReferenceType() const { if (IsValid()) - return m_type_system->GetNonReferenceType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNonReferenceType(m_type); return CompilerType(); } CompilerType CompilerType::GetPointeeType() const { if (IsValid()) { - return m_type_system->GetPointeeType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetPointeeType(m_type); } return CompilerType(); } CompilerType CompilerType::GetPointerType() const { if (IsValid()) { - return m_type_system->GetPointerType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetPointerType(m_type); } return CompilerType(); } CompilerType CompilerType::GetLValueReferenceType() const { if (IsValid()) - return m_type_system->GetLValueReferenceType(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetLValueReferenceType(m_type); + return CompilerType(); } CompilerType CompilerType::GetRValueReferenceType() const { if (IsValid()) - return m_type_system->GetRValueReferenceType(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetRValueReferenceType(m_type); + return CompilerType(); } CompilerType CompilerType::GetAtomicType() const { if (IsValid()) - return m_type_system->GetAtomicType(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetAtomicType(m_type); return CompilerType(); } CompilerType CompilerType::AddConstModifier() const { if (IsValid()) - return m_type_system->AddConstModifier(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->AddConstModifier(m_type); + return CompilerType(); } CompilerType CompilerType::AddVolatileModifier() const { if (IsValid()) - return m_type_system->AddVolatileModifier(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->AddVolatileModifier(m_type); + return CompilerType(); } CompilerType CompilerType::AddRestrictModifier() const { if (IsValid()) - return m_type_system->AddRestrictModifier(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->AddRestrictModifier(m_type); + return CompilerType(); } CompilerType CompilerType::CreateTypedef(const char *name, const CompilerDeclContext &decl_ctx, uint32_t payload) const { if (IsValid()) - return m_type_system->CreateTypedef(m_type, name, decl_ctx, payload); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->CreateTypedef(m_type, name, decl_ctx, payload); + return CompilerType(); } CompilerType CompilerType::GetTypedefedType() const { if (IsValid()) - return m_type_system->GetTypedefedType(m_type); - else - return CompilerType(); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypedefedType(m_type); + return CompilerType(); } // Create related types using the current type's AST @@ -479,7 +529,8 @@ CompilerType CompilerType::GetBasicTypeFromAST(lldb::BasicType basic_type) const { if (IsValid()) - return m_type_system->GetBasicTypeFromAST(basic_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetBasicTypeFromAST(basic_type); return CompilerType(); } // Exploring the type @@ -487,7 +538,8 @@ llvm::Optional CompilerType::GetBitSize(ExecutionContextScope *exe_scope) const { if (IsValid()) - return m_type_system->GetBitSize(m_type, exe_scope); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetBitSize(m_type, exe_scope); return {}; } @@ -500,35 +552,38 @@ llvm::Optional CompilerType::GetTypeBitAlign(ExecutionContextScope *exe_scope) const { if (IsValid()) - return m_type_system->GetTypeBitAlign(m_type, exe_scope); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeBitAlign(m_type, exe_scope); return {}; } lldb::Encoding CompilerType::GetEncoding(uint64_t &count) const { - if (!IsValid()) - return lldb::eEncodingInvalid; - - return m_type_system->GetEncoding(m_type, count); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetEncoding(m_type, count); + return lldb::eEncodingInvalid; } lldb::Format CompilerType::GetFormat() const { - if (!IsValid()) - return lldb::eFormatDefault; - - return m_type_system->GetFormat(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFormat(m_type); + return lldb::eFormatDefault; } uint32_t CompilerType::GetNumChildren(bool omit_empty_base_classes, const ExecutionContext *exe_ctx) const { - if (!IsValid()) - return 0; - return m_type_system->GetNumChildren(m_type, omit_empty_base_classes, + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumChildren(m_type, omit_empty_base_classes, exe_ctx); + return 0; } lldb::BasicType CompilerType::GetBasicTypeEnumeration() const { if (IsValid()) - return m_type_system->GetBasicTypeEnumeration(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetBasicTypeEnumeration(m_type); return eBasicTypeInvalid; } @@ -537,34 +592,39 @@ ConstString name, const llvm::APSInt &value)> const &callback) const { if (IsValid()) - return m_type_system->ForEachEnumerator(m_type, callback); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->ForEachEnumerator(m_type, callback); } uint32_t CompilerType::GetNumFields() const { - if (!IsValid()) - return 0; - return m_type_system->GetNumFields(m_type); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumFields(m_type); + return 0; } CompilerType CompilerType::GetFieldAtIndex(size_t idx, std::string &name, uint64_t *bit_offset_ptr, uint32_t *bitfield_bit_size_ptr, bool *is_bitfield_ptr) const { - if (!IsValid()) - return CompilerType(); - return m_type_system->GetFieldAtIndex(m_type, idx, name, bit_offset_ptr, + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetFieldAtIndex(m_type, idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr); + return CompilerType(); } uint32_t CompilerType::GetNumDirectBaseClasses() const { if (IsValid()) - return m_type_system->GetNumDirectBaseClasses(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumDirectBaseClasses(m_type); return 0; } uint32_t CompilerType::GetNumVirtualBaseClasses() const { if (IsValid()) - return m_type_system->GetNumVirtualBaseClasses(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumVirtualBaseClasses(m_type); return 0; } @@ -572,7 +632,8 @@ CompilerType::GetDirectBaseClassAtIndex(size_t idx, uint32_t *bit_offset_ptr) const { if (IsValid()) - return m_type_system->GetDirectBaseClassAtIndex(m_type, idx, + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetDirectBaseClassAtIndex(m_type, idx, bit_offset_ptr); return CompilerType(); } @@ -581,7 +642,8 @@ CompilerType::GetVirtualBaseClassAtIndex(size_t idx, uint32_t *bit_offset_ptr) const { if (IsValid()) - return m_type_system->GetVirtualBaseClassAtIndex(m_type, idx, + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetVirtualBaseClassAtIndex(m_type, idx, bit_offset_ptr); return CompilerType(); } @@ -613,13 +675,15 @@ uint32_t &child_bitfield_bit_offset, bool &child_is_base_class, bool &child_is_deref_of_parent, ValueObject *valobj, uint64_t &language_flags) const { - if (!IsValid()) - return CompilerType(); - return m_type_system->GetChildCompilerTypeAtIndex( - m_type, exe_ctx, idx, transparent_pointers, omit_empty_base_classes, - ignore_array_bounds, child_name, child_byte_size, child_byte_offset, - child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class, - child_is_deref_of_parent, valobj, language_flags); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetChildCompilerTypeAtIndex( + m_type, exe_ctx, idx, transparent_pointers, omit_empty_base_classes, + ignore_array_bounds, child_name, child_byte_size, child_byte_offset, + child_bitfield_bit_size, child_bitfield_bit_offset, + child_is_base_class, child_is_deref_of_parent, valobj, + language_flags); + return CompilerType(); } // Look for a child member (doesn't include base classes, but it does include @@ -659,7 +723,8 @@ const char *name, bool omit_empty_base_classes, std::vector &child_indexes) const { if (IsValid() && name && name[0]) { - return m_type_system->GetIndexOfChildMemberWithName( + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetIndexOfChildMemberWithName( m_type, name, omit_empty_base_classes, child_indexes); } return 0; @@ -667,7 +732,8 @@ size_t CompilerType::GetNumTemplateArguments(bool expand_pack) const { if (IsValid()) { - return m_type_system->GetNumTemplateArguments(m_type, expand_pack); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetNumTemplateArguments(m_type, expand_pack); } return 0; } @@ -675,14 +741,16 @@ TemplateArgumentKind CompilerType::GetTemplateArgumentKind(size_t idx, bool expand_pack) const { if (IsValid()) - return m_type_system->GetTemplateArgumentKind(m_type, idx, expand_pack); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTemplateArgumentKind(m_type, idx, expand_pack); return eTemplateArgumentKindNull; } CompilerType CompilerType::GetTypeTemplateArgument(size_t idx, bool expand_pack) const { if (IsValid()) { - return m_type_system->GetTypeTemplateArgument(m_type, idx, expand_pack); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeTemplateArgument(m_type, idx, expand_pack); } return CompilerType(); } @@ -690,25 +758,29 @@ llvm::Optional CompilerType::GetIntegralTemplateArgument(size_t idx, bool expand_pack) const { if (IsValid()) - return m_type_system->GetIntegralTemplateArgument(m_type, idx, expand_pack); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetIntegralTemplateArgument(m_type, idx, expand_pack); return llvm::None; } CompilerType CompilerType::GetTypeForFormatters() const { if (IsValid()) - return m_type_system->GetTypeForFormatters(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetTypeForFormatters(m_type); return CompilerType(); } LazyBool CompilerType::ShouldPrintAsOneLiner(ValueObject *valobj) const { if (IsValid()) - return m_type_system->ShouldPrintAsOneLiner(m_type, valobj); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->ShouldPrintAsOneLiner(m_type, valobj); return eLazyBoolCalculate; } bool CompilerType::IsMeaninglessWithoutDynamicResolution() const { if (IsValid()) - return m_type_system->IsMeaninglessWithoutDynamicResolution(m_type); + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->IsMeaninglessWithoutDynamicResolution(m_type); return false; } @@ -720,7 +792,8 @@ CompilerType::GetIndexOfChildWithName(const char *name, bool omit_empty_base_classes) const { if (IsValid() && name && name[0]) { - return m_type_system->GetIndexOfChildWithName(m_type, name, + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->GetIndexOfChildWithName(m_type, name, omit_empty_base_classes); } return UINT32_MAX; @@ -735,11 +808,11 @@ uint32_t bitfield_bit_offset, bool show_types, bool show_summary, bool verbose, uint32_t depth) { if (!IsValid()) - return; - m_type_system->DumpValue(m_type, exe_ctx, s, format, data, data_byte_offset, - data_byte_size, bitfield_bit_size, - bitfield_bit_offset, show_types, show_summary, - verbose, depth); + if (auto type_system_sp = GetTypeSystem()) + type_system_sp->DumpValue(m_type, exe_ctx, s, format, data, + data_byte_offset, data_byte_size, + bitfield_bit_size, bitfield_bit_offset, + show_types, show_summary, verbose, depth); } bool CompilerType::DumpTypeValue(Stream *s, lldb::Format format, @@ -748,11 +821,12 @@ uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, ExecutionContextScope *exe_scope) { - if (!IsValid()) - return false; - return m_type_system->DumpTypeValue(m_type, s, format, data, byte_offset, - byte_size, bitfield_bit_size, - bitfield_bit_offset, exe_scope); + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->DumpTypeValue(m_type, s, format, data, byte_offset, + byte_size, bitfield_bit_size, + bitfield_bit_offset, exe_scope); + return false; } void CompilerType::DumpSummary(ExecutionContext *exe_ctx, Stream *s, @@ -760,28 +834,30 @@ lldb::offset_t data_byte_offset, size_t data_byte_size) { if (IsValid()) - m_type_system->DumpSummary(m_type, exe_ctx, s, data, data_byte_offset, - data_byte_size); + if (auto type_system_sp = GetTypeSystem()) + type_system_sp->DumpSummary(m_type, exe_ctx, s, data, data_byte_offset, + data_byte_size); } void CompilerType::DumpTypeDescription(lldb::DescriptionLevel level) const { if (IsValid()) - m_type_system->DumpTypeDescription(m_type, level); + if (auto type_system_sp = GetTypeSystem()) + type_system_sp->DumpTypeDescription(m_type, level); } void CompilerType::DumpTypeDescription(Stream *s, lldb::DescriptionLevel level) const { - if (IsValid()) { - m_type_system->DumpTypeDescription(m_type, s, level); - } + if (IsValid()) + if (auto type_system_sp = GetTypeSystem()) + type_system_sp->DumpTypeDescription(m_type, s, level); } #ifndef NDEBUG LLVM_DUMP_METHOD void CompilerType::dump() const { if (IsValid()) - m_type_system->dump(m_type); - else - llvm::errs() << "\n"; + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->dump(m_type); + llvm::errs() << "\n"; } #endif @@ -888,10 +964,41 @@ #ifndef NDEBUG bool CompilerType::Verify() const { - return !IsValid() || m_type_system->Verify(m_type); + if (!IsValid()) + return true; + if (auto type_system_sp = GetTypeSystem()) + return type_system_sp->Verify(m_type); + return true; } #endif +CompilerType::ManagedTypeSystem CompilerType::GetTypeSystem() const { + if (!m_type_system) + return {}; + return {m_type_system->lock()}; +} + +lldb::TypeSystemWP *CompilerType::ManagedTypeSystem::GetCanonicalWP() const { + if (m_typesystem_sp) + return m_typesystem_sp->GetCanonicalWP(); + return nullptr; +} + +bool CompilerType::ManagedTypeSystem::operator==( + const CompilerType::ManagedTypeSystem &other) const { + if (!m_typesystem_sp && !other.m_typesystem_sp) + return true; + if (m_typesystem_sp && other.m_typesystem_sp) + return m_typesystem_sp->GetCanonicalWP() == + other.m_typesystem_sp->GetCanonicalWP(); + return false; +} + +TypeSystem *CompilerType::ManagedTypeSystem::operator->() const { + assert(m_typesystem_sp); + return m_typesystem_sp.get(); +} + bool lldb_private::operator==(const lldb_private::CompilerType &lhs, const lldb_private::CompilerType &rhs) { return lhs.GetTypeSystem() == rhs.GetTypeSystem() && Index: lldb/source/Symbol/SymbolFile.cpp =================================================================== --- lldb/source/Symbol/SymbolFile.cpp +++ lldb/source/Symbol/SymbolFile.cpp @@ -227,12 +227,13 @@ (*m_compile_units)[idx] = cu_sp; } -llvm::Expected +llvm::Expected SymbolFileCommon::GetTypeSystemForLanguage(lldb::LanguageType language) { auto type_system_or_err = m_objfile_sp->GetModule()->GetTypeSystemForLanguage(language); if (type_system_or_err) { - type_system_or_err->SetSymbolFile(this); + if (auto ts = *type_system_or_err) + ts->SetSymbolFile(this); } return type_system_or_err; } Index: lldb/source/Symbol/SymbolFileOnDemand.cpp =================================================================== --- lldb/source/Symbol/SymbolFileOnDemand.cpp +++ lldb/source/Symbol/SymbolFileOnDemand.cpp @@ -458,7 +458,7 @@ return m_sym_file_impl->GetTypes(sc_scope, type_mask, type_list); } -llvm::Expected +llvm::Expected SymbolFileOnDemand::GetTypeSystemForLanguage(LanguageType language) { if (!m_debug_info_enabled) { Log *log = GetLog(); Index: lldb/source/Symbol/Type.cpp =================================================================== --- lldb/source/Symbol/Type.cpp +++ lldb/source/Symbol/Type.cpp @@ -539,8 +539,10 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Symbols), std::move(err), "Unable to construct void type from TypeSystemClang"); } else { - CompilerType void_compiler_type = - type_system_or_err->GetBasicTypeFromAST(eBasicTypeVoid); + CompilerType void_compiler_type; + auto ts = *type_system_or_err; + if (ts) + void_compiler_type = ts->GetBasicTypeFromAST(eBasicTypeVoid); switch (m_encoding_uid_type) { case eEncodingIsUID: m_compiler_type = void_compiler_type; @@ -726,11 +728,14 @@ ModuleSP Type::GetExeModule() { if (m_compiler_type) { - SymbolFile *symbol_file = m_compiler_type.GetTypeSystem()->GetSymbolFile(); + auto ts = m_compiler_type.GetTypeSystem(); + if (!ts) + return {}; + SymbolFile *symbol_file = ts->GetSymbolFile(); if (symbol_file) return symbol_file->GetObjectFile()->GetModule(); } - return ModuleSP(); + return {}; } TypeAndOrName::TypeAndOrName(TypeSP &in_type_sp) { @@ -1038,7 +1043,7 @@ return CompilerType(); } -TypeSystem *TypeImpl::GetTypeSystem(bool prefer_dynamic) { +CompilerType::ManagedTypeSystem TypeImpl::GetTypeSystem(bool prefer_dynamic) { ModuleSP module_sp; if (CheckModule(module_sp)) { if (prefer_dynamic) { @@ -1047,7 +1052,7 @@ } return m_static_type.GetTypeSystem(); } - return nullptr; + return {}; } bool TypeImpl::GetDescription(lldb_private::Stream &strm, Index: lldb/source/Symbol/TypeSystem.cpp =================================================================== --- lldb/source/Symbol/TypeSystem.cpp +++ lldb/source/Symbol/TypeSystem.cpp @@ -12,7 +12,7 @@ #include "lldb/Symbol/CompilerType.h" #include "lldb/Target/Language.h" -#include +#include "llvm/ADT/DenseSet.h" using namespace lldb_private; using namespace lldb; @@ -37,19 +37,17 @@ TypeSystem::~TypeSystem() = default; -static lldb::TypeSystemSP CreateInstanceHelper(lldb::LanguageType language, - Module *module, Target *target) { +static TypeSystemSP CreateInstanceHelper(lldb::LanguageType language, + Module *module, Target *target) { uint32_t i = 0; TypeSystemCreateInstance create_callback; while ((create_callback = PluginManager::GetTypeSystemCreateCallbackAtIndex( i++)) != nullptr) { - lldb::TypeSystemSP type_system_sp = - create_callback(language, module, target); - if (type_system_sp) + if (auto type_system_sp = create_callback(language, module, target)) return type_system_sp; } - return lldb::TypeSystemSP(); + return {}; } lldb::TypeSystemSP TypeSystem::CreateInstance(lldb::LanguageType language, @@ -115,7 +113,7 @@ } CompilerType TypeSystem::GetTypeForFormatters(void *type) { - return CompilerType(this, type); + return CompilerType(GetCanonicalWP(), type); } size_t TypeSystem::GetNumTemplateArguments(lldb::opaque_compiler_type_t type, @@ -178,6 +176,11 @@ return {}; } +lldb::TypeSystemWP *TypeSystem::GetCanonicalWP() const { + assert(m_canonical_wp && "Owner should have set up a canonical weak pointer"); + return m_canonical_wp; +} + #pragma mark TypeSystemMap TypeSystemMap::TypeSystemMap() : m_mutex(), m_map() {} @@ -191,13 +194,13 @@ map = m_map; m_clear_in_progress = true; } - std::set visited; - for (auto pair : map) { - TypeSystem *type_system = pair.second.get(); - if (type_system && !visited.count(type_system)) { - visited.insert(type_system); + llvm::DenseSet visited; + for (auto &pair : map) { + if (visited.count(pair.second.wp_ptr)) + continue; + visited.insert(pair.second.wp_ptr); + if (lldb::TypeSystemSP type_system = pair.second.sp) type_system->Finalize(); - } } map.clear(); { @@ -207,22 +210,36 @@ } } -void TypeSystemMap::ForEach(std::function const &callback) { +void TypeSystemMap::ForEach( + std::function const &callback) { std::lock_guard guard(m_mutex); // Use a std::set so we only call the callback once for each unique // TypeSystem instance - std::set visited; - for (auto pair : m_map) { - TypeSystem *type_system = pair.second.get(); - if (type_system && !visited.count(type_system)) { - visited.insert(type_system); - if (!callback(type_system)) - break; - } + llvm::DenseSet visited; + for (auto &pair : m_map) { + lldb::TypeSystemWP *type_system = pair.second.wp_ptr; + if (visited.count(type_system)) + continue; + visited.insert(type_system); + assert(type_system); + if (!callback(*type_system)) + break; } } -llvm::Expected TypeSystemMap::GetTypeSystemForLanguage( +using TypeSystemWPMap = std::vector>; +TypeSystemMap::TypeSystemEntry +TypeSystemMap::GetTypeSystemEntry(TypeSystemSP type_system) { + static std::mutex g_mutex; + std::lock_guard guard(g_mutex); + + static TypeSystemWPMap g_typesystem_wp_map; + + g_typesystem_wp_map.push_back(std::make_unique(type_system)); + return {type_system, g_typesystem_wp_map.back().get()}; +} + +llvm::Expected TypeSystemMap::GetTypeSystemForLanguage( lldb::LanguageType language, llvm::Optional create_callback) { std::lock_guard guard(m_mutex); @@ -233,9 +250,10 @@ collection::iterator pos = m_map.find(language); if (pos != m_map.end()) { - auto *type_system = pos->second.get(); - if (type_system) - return *type_system; + if (pos->second.sp) { + assert(pos->second.sp->GetCanonicalWP()); + return pos->second.sp; + } return llvm::make_error( "TypeSystem for language " + llvm::StringRef(Language::GetNameForLanguageType(language)) + @@ -244,12 +262,14 @@ } for (const auto &pair : m_map) { - if (pair.second && pair.second->SupportsLanguage(language)) { + if (pair.second.sp && pair.second.sp->SupportsLanguage(language)) { // Add a new mapping for "language" to point to an already existing // TypeSystem that supports this language m_map[language] = pair.second; - if (pair.second.get()) - return *pair.second.get(); + if (pair.second.sp) { + assert(pair.second.sp->GetCanonicalWP()); + return pair.second.sp; + } return llvm::make_error( "TypeSystem for language " + llvm::StringRef(Language::GetNameForLanguageType(language)) + @@ -267,9 +287,14 @@ // Cache even if we get a shared pointer that contains a null type system // back TypeSystemSP type_system_sp = (*create_callback)(); - m_map[language] = type_system_sp; - if (type_system_sp.get()) - return *type_system_sp.get(); + auto entry = GetTypeSystemEntry(type_system_sp); + assert(entry.wp_ptr); + m_map[language] = entry; + if (type_system_sp) { + type_system_sp->SetCanonicalWP(entry.wp_ptr); + assert(entry.sp->GetCanonicalWP()); + return entry.sp; + } return llvm::make_error( "TypeSystem for language " + llvm::StringRef(Language::GetNameForLanguageType(language)) + @@ -277,7 +302,7 @@ llvm::inconvertibleErrorCode()); } -llvm::Expected +llvm::Expected TypeSystemMap::GetTypeSystemForLanguage(lldb::LanguageType language, Module *module, bool can_create) { if (can_create) { @@ -289,7 +314,7 @@ return GetTypeSystemForLanguage(language); } -llvm::Expected +llvm::Expected TypeSystemMap::GetTypeSystemForLanguage(lldb::LanguageType language, Target *target, bool can_create) { if (can_create) { Index: lldb/source/Target/Process.cpp =================================================================== --- lldb/source/Target/Process.cpp +++ lldb/source/Target/Process.cpp @@ -6069,8 +6069,11 @@ llvm::consumeError(type_system_or_err.takeError()); return false; } + auto ts = *type_system_or_err; + if (!ts) + return false; CompilerType void_ptr_type = - type_system_or_err->GetBasicTypeFromAST(eBasicTypeVoid).GetPointerType(); + ts->GetBasicTypeFromAST(eBasicTypeVoid).GetPointerType(); lldb::ThreadPlanSP call_plan_sp(new ThreadPlanCallFunction( *thread, *address, void_ptr_type, llvm::ArrayRef(), options)); if (call_plan_sp) { Index: lldb/source/Target/StackFrame.cpp =================================================================== --- lldb/source/Target/StackFrame.cpp +++ lldb/source/Target/StackFrame.cpp @@ -1368,9 +1368,11 @@ "Unable to guess value for given address"); return ValueObjectSP(); } else { + auto ts = *c_type_system_or_err; + if (!ts) + return {}; CompilerType void_ptr_type = - c_type_system_or_err - ->GetBasicTypeFromAST(lldb::BasicType::eBasicTypeChar) + ts->GetBasicTypeFromAST(lldb::BasicType::eBasicTypeChar) .GetPointerType(); return ValueObjectMemory::Create(this, "", addr, void_ptr_type); } Index: lldb/source/Target/Target.cpp =================================================================== --- lldb/source/Target/Target.cpp +++ lldb/source/Target/Target.cpp @@ -2294,7 +2294,7 @@ target->SetExecutableModule(exe_module_sp, eLoadDependentsYes); } -llvm::Expected +llvm::Expected Target::GetScratchTypeSystemForLanguage(lldb::LanguageType language, bool create_on_demand) { if (!m_valid) @@ -2323,14 +2323,15 @@ create_on_demand); } -std::vector Target::GetScratchTypeSystems(bool create_on_demand) { +std::vector +Target::GetScratchTypeSystems(bool create_on_demand) { if (!m_valid) return {}; // Some TypeSystem instances are associated with several LanguageTypes so // they will show up several times in the loop below. The SetVector filters // out all duplicates as they serve no use for the caller. - llvm::SetVector scratch_type_systems; + llvm::SetVector scratch_type_systems; LanguageSet languages_for_expressions = Language::GetLanguagesSupportingTypeSystemsForExpressions(); @@ -2345,7 +2346,8 @@ "system available", Language::GetNameForLanguageType(language)); else - scratch_type_systems.insert(&type_system_or_err.get()); + if (auto ts = *type_system_or_err) + scratch_type_systems.insert(ts->GetCanonicalWP()); } return scratch_type_systems.takeVector(); @@ -2362,7 +2364,13 @@ return nullptr; } - return type_system_or_err->GetPersistentExpressionState(); + if (auto ts = *type_system_or_err) + return ts->GetPersistentExpressionState(); + + LLDB_LOG(GetLog(LLDBLog::Target), + "Unable to get persistent expression state for language {}", + Language::GetNameForLanguageType(language)); + return nullptr; } UserExpression *Target::GetUserExpressionForLanguage( @@ -2379,8 +2387,16 @@ return nullptr; } - auto *user_expr = type_system_or_err->GetUserExpression( - expr, prefix, language, desired_type, options, ctx_obj); + auto ts = *type_system_or_err; + if (!ts) { + error.SetErrorStringWithFormat( + "Type system for language %s is no longer live", + Language::GetNameForLanguageType(language)); + return nullptr; + } + + auto *user_expr = ts->GetUserExpression(expr, prefix, language, desired_type, + options, ctx_obj); if (!user_expr) error.SetErrorStringWithFormat( "Could not create an expression for language %s", @@ -2401,9 +2417,15 @@ llvm::toString(std::move(err)).c_str()); return nullptr; } - - auto *persistent_fn = type_system_or_err->GetFunctionCaller( - return_type, function_address, arg_value_list, name); + auto ts = *type_system_or_err; + if (!ts) { + error.SetErrorStringWithFormat( + "Type system for language %s is no longer live", + Language::GetNameForLanguageType(language)); + return nullptr; + } + auto *persistent_fn = ts->GetFunctionCaller(return_type, function_address, + arg_value_list, name); if (!persistent_fn) error.SetErrorStringWithFormat( "Could not create an expression for language %s", @@ -2419,10 +2441,15 @@ auto type_system_or_err = GetScratchTypeSystemForLanguage(language); if (!type_system_or_err) return type_system_or_err.takeError(); - + auto ts = *type_system_or_err; + if (!ts) + return llvm::make_error( + llvm::StringRef("Type system for language") + + Language::GetNameForLanguageType(language) + + llvm::StringRef("is no longer live"), + llvm::inconvertibleErrorCode()); std::unique_ptr utility_fn = - type_system_or_err->CreateUtilityFunction(std::move(expression), - std::move(name)); + ts->CreateUtilityFunction(std::move(expression), std::move(name)); if (!utility_fn) return llvm::make_error( llvm::StringRef("Could not create an expression for language") + @@ -2516,8 +2543,13 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Target), std::move(err), "Unable to get scratch type system"); } else { - persistent_var_sp = - type_system_or_err->GetPersistentExpressionState()->GetVariable(expr); + auto ts = *type_system_or_err; + if (!ts) + LLDB_LOG_ERROR(GetLog(LLDBLog::Target), std::move(err), + "Scratch type system is no longer live"); + else + persistent_var_sp = + ts->GetPersistentExpressionState()->GetVariable(expr); } } if (persistent_var_sp) { @@ -2545,9 +2577,12 @@ lldb::ExpressionVariableSP Target::GetPersistentVariable(ConstString name) { lldb::ExpressionVariableSP variable_sp; m_scratch_type_system_map.ForEach( - [name, &variable_sp](TypeSystem *type_system) -> bool { + [name, &variable_sp](TypeSystemWP &type_system) -> bool { + auto ts = type_system.lock(); + if (!ts) + return true; if (PersistentExpressionState *persistent_state = - type_system->GetPersistentExpressionState()) { + ts->GetPersistentExpressionState()) { variable_sp = persistent_state->GetVariable(name); if (variable_sp) @@ -2562,9 +2597,13 @@ lldb::addr_t address = LLDB_INVALID_ADDRESS; m_scratch_type_system_map.ForEach( - [name, &address](TypeSystem *type_system) -> bool { + [name, &address](TypeSystemWP &type_system) -> bool { + auto ts = type_system.lock(); + if (!ts) + return true; + if (PersistentExpressionState *persistent_state = - type_system->GetPersistentExpressionState()) { + ts->GetPersistentExpressionState()) { address = persistent_state->LookupSymbol(name); if (address != LLDB_INVALID_ADDRESS) return false; // Stop iterating the ForEach Index: lldb/source/Target/ThreadPlanTracer.cpp =================================================================== --- lldb/source/Target/ThreadPlanTracer.cpp +++ lldb/source/Target/ThreadPlanTracer.cpp @@ -110,10 +110,10 @@ LLDB_LOG_ERROR(GetLog(LLDBLog::Types), std::move(err), "Unable to get integer pointer type from TypeSystem"); } else { - m_intptr_type = TypeFromUser( - type_system_or_err->GetBuiltinTypeForEncodingAndBitSize( - eEncodingUint, - target_sp->GetArchitecture().GetAddressByteSize() * 8)); + if (auto ts = *type_system_or_err) + m_intptr_type = TypeFromUser(ts->GetBuiltinTypeForEncodingAndBitSize( + eEncodingUint, + target_sp->GetArchitecture().GetAddressByteSize() * 8)); } } } Index: lldb/tools/lldb-test/lldb-test.cpp =================================================================== --- lldb/tools/lldb-test/lldb-test.cpp +++ lldb/tools/lldb-test/lldb-test.cpp @@ -658,13 +658,13 @@ if (!symfile) return make_string_error("Module has no symbol file."); - llvm::Expected type_system_or_err = + auto type_system_or_err = symfile->GetTypeSystemForLanguage(eLanguageTypeC_plus_plus); if (!type_system_or_err) return make_string_error("Can't retrieve TypeSystemClang"); - auto *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + auto ts = *type_system_or_err; + auto *clang_ast_ctx = llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return make_string_error("Retrieved TypeSystem was not a TypeSystemClang"); @@ -686,13 +686,12 @@ if (!symfile) return make_string_error("Module has no symbol file."); - llvm::Expected type_system_or_err = + auto type_system_or_err = symfile->GetTypeSystemForLanguage(eLanguageTypeObjC_plus_plus); if (!type_system_or_err) return make_string_error("Can't retrieve TypeSystemClang"); - - auto *clang_ast_ctx = - llvm::dyn_cast_or_null(&type_system_or_err.get()); + auto ts = *type_system_or_err; + auto *clang_ast_ctx = llvm::dyn_cast_or_null(ts.get()); if (!clang_ast_ctx) return make_string_error("Retrieved TypeSystem was not a TypeSystemClang"); Index: lldb/unittests/Expression/ClangExpressionDeclMapTest.cpp =================================================================== --- lldb/unittests/Expression/ClangExpressionDeclMapTest.cpp +++ lldb/unittests/Expression/ClangExpressionDeclMapTest.cpp @@ -24,9 +24,11 @@ FakeClangExpressionDeclMap(const std::shared_ptr &importer) : ClangExpressionDeclMap(false, nullptr, lldb::TargetSP(), importer, nullptr) { - m_scratch_context = clang_utils::createAST(); + m_holder = std::make_unique("ast"); + m_scratch_context = m_holder->GetAST(); } - std::unique_ptr m_scratch_context; + std::unique_ptr m_holder; + TypeSystemClang *m_scratch_context; /// Adds a persistent decl that can be found by the ClangExpressionDeclMap /// via GetPersistentDecl. void AddPersistentDeclForTest(clang::NamedDecl *d) { @@ -62,20 +64,23 @@ /// The ExpressionDeclMap for the current test case. std::unique_ptr decl_map; + std::unique_ptr holder; + /// The target AST that lookup results should be imported to. - std::unique_ptr target_ast; + TypeSystemClang *target_ast; void SetUp() override { importer = std::make_shared(); decl_map = std::make_unique(importer); - target_ast = clang_utils::createAST(); + holder = std::make_unique("target ast"); + target_ast = holder->GetAST(); decl_map->InstallASTContext(*target_ast); } void TearDown() override { importer.reset(); decl_map.reset(); - target_ast.reset(); + holder.reset(); } }; } // namespace Index: lldb/unittests/Symbol/TestClangASTImporter.cpp =================================================================== --- lldb/unittests/Symbol/TestClangASTImporter.cpp +++ lldb/unittests/Symbol/TestClangASTImporter.cpp @@ -42,7 +42,9 @@ // Tests that the ClangASTImporter::CopyDecl can copy TagDecls. clang_utils::SourceASTWithRecord source; - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; clang::Decl *imported = @@ -67,7 +69,9 @@ // Tests that the ClangASTImporter::CopyType can copy TagDecls types. clang_utils::SourceASTWithRecord source; - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; CompilerType imported = importer.CopyType(*target_ast, source.record_type); @@ -94,12 +98,16 @@ // Create an AST with a type thst is only a forward declaration with the // same name as the one in the other source. - std::unique_ptr fwd_decl_source = clang_utils::createAST(); + auto holder = + std::make_unique("ast"); + auto *fwd_decl_source = holder->GetAST(); CompilerType fwd_decl_type = clang_utils::createRecord( *fwd_decl_source, source_with_definition.record_decl->getName()); // Create a target and import the forward decl. - std::unique_ptr target = clang_utils::createAST(); + auto target_holder = + std::make_unique("target ast"); + auto *target = target_holder->GetAST(); ClangASTImporter importer; CompilerType imported = importer.CopyType(*target, fwd_decl_type); ASSERT_TRUE(imported.IsValid()); @@ -119,7 +127,9 @@ // Tests that the ClangASTImporter::DeportDecl completely copies TagDecls. clang_utils::SourceASTWithRecord source; - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; clang::Decl *imported = @@ -141,7 +151,9 @@ // Tests that the ClangASTImporter::CopyType can deport TagDecl types. clang_utils::SourceASTWithRecord source; - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; CompilerType imported = importer.DeportType(*target_ast, source.record_type); @@ -166,7 +178,9 @@ const lldb::user_id_t metadata = 123456; source.ast->SetMetadataAsUserID(source.record_decl, metadata); - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; clang::Decl *imported = @@ -188,14 +202,18 @@ const lldb::user_id_t metadata = 123456; source.ast->SetMetadataAsUserID(source.record_decl, metadata); - std::unique_ptr temporary_ast = clang_utils::createAST(); + auto tmp_holder = + std::make_unique("tmp ast"); + auto *temporary_ast = tmp_holder->GetAST(); ClangASTImporter importer; clang::Decl *temporary_imported = importer.CopyDecl(&temporary_ast->getASTContext(), source.record_decl); ASSERT_NE(nullptr, temporary_imported); - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); clang::Decl *imported = importer.CopyDecl(&target_ast->getASTContext(), temporary_imported); ASSERT_NE(nullptr, imported); @@ -212,7 +230,9 @@ clang_utils::SourceASTWithRecord source; const lldb::user_id_t metadata = 123456; - std::unique_ptr target_ast = clang_utils::createAST(); + auto holder = + std::make_unique("target ast"); + auto *target_ast = holder->GetAST(); ClangASTImporter importer; clang::Decl *imported = Index: lldb/unittests/Symbol/TestTypeSystemClang.cpp =================================================================== --- lldb/unittests/Symbol/TestTypeSystemClang.cpp +++ lldb/unittests/Symbol/TestTypeSystemClang.cpp @@ -27,14 +27,20 @@ SubsystemRAII subsystems; void SetUp() override { - m_ast.reset( - new TypeSystemClang("test ASTContext", HostInfo::GetTargetTriple())); + m_holder = + std::make_unique("test ASTContext"); + m_ast = m_holder->GetAST(); } - void TearDown() override { m_ast.reset(); } + void TearDown() override { + m_ast = nullptr; + m_holder.reset(); + } protected: - std::unique_ptr m_ast; + + TypeSystemClang *m_ast = nullptr; + std::unique_ptr m_holder; QualType GetBasicQualType(BasicType type) const { return ClangUtil::GetQualType(m_ast->GetBasicTypeFromAST(type)); @@ -257,7 +263,10 @@ for (lldb::BasicType basic_type : types_to_test) { SCOPED_TRACE(std::to_string(basic_type)); - TypeSystemClang ast("enum_ast", HostInfo::GetTargetTriple()); + auto holder = + std::make_unique("enum_ast"); + auto &ast = *holder->GetAST(); + CompilerType basic_compiler_type = ast.GetBasicType(basic_type); EXPECT_TRUE(basic_compiler_type.IsValid()); @@ -273,7 +282,9 @@ } TEST_F(TestTypeSystemClang, TestOwningModule) { - TypeSystemClang ast("module_ast", HostInfo::GetTargetTriple()); + auto holder = + std::make_unique("module_ast"); + auto &ast = *holder->GetAST(); CompilerType basic_compiler_type = ast.GetBasicType(BasicType::eBasicTypeInt); CompilerType enum_type = ast.CreateEnumerationType( "my_enum", ast.GetTranslationUnitDecl(), OptionalClangModuleID(100), @@ -301,7 +312,7 @@ clang::ASTContext &context = m_ast->getASTContext(); lldb::opaque_compiler_type_t bool_ctype = TypeSystemClang::GetOpaqueCompilerType(&context, lldb::eBasicTypeBool); - CompilerType bool_type(m_ast.get(), bool_ctype); + CompilerType bool_type(m_ast->GetCanonicalWP(), bool_ctype); CompilerType record_type = m_ast->CreateRecordType( nullptr, OptionalClangModuleID(100), lldb::eAccessPublic, "FooRecord", clang::TTK_Struct, lldb::eLanguageTypeC_plus_plus, nullptr); @@ -489,13 +500,13 @@ "foo_def", m_ast->CreateDeclContext(m_ast->GetTranslationUnitDecl()), 0); CompilerType auto_type( - m_ast.get(), + m_ast->GetCanonicalWP(), m_ast->getASTContext() .getAutoType(ClangUtil::GetCanonicalQualType(typedef_type), clang::AutoTypeKeyword::Auto, false) .getAsOpaquePtr()); - CompilerType int_type(m_ast.get(), + CompilerType int_type(m_ast->GetCanonicalWP(), m_ast->getASTContext().IntTy.getAsOpaquePtr()); for (CompilerType t : {type, typedef_type, auto_type}) { SCOPED_TRACE(t.GetTypeName().AsCString()); Index: lldb/unittests/SymbolFile/DWARF/DWARFASTParserClangTests.cpp =================================================================== --- lldb/unittests/SymbolFile/DWARF/DWARFASTParserClangTests.cpp +++ lldb/unittests/SymbolFile/DWARF/DWARFASTParserClangTests.cpp @@ -9,6 +9,7 @@ #include "Plugins/SymbolFile/DWARF/DWARFASTParserClang.h" #include "Plugins/SymbolFile/DWARF/DWARFCompileUnit.h" #include "Plugins/SymbolFile/DWARF/DWARFDIE.h" +#include "TestingSupport/Symbol/ClangTestUtils.h" #include "TestingSupport/Symbol/YAMLModuleTester.h" #include "gmock/gmock.h" #include "gtest/gtest.h" @@ -93,7 +94,9 @@ YAMLModuleTester t(yamldata); ASSERT_TRUE((bool)t.GetDwarfUnit()); - TypeSystemClang ast_ctx("dummy ASTContext", HostInfoBase::GetTargetTriple()); + auto holder = std::make_unique("ast"); + auto &ast_ctx = *holder->GetAST(); + DWARFASTParserClangStub ast_parser(ast_ctx); DWARFUnit *unit = t.GetDwarfUnit(); @@ -244,7 +247,8 @@ ASSERT_EQ(cu_entry->Tag(), DW_TAG_compile_unit); DWARFDIE cu_die(unit, cu_entry); - TypeSystemClang ast_ctx("dummy ASTContext", HostInfoBase::GetTargetTriple()); + auto holder = std::make_unique("ast"); + auto &ast_ctx = *holder->GetAST(); DWARFASTParserClangStub ast_parser(ast_ctx); std::vector found_function_types; @@ -276,10 +280,12 @@ struct ExtractIntFromFormValueTest : public testing::Test { SubsystemRAII subsystems; - TypeSystemClang ts; + clang_utils::TypeSystemClangHolder holder; + TypeSystemClang &ts; + DWARFASTParserClang parser; ExtractIntFromFormValueTest() - : ts("dummy ASTContext", HostInfoBase::GetTargetTriple()), parser(ts) {} + : holder("dummy ASTContext"), ts(*holder.GetAST()), parser(ts) {} /// Takes the given integer value, stores it in a DWARFFormValue and then /// tries to extract the value back via Index: lldb/unittests/TestingSupport/Symbol/ClangTestUtils.h =================================================================== --- lldb/unittests/TestingSupport/Symbol/ClangTestUtils.h +++ lldb/unittests/TestingSupport/Symbol/ClangTestUtils.h @@ -21,11 +21,6 @@ return ast.getASTContext().DeclarationNames.getIdentifier(&II); } -inline std::unique_ptr createAST() { - return std::make_unique("test ASTContext", - HostInfo::GetTargetTriple()); -} - inline CompilerType createRecord(TypeSystemClang &ast, llvm::StringRef name) { return ast.CreateRecordType(ast.getASTContext().getTranslationUnitDecl(), OptionalClangModuleID(), @@ -49,16 +44,33 @@ return t; } +/// Simulates a Clang type system owned by a TypeSystemMap. +class TypeSystemClangHolder { + TypeSystemClang *m_ast; + lldb::TypeSystemSP m_ast_sp; + lldb::TypeSystemWP m_ast_wp; +public: + TypeSystemClangHolder(const char *name) { + m_ast = new TypeSystemClang(name, HostInfo::GetTargetTriple()); + m_ast_sp.reset(m_ast); + m_ast_wp = m_ast_sp; + m_ast_sp->SetCanonicalWP(&m_ast_wp); + } + TypeSystemClang *GetAST() const { return m_ast; } +}; + /// Constructs a TypeSystemClang that contains a single RecordDecl that contains /// a single FieldDecl. Utility class as this setup is a common starting point /// for unit test that exercise the ASTImporter. struct SourceASTWithRecord { - std::unique_ptr ast; + std::unique_ptr holder; + TypeSystemClang *ast; CompilerType record_type; clang::RecordDecl *record_decl = nullptr; clang::FieldDecl *field_decl = nullptr; SourceASTWithRecord() { - ast = createAST(); + holder = std::make_unique("test ASTContext"); + ast = holder->GetAST(); record_type = createRecordWithField( *ast, "Source", ast->GetBasicType(lldb::BasicType::eBasicTypeChar), "a_field");