Skip to content

IRGen: Correctly compute instanceStart for a Swift class that starts … #29219

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

Conversation

aschwaighofer
Copy link
Contributor

…with an empty field and is followed by a resilient field

We used to crash for classes that have an empty and a resilient field
during intialization if the object was in the shared cache.

class CrashInInit {
var empty = EmptyStruct()
var resilient = ResilientThing()
}

What happened was that for such a class we we would compute a
instanceStart of 0. The shared cache builder would then slide the value
of the constant ivar offset for the empty field from 0 to 16. However,
the field offset for empty fields is assumed to be zero and the runtime
does not compute a different value for the empty field and so the field
offset for the empty field remains 0. The runtime then trys to reconcile
the field offset (0) and the ivar offset (16) trying to write to the ivar
offset. However, the ivar offset is marked as constant and so we
crashed.
This can be avoided by correctly computing the instanceStart for such a
class to be 16 such that the shared cache builder does not update the
value of the empty field.

rdar://rdar://58458169

…with an empty field and is followed by a resilient field

We used to crash for classes that have an empty and a resilient field
during intialization if the object was in the shared cache.

  class CrashInInit {
    var empty = EmptyStruct()
    var resilient = ResilientThing()
  }

What happened was that for such a class we we would compute a
instanceStart of 0. The shared cache builder would then slide the value
of the constant ivar offset for the empty field from 0 to 16. However,
the field offset for empty fields is assumed to be zero and the runtime
does not compute a different value for the empty field and so the field
offset for the empty field remains 0. The runtime then trys to reconcile
the field offset (0) and the ivar offset (16) trying to write to the ivar
offset. However, the ivar offset is marked as constant and so we
crashed.
This can be avoided by correctly computing the instanceStart for such a
class to be 16 such that the shared cache builder does not update the
value of the empty field.

rdar://rdar://58458169
@aschwaighofer
Copy link
Contributor Author

@swift-ci Please test

@mikeash
Copy link
Contributor

mikeash commented Jan 15, 2020

Thanks for working through this, Arnold!

@swift-ci
Copy link
Contributor

Build failed
Swift Test Linux Platform
Git Sha - 7f20d93

@aschwaighofer
Copy link
Contributor Author

@swift-ci Please test

@swift-ci
Copy link
Contributor

Build failed
Swift Test OS X Platform
Git Sha - 7f20d93

@swift-ci
Copy link
Contributor

Build failed
Swift Test Linux Platform
Git Sha - 7f20d93

Copy link
Contributor

@jckarter jckarter left a comment

Choose a reason for hiding this comment

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

Makes sense to me. Thanks for working through this again!

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