@@ -2798,27 +2798,48 @@ uint32_t TypeSystemSwiftTypeRef::GetNumFields(opaque_compiler_type_t type,
27982798 ExecutionContext *exe_ctx) {
27992799 LLDB_SCOPED_TIMER ();
28002800 FALLBACK (GetNumFields, (ReconstructType (type), exe_ctx));
2801- if (exe_ctx)
2802- if (auto *runtime = SwiftLanguageRuntime::Get (exe_ctx->GetProcessSP ()))
2803- if (auto num_fields =
2804- runtime->GetNumFields (GetCanonicalType (type), exe_ctx))
2805- // Use a lambda to intercept & unwrap the `Optional` return value from
2806- // `SwiftLanguageRuntime::GetNumFields`.
2807- // Optional<uint32_t> uses more lax equivalency function.
2808- return [&]() -> llvm::Optional<uint32_t > {
2809- auto impl = [&]() -> llvm::Optional<uint32_t > {
2810- if (!type)
2811- return 0 ;
2812- return num_fields;
2813- };
2814- ExecutionContext exe_ctx_obj;
2815- if (exe_ctx)
2816- exe_ctx_obj = *exe_ctx;
2817- VALIDATE_AND_RETURN (impl, GetNumFields, type, exe_ctx_obj,
2818- (ReconstructType (type), exe_ctx),
2819- (ReconstructType (type), exe_ctx));
2820- }()
2821- .getValueOr (0 );
2801+
2802+ auto impl = [&]() -> llvm::Optional<uint32_t > {
2803+ if (exe_ctx)
2804+ if (auto *runtime = SwiftLanguageRuntime::Get (exe_ctx->GetProcessSP ()))
2805+ if (auto num_fields =
2806+ runtime->GetNumFields (GetCanonicalType (type), exe_ctx))
2807+ return num_fields;
2808+
2809+ bool is_imported = false ;
2810+ if (auto clang_type = GetAsClangTypeOrNull (type, &is_imported)) {
2811+ switch (clang_type.GetTypeClass ()) {
2812+ case lldb::eTypeClassObjCObject:
2813+ case lldb::eTypeClassObjCInterface:
2814+ // Imported ObjC types are treated as having no fields.
2815+ return 0 ;
2816+ default :
2817+ return clang_type.GetNumFields (exe_ctx);
2818+ }
2819+ } else if (is_imported) {
2820+ // A known imported type, but where clang has no info. Return early to
2821+ // avoid loading Swift ASTContexts, only to return the same zero value.
2822+ LLDB_LOGF (GetLog (LLDBLog::Types),
2823+ " No CompilerType for imported Clang type %s" ,
2824+ AsMangledName (type));
2825+ return 0 ;
2826+ }
2827+ return {};
2828+ };
2829+ if (auto num_fields = impl ()) {
2830+ // Use a lambda to intercept and unwrap the `Optional` return value.
2831+ // Optional<uint32_t> uses more lax equivalency function.
2832+ return [&]() -> llvm::Optional<uint32_t > {
2833+ auto impl = [&]() { return num_fields; };
2834+ ExecutionContext exe_ctx_obj;
2835+ if (exe_ctx)
2836+ exe_ctx_obj = *exe_ctx;
2837+ VALIDATE_AND_RETURN (impl, GetNumFields, type, exe_ctx_obj,
2838+ (ReconstructType (type), exe_ctx),
2839+ (ReconstructType (type), exe_ctx));
2840+ }()
2841+ .getValueOr (0 );
2842+ }
28222843
28232844 LLDB_LOGF (GetLog (LLDBLog::Types),
28242845 " Using SwiftASTContext::GetNumFields fallback for type %s" ,
@@ -3257,8 +3278,9 @@ bool TypeSystemSwiftTypeRef::IsMeaninglessWithoutDynamicResolution(
32573278 (ReconstructType (type)));
32583279}
32593280
3260- CompilerType TypeSystemSwiftTypeRef::GetAsClangTypeOrNull (
3261- lldb::opaque_compiler_type_t type) {
3281+ CompilerType
3282+ TypeSystemSwiftTypeRef::GetAsClangTypeOrNull (lldb::opaque_compiler_type_t type,
3283+ bool *is_imported) {
32623284 using namespace swift ::Demangle;
32633285 Demangler dem;
32643286 NodePointer node = GetDemangledType (dem, AsMangledName (type));
@@ -3275,7 +3297,9 @@ CompilerType TypeSystemSwiftTypeRef::GetAsClangTypeOrNull(
32753297 return node_clangtype.second ;
32763298 }
32773299 CompilerType clang_type;
3278- IsImportedType (type, &clang_type);
3300+ bool imported = IsImportedType (type, &clang_type);
3301+ if (is_imported)
3302+ *is_imported = imported;
32793303 return clang_type;
32803304}
32813305
0 commit comments