@@ -2798,27 +2798,48 @@ uint32_t TypeSystemSwiftTypeRef::GetNumFields(opaque_compiler_type_t type,
2798
2798
ExecutionContext *exe_ctx) {
2799
2799
LLDB_SCOPED_TIMER ();
2800
2800
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
+ }
2822
2843
2823
2844
LLDB_LOGF (GetLog (LLDBLog::Types),
2824
2845
" Using SwiftASTContext::GetNumFields fallback for type %s" ,
@@ -3257,8 +3278,9 @@ bool TypeSystemSwiftTypeRef::IsMeaninglessWithoutDynamicResolution(
3257
3278
(ReconstructType (type)));
3258
3279
}
3259
3280
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) {
3262
3284
using namespace swift ::Demangle;
3263
3285
Demangler dem;
3264
3286
NodePointer node = GetDemangledType (dem, AsMangledName (type));
@@ -3275,7 +3297,9 @@ CompilerType TypeSystemSwiftTypeRef::GetAsClangTypeOrNull(
3275
3297
return node_clangtype.second ;
3276
3298
}
3277
3299
CompilerType clang_type;
3278
- IsImportedType (type, &clang_type);
3300
+ bool imported = IsImportedType (type, &clang_type);
3301
+ if (is_imported)
3302
+ *is_imported = imported;
3279
3303
return clang_type;
3280
3304
}
3281
3305
0 commit comments