- Notifications
You must be signed in to change notification settings - Fork 10.6k
[SR-13503] [Sema] Special InsertExplicitCall for nominal callable types #34006
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
[SR-13503] [Sema] Special InsertExplicitCall for nominal callable types #34006
Conversation
01e36b6 to 9cac752 Compare
xedin left a comment
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 approach makes sense to me, but I think we need to use existing functionality to form implicit call and match result. I have left a couple of comments about this inline.
274fa09 to a6bb7a0 Compare 51b2702 to 8f73343 Compare 4bcc9d2 to 203dbe6 Compare | @swift-ci Please smoke test |
07f0d2f to a83c10b Compare | @swift-ci Please smoke test |
d92b4b5 to e52ecc9 Compare | @swift-ci Please smoke test |
9e22659 to df9c27d Compare a968b59 to 84b7e61 Compare lib/Sema/CSSimplify.cpp Outdated
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.
Let's rephrase this a bit:
If this is a call formed by a fix to attempt explicit call of a callable type to see if that would match expected contextual type, let's fail if some of the expected arguments are missing.
But I also don't fully understand why do we want to do that? I think the idea where would be to suggest adding a call and missing arguments, no? I guess we'd just need to adjust a fix for synthesized arguments to handle implicit calls to support that...
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 think the idea where would be to suggest adding a call and missing arguments, no?
Not really sure, that would mean a fix for a declaration like func callAsFunction(a: Int) -> Int { 0 } would be (a: <#editor placeholder#>)?
I guess we'd just need to adjust a fix for synthesized arguments to handle implicit calls to support that...
I didn't get it, have to take a look into this synthesized fix first :)
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.
bq. Not really sure, that would mean a fix for a declaration like func callAsFunction(a: Int) -> Int { 0 } would be (a: <#editor placeholder#>)?
Yeah, that's exactly how I see it.
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.
Ahh, I thought about this at the beginning, but as I was looking at the existing InsertExplicitCall fix for function types and since it didn't have this, I figure it would be something more simple to maintain this behavior here. Do you think is worth introducing this here for both?
Also, in the beginning, I was trying to think from the user perspective that to insert a () call in value mismatch is more likely to be an expected fix than a call with parameters, so the more generic mismatch fix would fit better in this 'with params' case? I'm not sure, just trying to think if insert explicit call would be a better diagnostic in this case :)
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 is going to be tricky because we'd effectively have to combine (or coalesce) missing arguments with missing call fix to make it work. I think we'd need some test cases to make sure that if this happens diagnostic logic wouldn't crash since there is no call :)
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.
Yeah, I was also thinking about some other cases where we should give a good thought about like
struct S { func callAsFunction(a: Int) -> Int { 0 } func callAsFunction(b: String) -> Int { 0 } } What we should do in a mismatchS and Int like suggest one or another doesn't feel right...
So offer two fix-its? In that case, diagnostic wording should probably change in those situations.
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 think in this case, if there are no other options, diagnostic should just say that call is missing and let the developer disambiguate...
lib/Sema/CSSimplify.cpp Outdated
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 not help but I suspect it also hurts something if we have to do this explicitly? :)
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.
Hum, I have to remember exactly which is the case for this ... but I'll take a more detailed look
lib/Sema/CSSimplify.cpp Outdated
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.
If I understand it correctly, all of the checks for isForImplicitApplyCallableValue sprinkled around the code are necessary because there is no way to come back to a generic "fix" for a type mismatch?... If that's the same then the solution would be to add one more option to the overload set for explicit call which would just register that generic fix and do nothing else - that way we don't need any special handling for call overloads which didn't match...
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.
Humm, that would be to add a fixed choice constraint as the last constraint before addOverloadSet?
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.
Yeah, we'd probably need to do a lookup as part of a fix and adjust the overload set to have that "fallback" choice.
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.
Hum, when trying to do this I was struggling because as my understanding we would have to Constraint::createFixedChoice but didn't know what would be the "fallback" overload choice?
do a lookup as part of a fix
Sorry, not sure I understand this part, that means we have to do a lookup in order to create the fallback fixed choice constraint?
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.
As I see it the logic here would be to:
- Use
performMemberLookupto form a member set, add a "fallback" choice like "don't do anything but apply a fix (e.g.ContextualMismatchone) - Construct an
ApplicableFunctionconstraint to imitate presence of a missing call.
This way if any of the choices found by lookup produce other fixes they'd be considered a worse solution vs. the "fallback".
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.
Ahh great, thank you @xedin :)
I will get back to this soon
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.
Hey @xedin :)
While getting back to this I've found this behavior SR-13844, so I'm thinking before moving on with this I should take a look at that problem. WDYT?
I'm just asking because I've seen that there is a TODO of some refactors needed in simplifyDynamicCallableApplication and I'm trying to organize between some SRs/PRs I've opened.
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.
@LucianoPAlmeida I think it would make sense to refactor some of the code around that area before going back to this, it might make it easier.
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.
Right, thanks @xedin!
I'll take a look at that 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.
Great!
84b7e61 to 236b8bc Compare f5f8b8a to 49e89bc Compare 7ca544e to 29a798f Compare f366e50 to 897046b Compare 897046b to 3e24dee Compare …meter that handles access control
…we attempting to verify if a value can be called to produce expected type
…ctly produce mismatch diagnostics for parameterized overload
… callable value can be explicit called to produce type
… for callable values
f70c96b to 32f0449 Compare 32f0449 to 640fbe6 Compare | Just organizing some old PRs, so closing this. It's linked to the ticket for future reference =] |
Detect if a type mismatch we the source type is a callable nominal and has a
callAsFunctionthat produces the destination type, so we can suggest making it an explicit call to it.Resolves SR-13503.