Skip to content

Various existential l-value fixes #9864

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

Conversation

rjmccall
Copy link
Contributor

@rjmccall rjmccall commented May 23, 2017

There are a variety of problems with SILGen for class and metatype existential values held in mutable variables. Those problems are currently masked for class types by a quirk of Sema, which we are not proposing to change in swift-4.0-branch. However, they are exposed for metatype values, leading to crashes in SILGen.

This combines #9637 and #9852 for swift-4.0-branch. It fixes rdar://32288618.

This patch affects code generation for mutable existential l-values. Because of the quirk in Sema, its largest impact is on existential metatypes: specifically, when they're held in mutable variables.

The risk is fairly low. This patch does change some important code paths, but they are relatively well-tested for the most important cases. The main case affected otherwise is the existential-metatype case, which currently just doesn't compile at all.

This has been tested with our full regression test suite.

slavapestov and others added 5 commits May 23, 2017 01:43
This is an LValue component whose value is the class
reference inside of a class existential.

Unlike OpenOpaqueExistentialComponent, this is a logical
component, with a "writeback" consisting of wrapping the
new class reference in a class existential having the
same conformances as the original.

This is slightly awkward, but adding "by-address" operations
on class existentials, and projecting the payload out is
a big change and might not make sense for other reasons.
…s as lvalues

This is part of allowing lvalue access on class existential
payloads.
…ntials

This is pretty awkward. If an lvalue has an open existential
as its RValue type, we would emit an alloc_stack instruction
holding the materialized temporary before we emitted the
value itself. This introduced a def-after-use violation
because the open existential type in the stack allocation
was not dominated by its definition.

To get around this, don't use an SGFContext to emit the 'get'
in-place. There's no performance degradation, because the only
time we will attempt materializing an lvalue with an open
existential type is when performing an lvalue access of a
class existential payload, and here we in-place initialization
makes no difference since the value is a single reference.
@rjmccall
Copy link
Contributor Author

@swift-ci Please test.

@rjmccall
Copy link
Contributor Author

@slavapestov Does this seem at all reasonable?

@slavapestov
Copy link
Contributor

LGTM.

@tkremenek tkremenek merged commit fc7d9ec into swiftlang:swift-4.0-branch May 23, 2017
@rjmccall rjmccall deleted the existential-lvalue-fixes branch May 23, 2017 21:26
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.

3 participants