A lazy property setter stores a value to the underlying storage
of the lazy property. The underlying storage is private, and it
is not proper for a public transparent function body to reference
a private member.
In practice, this only failed if the private member had a
non-constant offset, which only occurs with subclasses of @objc
classes, and resilient classes.
For @objc classes we already had a workaround where no accessors
for stored properties are ever transparent. I put this in to fix
this very issue with lazy properties, but now I realize it was
the wrong workaround, because we still had this problem with
resilient classes.
Note that I'm keeping the logic which made @objc accessors
non-transparent in place, because there's a good chance we will
decide that field offset globals should always be private.
Also, to make this issue reproducible in the test, I changed the
resilience execution tests to build the resilient library as a
dylib and link against that instead of just linking .o files
together. This is because .o files can see each other's internal
symbols, so I was not able to reproduce the original failure
this way. I went ahead and updated the other resilient tests to
do this as well. Also, each test now builds in WMO and non-WMO
mode, to exercise different SIL linking behavior. Again, the
WMO variant was needed to reproduce the issue fixed by this
commit, because without WMO we currently discard serialized SIL,
so no cross-module inlining of the lazy property setter was
taking place.
This is needed if we compile StdlibUnittest with -sil-serialize-all
So far I added the imports only in files which needed them. But this may change, depending on the optimizer (inlining).
Adding them in all files doesn't harm and avoids confusion if someone makes an unrelated change which would result in such a linker error.
It is still not clear to me when we access global variables from other
modules directly, versus using accessors; it seems to be controlled
by the -sil-serialize-all flag, rather than any language feature.
Until/if we add a @_fixed_layout equivalent for globals, I can't really
test direct access of globals from other modules; when we figure out
the story here I'll be able to add more tests and also tighten up
some isResilient() checks in the global code, but what's in there now
seems to work.