Skip to content

Commit 4ccae3c

Browse files
authored
Merge pull request #2260 from apple/lldb-Implement-TypeSystemSwiftTypeRef-GetIndexOfChildMemberWithName
[lldb] Implement TypeSystemSwiftTypeRef::GetIndexOfChildMemberWithName
2 parents ae2e3d9 + ecc71dd commit 4ccae3c

23 files changed

+253
-55
lines changed

lldb/include/lldb/Symbol/CompilerType.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -324,7 +324,7 @@ class CompilerType {
324324

325325
/// Lookup a child given a name. This function will match base class names and
326326
/// member member names in "clang_type" only, not descendants.
327-
uint32_t GetIndexOfChildWithName(const char *name,
327+
uint32_t GetIndexOfChildWithName(const char *name, ExecutionContext *exe_ctx,
328328
bool omit_empty_base_classes) const;
329329

330330
/// Lookup a child member given a name. This function will match member names
@@ -334,7 +334,8 @@ class CompilerType {
334334
/// vector<vector<uint32_t>>
335335
/// so we catch all names that match a given child name, not just the first.
336336
size_t
337-
GetIndexOfChildMemberWithName(const char *name, bool omit_empty_base_classes,
337+
GetIndexOfChildMemberWithName(const char *name, ExecutionContext *exe_ctx,
338+
bool omit_empty_base_classes,
338339
std::vector<uint32_t> &child_indexes) const;
339340

340341
size_t GetNumTemplateArguments() const;

lldb/include/lldb/Symbol/TypeSystem.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -355,6 +355,7 @@ class TypeSystem : public PluginInterface {
355355
// member member names in "clang_type" only, not descendants.
356356
virtual uint32_t GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
357357
const char *name,
358+
ExecutionContext *exe_ctx,
358359
bool omit_empty_base_classes) = 0;
359360

360361
// Lookup a child member given a name. This function will match member names
@@ -365,7 +366,8 @@ class TypeSystem : public PluginInterface {
365366
// so we catch all names that match a given child name, not just the first.
366367
virtual size_t
367368
GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type,
368-
const char *name, bool omit_empty_base_classes,
369+
const char *name, ExecutionContext *exe_ctx,
370+
bool omit_empty_base_classes,
369371
std::vector<uint32_t> &child_indexes) = 0;
370372

371373
virtual size_t GetNumTemplateArguments(lldb::opaque_compiler_type_t type);

lldb/include/lldb/Target/SwiftLanguageRuntime.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -256,6 +256,10 @@ class SwiftLanguageRuntime : public LanguageRuntime {
256256
llvm::Optional<unsigned> GetNumChildren(CompilerType type,
257257
ValueObject *valobj);
258258

259+
llvm::Optional<size_t> GetIndexOfChildMemberWithName(
260+
CompilerType type, llvm::StringRef name, ExecutionContext *exe_ctx,
261+
bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes);
262+
259263
/// Ask Remote Mirrors about a child of a composite type.
260264
CompilerType GetChildCompilerTypeAtIndex(
261265
CompilerType type, size_t idx, bool transparent_pointers,

lldb/source/Core/ValueObject.cpp

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -595,7 +595,8 @@ lldb::ValueObjectSP ValueObject::GetChildAtNamePath(
595595

596596
size_t ValueObject::GetIndexOfChildWithName(ConstString name) {
597597
bool omit_empty_base_classes = true;
598-
return GetCompilerType().GetIndexOfChildWithName(name.GetCString(),
598+
ExecutionContext exe_ctx(GetExecutionContextRef());
599+
return GetCompilerType().GetIndexOfChildWithName(name.GetCString(), &exe_ctx,
599600
omit_empty_base_classes);
600601
}
601602

@@ -614,9 +615,10 @@ ValueObjectSP ValueObject::GetChildMemberWithName(ConstString name,
614615
if (!GetCompilerType().IsValid())
615616
return ValueObjectSP();
616617

618+
ExecutionContext exe_ctx(GetExecutionContextRef());
617619
const size_t num_child_indexes =
618620
GetCompilerType().GetIndexOfChildMemberWithName(
619-
name.GetCString(), omit_empty_base_classes, child_indexes);
621+
name.GetCString(), &exe_ctx, omit_empty_base_classes, child_indexes);
620622
if (num_child_indexes == 0)
621623
return nullptr;
622624

lldb/source/Plugins/Language/CPlusPlus/BlockPointer.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -158,8 +158,8 @@ class BlockPointerSyntheticFrontEnd : public SyntheticChildrenFrontEnd {
158158
return UINT32_MAX;
159159

160160
const bool omit_empty_base_classes = false;
161-
return m_block_struct_type.GetIndexOfChildWithName(name.AsCString(),
162-
omit_empty_base_classes);
161+
return m_block_struct_type.GetIndexOfChildWithName(
162+
name.AsCString(), nullptr, omit_empty_base_classes);
163163
}
164164

165165
private:

lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.cpp

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -6504,7 +6504,8 @@ static uint32_t GetIndexForRecordChild(const clang::RecordDecl *record_decl,
65046504

65056505
size_t TypeSystemClang::GetIndexOfChildMemberWithName(
65066506
lldb::opaque_compiler_type_t type, const char *name,
6507-
bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
6507+
ExecutionContext *exe_ctx, bool omit_empty_base_classes,
6508+
std::vector<uint32_t> &child_indexes) {
65086509
if (type && name && name[0]) {
65096510
clang::QualType qual_type = RemoveWrappingTypes(GetCanonicalQualType(type));
65106511
const clang::Type::TypeClass type_class = qual_type->getTypeClass();
@@ -6532,7 +6533,7 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
65326533
CompilerType field_type = GetType(field->getType());
65336534
child_indexes.push_back(child_idx);
65346535
if (field_type.GetIndexOfChildMemberWithName(
6535-
name, omit_empty_base_classes, child_indexes))
6536+
name, exe_ctx, omit_empty_base_classes, child_indexes))
65366537
return child_indexes.size();
65376538
child_indexes.pop_back();
65386539

@@ -6641,7 +6642,7 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
66416642
GetType(getASTContext().getObjCInterfaceType(
66426643
superclass_interface_decl));
66436644
if (superclass_clang_type.GetIndexOfChildMemberWithName(
6644-
name, omit_empty_base_classes, child_indexes)) {
6645+
name, exe_ctx, omit_empty_base_classes, child_indexes)) {
66456646
// We did find an ivar in a superclass so just return the
66466647
// results!
66476648
return child_indexes.size();
@@ -6661,7 +6662,7 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
66616662
llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())
66626663
->getPointeeType());
66636664
return objc_object_clang_type.GetIndexOfChildMemberWithName(
6664-
name, omit_empty_base_classes, child_indexes);
6665+
name, exe_ctx, omit_empty_base_classes, child_indexes);
66656666
} break;
66666667

66676668
case clang::Type::ConstantArray: {
@@ -6713,7 +6714,7 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
67136714

67146715
if (pointee_clang_type.IsAggregateType()) {
67156716
return pointee_clang_type.GetIndexOfChildMemberWithName(
6716-
name, omit_empty_base_classes, child_indexes);
6717+
name, exe_ctx, omit_empty_base_classes, child_indexes);
67176718
}
67186719
} break;
67196720

@@ -6722,7 +6723,7 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
67226723

67236724
if (pointee_clang_type.IsAggregateType()) {
67246725
return pointee_clang_type.GetIndexOfChildMemberWithName(
6725-
name, omit_empty_base_classes, child_indexes);
6726+
name, exe_ctx, omit_empty_base_classes, child_indexes);
67266727
}
67276728
} break;
67286729

@@ -6737,10 +6738,9 @@ size_t TypeSystemClang::GetIndexOfChildMemberWithName(
67376738
// doesn't descend into the children, but only looks one level deep and name
67386739
// matches can include base class names.
67396740

6740-
uint32_t
6741-
TypeSystemClang::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
6742-
const char *name,
6743-
bool omit_empty_base_classes) {
6741+
uint32_t TypeSystemClang::GetIndexOfChildWithName(
6742+
lldb::opaque_compiler_type_t type, const char *name,
6743+
ExecutionContext *exe_ctx, bool omit_empty_base_classes) {
67446744
if (type && name && name[0]) {
67456745
clang::QualType qual_type = RemoveWrappingTypes(GetCanonicalQualType(type));
67466746

@@ -6842,7 +6842,7 @@ TypeSystemClang::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
68426842
llvm::cast<clang::ObjCObjectPointerType>(qual_type.getTypePtr())
68436843
->getPointeeType());
68446844
return pointee_clang_type.GetIndexOfChildWithName(
6845-
name, omit_empty_base_classes);
6845+
name, exe_ctx, omit_empty_base_classes);
68466846
} break;
68476847

68486848
case clang::Type::ConstantArray: {
@@ -6892,7 +6892,7 @@ TypeSystemClang::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
68926892
CompilerType pointee_type = GetType(reference_type->getPointeeType());
68936893

68946894
if (pointee_type.IsAggregateType()) {
6895-
return pointee_type.GetIndexOfChildWithName(name,
6895+
return pointee_type.GetIndexOfChildWithName(name, exe_ctx,
68966896
omit_empty_base_classes);
68976897
}
68986898
} break;
@@ -6903,7 +6903,7 @@ TypeSystemClang::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
69036903
CompilerType pointee_type = GetType(pointer_type->getPointeeType());
69046904

69056905
if (pointee_type.IsAggregateType()) {
6906-
return pointee_type.GetIndexOfChildWithName(name,
6906+
return pointee_type.GetIndexOfChildWithName(name, exe_ctx,
69076907
omit_empty_base_classes);
69086908
} else {
69096909
// if (parent_name)

lldb/source/Plugins/TypeSystem/Clang/TypeSystemClang.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -821,7 +821,7 @@ class TypeSystemClang : public TypeSystem {
821821
// Lookup a child given a name. This function will match base class names and
822822
// member member names in "clang_type" only, not descendants.
823823
uint32_t GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
824-
const char *name,
824+
const char *name, ExecutionContext *exe_ctx,
825825
bool omit_empty_base_classes) override;
826826

827827
// Lookup a child member given a name. This function will match member names
@@ -832,7 +832,8 @@ class TypeSystemClang : public TypeSystem {
832832
// so we catch all names that match a given child name, not just the first.
833833
size_t
834834
GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type,
835-
const char *name, bool omit_empty_base_classes,
835+
const char *name, ExecutionContext *exe_ctx,
836+
bool omit_empty_base_classes,
836837
std::vector<uint32_t> &child_indexes) override;
837838

838839
size_t GetNumTemplateArguments(lldb::opaque_compiler_type_t type) override;

lldb/source/Plugins/TypeSystem/Swift/SwiftASTContext.cpp

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -7259,8 +7259,8 @@ CompilerType SwiftASTContext::GetChildCompilerTypeAtIndex(
72597259
// second index 1 is the child index for "m_b" within class A.
72607260

72617261
size_t SwiftASTContext::GetIndexOfChildMemberWithName(
7262-
opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes,
7263-
std::vector<uint32_t> &child_indexes) {
7262+
opaque_compiler_type_t type, const char *name, ExecutionContext *exe_ctx,
7263+
bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
72647264
VALID_OR_RETURN(0);
72657265

72667266
if (type && name && name[0]) {
@@ -7282,7 +7282,7 @@ size_t SwiftASTContext::GetIndexOfChildMemberWithName(
72827282
case swift::TypeKind::UnownedStorage:
72837283
case swift::TypeKind::WeakStorage:
72847284
return ToCompilerType(swift_can_type->getReferenceStorageReferent())
7285-
.GetIndexOfChildMemberWithName(name, omit_empty_base_classes,
7285+
.GetIndexOfChildMemberWithName(name, exe_ctx, omit_empty_base_classes,
72867286
child_indexes);
72877287
case swift::TypeKind::GenericTypeParam:
72887288
case swift::TypeKind::DependentMember:
@@ -7363,7 +7363,7 @@ size_t SwiftASTContext::GetIndexOfChildMemberWithName(
73637363
CompilerType superclass_type =
73647364
ToCompilerType(superclass_swift_type.getPointer());
73657365
if (superclass_type.GetIndexOfChildMemberWithName(
7366-
name, omit_empty_base_classes, child_indexes))
7366+
name, exe_ctx, omit_empty_base_classes, child_indexes))
73677367
return child_indexes.size();
73687368

73697369
// We didn't find a stored property matching "name" in our
@@ -7409,7 +7409,7 @@ size_t SwiftASTContext::GetIndexOfChildMemberWithName(
74097409

74107410
if (pointee_clang_type.IsAggregateType()) {
74117411
return pointee_clang_type.GetIndexOfChildMemberWithName(
7412-
name, omit_empty_base_classes, child_indexes);
7412+
name, exe_ctx, omit_empty_base_classes, child_indexes);
74137413
}
74147414
} break;
74157415
case swift::TypeKind::UnboundGeneric:

lldb/source/Plugins/TypeSystem/Swift/SwiftASTContext.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -610,7 +610,8 @@ class SwiftASTContext : public TypeSystemSwift {
610610
// name, not just the first.
611611
size_t
612612
GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type,
613-
const char *name, bool omit_empty_base_classes,
613+
const char *name, ExecutionContext *exe_ctx,
614+
bool omit_empty_base_classes,
614615
std::vector<uint32_t> &child_indexes) override;
615616

616617
size_t GetNumTemplateArguments(lldb::opaque_compiler_type_t type) override;

lldb/source/Plugins/TypeSystem/Swift/TypeSystemSwift.cpp

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -102,12 +102,11 @@ bool TypeSystemSwift::ShouldTreatScalarValueAsAddress(
102102
.AnySet(eTypeInstanceIsPointer | eTypeIsReference);
103103
}
104104

105-
uint32_t
106-
TypeSystemSwift::GetIndexOfChildWithName(opaque_compiler_type_t type,
107-
const char *name,
108-
bool omit_empty_base_classes) {
105+
uint32_t TypeSystemSwift::GetIndexOfChildWithName(
106+
opaque_compiler_type_t type, const char *name, ExecutionContext *exe_ctx,
107+
bool omit_empty_base_classes) {
109108
std::vector<uint32_t> child_indexes;
110109
size_t num_child_indexes = GetIndexOfChildMemberWithName(
111-
type, name, omit_empty_base_classes, child_indexes);
110+
type, name, exe_ctx, omit_empty_base_classes, child_indexes);
112111
return num_child_indexes == 1 ? child_indexes.front() : UINT32_MAX;
113112
}

lldb/source/Plugins/TypeSystem/Swift/TypeSystemSwift.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -246,7 +246,7 @@ class TypeSystemSwift : public TypeSystem {
246246
/// Lookup a child given a name. This function will match base class names
247247
/// and member names in \p type only, not descendants.
248248
uint32_t GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
249-
const char *name,
249+
const char *name, ExecutionContext *exe_ctx,
250250
bool omit_empty_base_classes) override;
251251

252252
/// \}

lldb/source/Plugins/TypeSystem/Swift/TypeSystemSwiftTypeRef.cpp

Lines changed: 66 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,9 @@
3535
#include "clang/APINotes/APINotesManager.h"
3636
#include "clang/APINotes/APINotesReader.h"
3737

38+
#include <algorithm>
39+
#include <sstream>
40+
3841
using namespace lldb;
3942
using namespace lldb_private;
4043

@@ -2324,7 +2327,7 @@ CompilerType TypeSystemSwiftTypeRef::GetChildCompilerTypeAtIndex(
23242327
if (m_swift_ast_context->GetNumChildren(ReconstructType(type),
23252328
omit_empty_base_classes, exe_ctx) <
23262329
runtime->GetNumChildren({this, type}, valobj).getValueOr(0))
2327-
return fallback();
2330+
return impl();
23282331

23292332
#ifndef NDEBUG
23302333
std::string ast_child_name;
@@ -2365,11 +2368,70 @@ CompilerType TypeSystemSwiftTypeRef::GetChildCompilerTypeAtIndex(
23652368
}
23662369

23672370
size_t TypeSystemSwiftTypeRef::GetIndexOfChildMemberWithName(
2368-
opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes,
2369-
std::vector<uint32_t> &child_indexes) {
2371+
opaque_compiler_type_t type, const char *name, ExecutionContext *exe_ctx,
2372+
bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
2373+
if (auto *exe_scope = exe_ctx->GetBestExecutionContextScope())
2374+
if (auto *runtime =
2375+
SwiftLanguageRuntime::Get(exe_scope->CalculateProcess()))
2376+
if (auto index_size = runtime->GetIndexOfChildMemberWithName(
2377+
GetCanonicalType(type), name, exe_ctx, omit_empty_base_classes,
2378+
child_indexes)) {
2379+
#ifndef NDEBUG
2380+
// This block is a custom VALIDATE_AND_RETURN implementation to support
2381+
// checking the return value, plus the by-ref `child_indexes`.
2382+
if (!m_swift_ast_context)
2383+
return *index_size;
2384+
auto ast_type = ReconstructType(type);
2385+
if (!ast_type)
2386+
return *index_size;
2387+
std::vector<uint32_t> ast_child_indexes;
2388+
auto ast_index_size = m_swift_ast_context->GetIndexOfChildMemberWithName(
2389+
ast_type, name, exe_ctx, omit_empty_base_classes,
2390+
ast_child_indexes);
2391+
// The runtime has more info than the AST. No useful validation can be
2392+
// done.
2393+
if (*index_size > ast_index_size)
2394+
return *index_size;
2395+
2396+
auto fail = [&]() {
2397+
auto join = [](const auto &v) {
2398+
std::ostringstream buf;
2399+
buf << "{";
2400+
for (const auto &item : v)
2401+
buf << item << ",";
2402+
buf.seekp(-1, std::ios_base::end);
2403+
buf << "}";
2404+
return buf.str();
2405+
};
2406+
llvm::dbgs() << join(child_indexes)
2407+
<< " != " << join(ast_child_indexes) << "\n";
2408+
llvm::dbgs() << "failing type was " << (const char *)type
2409+
<< ", member was " << name << "\n";
2410+
assert(false &&
2411+
"TypeSystemSwiftTypeRef diverges from SwiftASTContext");
2412+
};
2413+
if (*index_size != ast_index_size)
2414+
fail();
2415+
for (unsigned i = 0; i < *index_size; ++i)
2416+
if (child_indexes[i] < ast_child_indexes[i])
2417+
// When the runtime may know know about more children. When this
2418+
// happens, indexes will be larger. But if an index is smaller, that
2419+
// means the runtime has dropped info somehow.
2420+
fail();
2421+
#endif
2422+
return *index_size;
2423+
}
2424+
2425+
LLDB_LOGF(GetLogIfAllCategoriesSet(LIBLLDB_LOG_TYPES),
2426+
"Using SwiftASTContext::GetIndexOfChildMemberWithName fallback for "
2427+
"type %s",
2428+
AsMangledName(type));
2429+
23702430
return m_swift_ast_context->GetIndexOfChildMemberWithName(
2371-
ReconstructType(type), name, omit_empty_base_classes, child_indexes);
2431+
ReconstructType(type), name, exe_ctx, omit_empty_base_classes,
2432+
child_indexes);
23722433
}
2434+
23732435
size_t
23742436
TypeSystemSwiftTypeRef::GetNumTemplateArguments(opaque_compiler_type_t type) {
23752437
return m_swift_ast_context->GetNumTemplateArguments(ReconstructType(type));

lldb/source/Plugins/TypeSystem/Swift/TypeSystemSwiftTypeRef.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -167,7 +167,8 @@ class TypeSystemSwiftTypeRef : public TypeSystemSwift {
167167
ValueObject *valobj, uint64_t &language_flags) override;
168168
size_t
169169
GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type,
170-
const char *name, bool omit_empty_base_classes,
170+
const char *name, ExecutionContext *exe_ctx,
171+
bool omit_empty_base_classes,
171172
std::vector<uint32_t> &child_indexes) override;
172173
size_t GetNumTemplateArguments(lldb::opaque_compiler_type_t type) override;
173174
CompilerType GetTypeForFormatters(lldb::opaque_compiler_type_t type) override;

lldb/source/Symbol/CompilerType.cpp

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -654,11 +654,11 @@ CompilerType CompilerType::GetChildCompilerTypeAtIndex(
654654
// index 1 is the child index for "m_b" within class A
655655

656656
size_t CompilerType::GetIndexOfChildMemberWithName(
657-
const char *name, bool omit_empty_base_classes,
657+
const char *name, ExecutionContext *exe_ctx, bool omit_empty_base_classes,
658658
std::vector<uint32_t> &child_indexes) const {
659659
if (IsValid() && name && name[0]) {
660660
return m_type_system->GetIndexOfChildMemberWithName(
661-
m_type, name, omit_empty_base_classes, child_indexes);
661+
m_type, name, exe_ctx, omit_empty_base_classes, child_indexes);
662662
}
663663
return 0;
664664
}
@@ -714,9 +714,10 @@ bool CompilerType::IsMeaninglessWithoutDynamicResolution() const {
714714

715715
uint32_t
716716
CompilerType::GetIndexOfChildWithName(const char *name,
717+
ExecutionContext *exe_ctx,
717718
bool omit_empty_base_classes) const {
718719
if (IsValid() && name && name[0]) {
719-
return m_type_system->GetIndexOfChildWithName(m_type, name,
720+
return m_type_system->GetIndexOfChildWithName(m_type, name, exe_ctx,
720721
omit_empty_base_classes);
721722
}
722723
return UINT32_MAX;

0 commit comments

Comments
 (0)