Some notes:
This is not emitted by SILGen. This is just intended to be used so I can write
SIL test cases for transfer non sendable. I did this by adding an
ActorIsolationCrossing field to all FullApplySites rather than adding it into
the type system on a callee. The reason that this makes sense from a modeling
perspective is that an actor isolation crossing is a caller concept since it is
describing a difference in between the caller's and callee's isolation. As a
bonus it makes this a less viral change.
For simplicity, I made it so that the isolation is represented as an optional
modifier on the instructions:
apply [callee_isolation=XXXX] [caller_isolation=XXXX]
where XXXX is a printed representation of the actor isolation.
When neither callee or caller isolation is specified then the
ApplyIsolationCrossing is std::nullopt. If only one is specified, we make the
other one ActorIsolation::Unspecified.
This required me to move ActorIsolationCrossing from AST/Expr.h ->
AST/ActorIsolation.h to work around compilation issues... Arguably that is where
it should exist anyways so it made sense.
rdar://118521597
* `alloc_vector`: allocates an uninitialized vector of elements on the stack or in a statically initialized global
* `vector`: creates an initialized vector in a statically initialized global
If the var is captured in a closure before it is transferred, it is not safe to
access the Sendable field since we may race on accessing the field with an
assignment to the field in another concurrency domain.
rdar://115124361
To verify if a function may read from an indirect argument, don't use AliasAnalysis.
Instead use the CalleeCache to get the list of callees of an apply instruction.
Then use a simple call-back into the swift Function to check if a callee has any relevant memory effect set.
This avoids a dependency from SIL to the Optimizer.
It fixes a linker error when building some unit tests in debug.
* add `NominalTypeDecl.isResilient`
* make the return type of `Type.getNominalFields` optional and return nil in case the nominal type is resilient.
This forces users of this API to think about what to do in case the nominal type is resilient.
To do this I used 8 spare bits in the pointers in Operand for the custom flags.
The reason I did this is just like one sometimes wants to iterate and use
sets/worklists with Nodes/Blocks, one often wants to do it with operands
especially in situations where one wants to know a using instruction and the
value on the instruction that was used.
`getRootLocalArchetypeDef()` may return a `PlaceholderValue` which makes the
`cast<SingleValueInstruction>` invalid. Use `dyn_cast` and then update the
callers of `getRootLocalArchetypeDefInst()` to handle `nullptr`.
[region-isolation] Since we now propagate the transferred instruction, use that to emit the error instead of attempting to infer the transfer instruction for a requires
This class is more or less just duplicating LLVM's
`Counter` class, as such we can just wrap it
directly and avoid having to construct it later.
This is a tentative fix for rdar://118185163 since
it eliminates the code in question, though I still
want to investigate that issue further.
This is another NFC refactor in preparation for changing how we emit
errors. Specifically, we need access to not only the instruction, but also the
specific operand that the transfer occurs at. This ensures that we can look up
the specific type information later when we emit an error rather than tracking
this information throughout the entire pass.
Previously if one wanted to get an ASTNode, one needed to use the
getAsASTNode<T>() type. If one just wants to get out the type and use it in a
generic way using ASTNode there wasn't any way to do this... so I did it. We
actually have to do the marshalling here since ASTNodeTy and ASTNode have
different layouts despite them both being PointerUnions. So one can't just cast
in between them =---(.
Avoid heap-allocating an immortal FunctionTest with `new` because it
results in LSAN reporting a leak.
In fact, the "leaked" value wasn't leaked: a reference to it was stored
in a global map when the type's constructor ran. It was only a leak in
the sense that it was never freed, not that there was a dangling
allocation which couldn't be freed.
Work around this by storing the global instances themselves in a second
static structure. Store pointers to the instances into the global map
as before.
rdar://118134637