Skip to content

[IRGen] Fix crasher in emitPartialApplicationForwarder when the result type is a struct. #22401

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

Merged
merged 2 commits into from
Feb 7, 2019

Conversation

rxwei
Copy link
Contributor

@rxwei rxwei commented Feb 6, 2019

In emitPartialApplicationForwarder, when we handle result types that have a type parameter, the lowered result type could be a struct. This happens when we have a function result, for instance:

  %0 = function_ref @returns_closure : $@convention(thin) <τ_0_0> (Empty<τ_0_0>) -> (@owned Empty<τ_0_0>, @owned @callee_guaranteed (Empty<τ_0_0>) -> @owned Empty<τ_0_0>)
  %1 = partial_apply [callee_guaranteed] %0<S>() : $@convention(thin) <τ_0_0> (Empty<τ_0_0>) -> (@owned Empty<τ_0_0>, @owned @callee_guaranteed (Empty<τ_0_0>) -> @owned Empty<τ_0_0>)

In this case, we emit code that casts the struct memberwise.

Resolves SR-9709.

…urn type is a tuple that contains a closure.

In `emitPartialApplicationForwarder`, when we handle result types that have a type parameter, the lowered result type could be a struct.
This happens when we have a function result, for instance:

```swift
  %0 = function_ref @returns_closure : $@convention(thin) <τ_0_0> (Empty<τ_0_0>) -> (@owned Empty<τ_0_0>, @owned @callee_guaranteed (Empty<τ_0_0>) -> @owned Empty<τ_0_0>)
  %1 = partial_apply [callee_guaranteed] %0<S>() : $@convention(thin) <τ_0_0> (Empty<τ_0_0>) -> (@owned Empty<τ_0_0>, @owned @callee_guaranteed (Empty<τ_0_0>) -> @owned Empty<τ_0_0>)
```

In this case, we emit code that casts the struct memberwise.

Resolves [SR-9709](https://bugs.swift.org/browse/SR-9709).
@rxwei rxwei requested a review from aschwaighofer February 6, 2019 00:24
for (auto i : range(structType->getStructNumElements())) {
auto desiredEltTy = structType->getElementType(i);
auto elt = subIGF.Builder.CreateExtractValue(callResult, {i});
auto castElt = subIGF.Builder.CreateBitCast(elt, desiredEltTy);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Don't you need a recursion here?

Maybe emitCastToSubstSchema() can be used here?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know enough IRGen. Can any element be a nested struct? I assumed everything has been exploded at this stage.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Everything is going to be exploded. When we form a direct return value we call getScalarResultType (among other things) which makes this assumption.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You could use IRGenFunction::coerceValue instead.

    // If the result type is dependent on a type parameter we might have to
    // cast to the result type - it could be substituted.
    if (origConv.getSILResultType().hasTypeParameter()) {
      auto ResType = fwd->getReturnType();
      if (ResType != callResult->getType())
        callResult =
          subIGF.coerceValue(callResult, ResType, subIGF.IGM.DataLayout);
    }
    subIGF.Builder.CreateRet(callResult);

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

coerceValue() looks much cleaner, thanks Arnold!

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done. This is much nicer :)

@rxwei
Copy link
Contributor Author

rxwei commented Feb 6, 2019

@swift-ci please smoke test

@rxwei
Copy link
Contributor Author

rxwei commented Feb 7, 2019

@swift-ci please smoke test and merge

@swift-ci swift-ci merged commit 2415111 into swiftlang:master Feb 7, 2019
@rxwei rxwei deleted the SR-9709 branch February 7, 2019 01:36
rxwei pushed a commit that referenced this pull request Jun 23, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants