-
Notifications
You must be signed in to change notification settings - Fork 344
[lldb] Add ReferenceTypeInfo support to SwiftLanguageRuntimeImpl::GetNumChildren #2218
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[lldb] Add ReferenceTypeInfo support to SwiftLanguageRuntimeImpl::GetNumChildren #2218
Conversation
@@ -997,6 +997,38 @@ llvm::Optional<uint64_t> SwiftLanguageRuntimeImpl::GetMemberVariableOffset( | |||
return offset; | |||
} | |||
|
|||
static CompilerType GetWeakReferent(TypeSystemSwiftTypeRef &ts, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this whole function was moved up and nothing more.
GetTypeInfo(CompilerType type, ExecutionContextScope *exe_scope, | ||
swift::reflection::TypeRef const **out_tr = nullptr); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added an out parameter to return the typeref.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It might be cleaner to factor out a function
const swift::reflection::TypeInfo *GetTypeInfo(swift::reflection::TypeRef type_ref)
and call that directly where we need the type_ref? If it isn't, then returning either a std::pair<>
or a struct {TypeInfo type_info; TypeRef type_ref}
may be more elegant.
Initial draft for availability/review, haven't done tests yet. |
TODO
|
auto *reflection_ctx = GetReflectionContext(); | ||
auto tc = swift::reflection::TypeConverter(reflection_ctx->getBuilder()); | ||
LLDBTypeInfoProvider tip(*this, *ts); | ||
auto *cti = tc.getClassInstanceTypeInfo(tr, 0, &tip); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have a todo to figure out if other values should be used instead of 0
for start
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The tests pass, and no SwiftASTContext
validations fail when using start = 0
. I'll learn more about this field before merging, but I don't think it's an issue.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sounds good.
auto *cti = tc.getClassInstanceTypeInfo(tr, 0, &tip); | ||
if (auto *rti = | ||
llvm::dyn_cast_or_null<swift::reflection::RecordTypeInfo>(cti)) { | ||
return rti->getNumFields(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should this be a recursive case or will there only ever be a record type underneath a class? (Well, probably).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Currently it's only ever a RecordTypeInfo:
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We could factor out a helper function GetNumFieldsFromTypeInfo()
that calls itself here, but the savings are marginal.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll soon be implementing GetNumFields
, and which may call for some refactoring.
I have a question, by "calls itself" do you mean recursive like in your top comment? If so, can you elaborate on what needs to be recursive?
if (!tr) | ||
return {}; | ||
|
||
auto *reflection_ctx = GetReflectionContext(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would this fit nicely into one case in the switch above, or are there many different kinds for which this path makes sense?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
good question, I'm not sure yet. Once this PR is working, I'll compare the paths then.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What do you think? There are a couple distinct conditions in each case that don't make sense to the other case, and so combing the two doesn't feel like a no-brainer to me.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I was just thinking of writing this as
switch (rti->getReferenceKind()) {
case swift::reflection::ReferenceKind::Weak:
case swift::reflection::ReferenceKind::Unowned:
case swift::reflection::ReferenceKind::Unmanaged:
// Weak references are implicitly Optionals, so report the one
// child of Optional here.
if (GetWeakReferent(*ts, type))
return 1;
break;
default: {
if (!tr)
return {};
auto tc = swift::reflection::TypeConverter(reflection_ctx->getBuilder());
....
but that's purely cosmetic and not important at all...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
thanks, I had misunderstood. I will make that change in a follow up.
Currently one kind of test failure is with subclasses: Another test failure is something I mentioned in #2200, that |
Maybe you can reuse some of the code used in GetChildCompilerTypeAtIndex for this (although it does start out from an instance pointer).
That's actually a good thing and precisely what we need in order for Foundation value types to work! |
yes I was excited to see it! |
I figured I'd need a way to do it with just the reflection API (no instance), and I found |
@swift-ci test |
@swift-ci test |
Tests pass locally, hopefully CI too. Ready for review. |
To follow up here, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Functionally this LGTM. I have only cosmetic comments and those can also be addressed later.
Thanks, I will do the cosmetic changes in a followup, primarily because I don't want to wait another full test cycle. |
Add
ReferenceTypeInfo
support toSwiftLanguageRuntimeImpl::GetNumChildren
. This usesTypeConverter::getClassInstanceTypeInfo
to get aRecordTypeInfo
for a class. And usesTypeRefBuilder::lookupSuperclass
to determine if a class has a superclass (base class).rdar://68171335