Commit Graph

2592 Commits

Author SHA1 Message Date
swift-ci
54862c1439 Merge pull request #64700 from meg-gupta/updatehaspointerescapedce
Support all BorrowedValueKind in hasPointerEscape(BorrowedValue) api
2023-03-29 00:36:03 -07:00
Meghana Gupta
a135f4fc50 Check lexicality at reborrow instead of borrow while disabling DCE 2023-03-28 20:31:32 -07:00
Meghana Gupta
b77a3f8a38 Use the updated hasPointerEscape api in DCE 2023-03-28 20:31:32 -07:00
eeckstein
85986f4e58 Merge pull request #64635 from eeckstein/fix-inline-always
PerformanceInliner:  protect against misuse of @inline(__always)
2023-03-28 16:24:12 +02:00
Konrad `ktoso` Malawski
0586c14b60 [Concurrency] SerialExecutor.isSameExclusiveExecutionContext (#64604) 2023-03-28 15:56:28 +09:00
Nate Chandler
1a7c4a4d12 [NFC] Renamed DestroyAddrHoisting.
It was previously named SSADestroyHoisting which is rather misleading
considering that it deals with addresses and hoists destroy_addrs.
2023-03-27 14:15:03 -07:00
Erik Eckstein
0a4b0a8da7 PerformanceInliner: protect against misuse of @inline(__always)
Inline-always should only be used on relatively small functions. It must not be used on recursive functions.
Add a check that prevents that inlining of large @inline(__always) functions.

https://github.com/apple/swift/issues/64319
rdar://106655649
2023-03-27 17:29:37 +02:00
Nate Chandler
4f0d1dab5e [CopyPropagation] Canonicalize copies of lexical.
Currently, CopyPropagation only canonicalizes defs that are "canonical",
that is, the root of the copy_value tree.  When that canonical
def is lexical, however, the canonicalization respects deinit barriers.
But copies of lexical values are not themselves lexical, so their
lifetimes can be shortened without respect to deinit barriers.

Here, immediate copies of lexical values are canonicalized before the
lexical values themselves are.

rdar://107197935
2023-03-27 07:08:01 -07:00
Nate Chandler
ec3f005f31 [CanonOSSALifetime] Run on lexical lifetimes.
Previously, the utility bailed out on lexical lifetimes because it
didn't respect deinit barriers.  Here, deinit barriers are found and
added to liveness if the value is lexical.  This enables copies to be
propagated without hoisting destroys over deinit barriers.

rdar://104630103
2023-03-25 21:17:26 -07:00
Nate Chandler
4d4042931b [Reachability] NFC: Allow more initial blocks.
Allow clients to specify any number (an array) of blocks beyond which
dataflow won't propagate rather than 1 or 0 (a pointer).
2023-03-25 12:27:57 -07:00
Andrew Trick
119e712c32 Merge pull request #64534 from atrick/liveblocks-bitfield
Cleanup PrunedLiveBlocks
2023-03-22 16:33:08 -07:00
Andrew Trick
15796e3ff9 PrunedLiveness: add a SILFunction argument
So that liveness can migrate to using a SILBitfield.
2023-03-22 01:36:48 -07:00
nate-chandler
cee389033d Merge pull request #64495 from nate-chandler/copy-propagation/canonicalize-move-source
[CopyPropagation] Canonicalize moved-from values.
2023-03-21 12:14:11 -07:00
Erik Eckstein
8c05024ea6 SIL: move the SILInstruction::MemoryBehavior enum out of SILInstruction into the swift namespace 2023-03-21 15:33:09 +01:00
Nate Chandler
6b1bee7324 [CopyPropagation] Canonicalize moved-from values.
If a move_value is determined to be redundant and removed, take the
opportunity its removal makes available to canonicalize the moved-from
value without the obstruction of the move_value.
2023-03-20 18:04:57 -07:00
Anthony Latsis
e8be44d14e Merge pull request #64324 from AnthonyLatsis/cse-open-exist
SILOptimizer: Fix some issues with CSE of `open_existential_ref`
2023-03-17 17:26:09 +03:00
nate-chandler
3644d98d5f Merge pull request #64400 from nate-chandler/copy-propagation/run-side-effect-analysis-first
CopyPropagation: Compute side-effects first.
2023-03-16 18:17:39 -07:00
nate-chandler
1f3623d570 Merge pull request #64339 from nate-chandler/copy-propagation/redundant-move-elim
[CopyPropagation] Eliminate redundant moves.
2023-03-16 17:02:25 -07:00
Nate Chandler
ade29db6bd CopyPropagation: Compute side-effects first.
Add a run of ComputeSideEffects before the first run of CopyPropagation.
Allow hoisting over applies of functions that are able to be analyzed
not to be deinit barriers at this early point.
2023-03-16 13:01:05 -07:00
nate-chandler
1208d32d80 Merge pull request #64356 from nate-chandler/rdar106224845
[Mem2Reg] Instantiate arbitrary empty types.
2023-03-16 10:56:23 -07:00
Nate Chandler
16216924b1 [CopyPropagation] Eliminate redundant moves.
SemanticARCOpts already eliminates move values that are redundant that
block its optimizations.  But it's always run after CopyPropagation.

Because move_values divide copy-extended lifetimes, move_values obstruct
lifetime canonicalization.  If a move_value isn't separating lifetimes
with different characteristics (specifically: lexicallity, escaping),
then it is only obstructing lifetime canonicalization.  Remove it
before canonicalizing the lifetime of the moved-from value.
2023-03-15 11:56:27 -07:00
Konrad `ktoso` Malawski
41f99fc2ae [Executors][Distributed] custom executors for distributed actor (#64237)
* [Executors][Distributed] custom executors for distributed actor

* harden ordering guarantees of synthesised fields

* the issue was that a non-default actor must implement the is remote check differently

* NonDefaultDistributedActor to complete support and remote flag handling

* invoke nonDefaultDistributedActorInitialize when necessary in SILGen

* refactor inline assertion into method

* cleanup

* [Executors][Distributed] Update module version for NonDefaultDistributedActor

* Minor docs cleanup

* we solved those fixme's

* add mangling test for non-def-dist-actor
2023-03-15 23:42:55 +09:00
Nate Chandler
e9294539f0 [NFC] Switched to StackList.
No need for a worklist of any sort, a simple list suffices.
2023-03-15 07:38:59 -07:00
Nate Chandler
e089e95d09 [Mem2Reg] Instantiate arbitrary empty types.
Currently, memory locations whose type is empty (`SILType::isEmpty`) are
regarded as viable sources for loads.

Previously, though, Mem2Reg only handled loads from empty types formed
only by tupling.  Here, support is added for types formed also by
struct'ing.  As before, this entails recursively instantiating the empty
types until reaching the innermost empty types (which aggregate nothing)
and then aggregating the resulting instances.

rdar://106224845
2023-03-14 10:54:22 -07:00
Anthony Latsis
d650ce47f3 SILOptimizer: Fix some issues with CSE of open_existential_ref
* A direct user might have a dependent result
* An indirect user can also be a terminator instruction
2023-03-13 21:41:02 +03:00
Erik Eckstein
96049626bc SILOptimizer: add complexity limit in ARCCodeMotion and DeadStoreElimination
Add an emergency exit to avoid bad compile time problems in rare corner cases.
The introduced limit is more than enough for "real world" code. Even large functions have < 100 locations.
But in some corner cases - especially in generated code - we can run into quadratic complexity for large functions without that limit.

Fixes a compile time problem.
Unfortunately I don't have isolated test cases for these problems.

rdar://106516360
2023-03-13 18:46:27 +01:00
Meghana Gupta
df90e2ac46 Don't DCE lexical phis with only destroy users 2023-03-10 00:27:48 -08:00
Erik Eckstein
b741aa0018 SILOptimizer: fix a stack overflow in DCE
For very large control flow graphs the markControllingTerminatorsLive can stack overflow.
Fix this by doing the work iteratively instead of recursively.

rdar://106198943
2023-03-08 12:20:45 +01:00
nate-chandler
ebdeecfe4d Merge pull request #64013 from nate-chandler/mandatory-generic-specializer/partial-apply-stack-discipline
[MandatoryGenericSpecializer] Fix stack nesting when lowering OSSA during inlining.
2023-03-02 06:58:37 -08:00
nate-chandler
7ba396a1cc Merge pull request #64005 from nate-chandler/cse/partial-apply-stack-discipline
[CSE] Stack nest at OSSA lowering after inlining.
2023-03-01 18:09:05 -08:00
Nate Chandler
1dda30e6ba [GenericSpecializer] Nest at inline+lower OSSA.
MandatoryGenericSpecializer inlines transparent functions that it
specializes.

Now that in OSSA `partial_apply [on_stack]`s are represented as owned
values rather than stack locations, it is possible for their destroys to
violate stack discipline.  A direct lowering of the instructions to
non-OSSA would violate stack nesting.

Previously, when inlining during MandatoryGenericSpecializer, it was
assumed that the callee maintained stack discipline.  And, when inlining
an OSSA function into a non-OSSA function, OSSA instructions were
lowered directly.  The result was that stack discipline would be
violated when directly lowering callees with `partial_apply [on_stack]`s
that violate stack discipline.

Here, when MandatoryGenericSpecializer inlines a specialized generic
function in OSSA form into a function lowered out of OSSA form, stack
nesting is fixed up.
2023-03-01 15:30:47 -08:00
Nate Chandler
1a2b781d3e [CSE] Stack nest at OSSA lowering after inlining.
CSE inlines a portion of lazy property getters.

Now that in OSSA `partial_apply [on_stack]`s are represented as owned
values rather than stack locations, it is possible for their destroys to
violate stack discipline.  A direct lowering of the instructions to
non-OSSA would violate stack nesting.

Previously, when inlining during CSE, it was assumed that the callee
maintained stack discipline.  And, when inlining an OSSA function into a
non-OSSA function, OSSA instructions were lowered directly.  The result
was that stack discipline could be violated when directly lowering
callees with `partial_apply [on_stack]`s that violate stack discipline
upon direct lowering.

Here, when CSE inlining a lazy property getter in OSSA form into a
function lowered out of OSSA form, stack nesting is fixed up.
2023-03-01 11:46:06 -08:00
Nate Chandler
a8c5d4e4ce [PerformanceInliner] Stack nest at OSSA lowering.
Now that in OSSA `partial_apply [on_stack]`s are represented as owned
values rather than stack locations, it is possible for their destroys to
violate stack discipline.  A direct lowering of the instructions to
non-OSSA would violate stack nesting.

Previously, when inlining, it was assumed that non-coroutine callees
maintained stack discipline.  And, when inlining an OSSA function into a
non-OSSA function, OSSA instructions were lowered directly.  The result
was that stack discipline could be violated.

Here, when inlining a function in OSSA form into a function lowered out
of OSSA form, stack nesting is fixed up.
2023-02-28 15:40:46 -08:00
Nate Chandler
32685ce68e [Inliner] Add per-inlining verification.
Previously, there was an -Xllvm option to verify after all inlining to a
particlar caller.  That makes it a chore to track down which apply's
inlining resulted in invalid code.  Here, a new option is added that
verifies after each run of the inliner.
2023-02-28 15:40:46 -08:00
Meghana Gupta
a0d1b08dd5 Ensure isEqual and getHashValue() are in sync with an invariant in CSE 2023-02-23 12:07:33 -08:00
swift-ci
4ab5024b3c Merge pull request #63791 from meg-gupta/csebug
Fix CSE `isEqual` and `HashVisitor` for escaped values
2023-02-23 03:54:38 -08:00
Meghana Gupta
619b4cd539 CSE: Don't look through ownership instructions for escaped values
CSE relies on OSSA RAUW for lifetime extension when replacing a redundant instruction.
OSSA RAUW however does not handle lifetime extension for escaped base values.
Values escape from ownership via pointer escape, bitwise escape, forwarding unowned operations
and have none or unowned ownership. For all such values do not look through ownership instructions
while determining equality. It is possible to CSE such values with equivalent operands, because the
operand use guarantees lifetime of the base operand.
2023-02-22 21:11:03 -08:00
Michael Gottesman
1dd896ded9 [move-only] Implement escaping closure semantics.
NOTE: A few of the test patterns need to be made better, but this patch series
is large enough, I want to get it into tree and iterate.
2023-02-20 11:04:21 -08:00
Michael Gottesman
f4e1b2a8f2 [move-only] Update SILGen/MoveCheckers so that vars are emitted in eagerly projected box form.
This is the first slice of bringing up escaping closure support. The support is
based around introducing a new type of SILGen VarLoc: a VarLoc with a box and
without a value. Because the VarLoc only has a box, we have to in SILGen always
eagerly reproject out the address from the box. The reason why I am doing this
is that it makes it easy for the move checker to distinguish in between
different accesses to the box that we want to check separately. As such every
time that we open the box, we insert a mark_must_check
[assignable_but_not_consumable] on that project. If allocbox_to_stack manages to
determine that the box can be stack allocated, we eliminate all of the
mark_must_check and place a new mark_must_check [consumable_and_assignable] on
the alloc_stack.  The end result is that we get the old model that we had before
and also can support escaping closures.
2023-02-20 11:04:21 -08:00
Michael Gottesman
ecb864c159 Merge pull request #63755 from gottesmm/pr-dac78af5673ab6d4a9bebea882b8440c37c9457c
[move-only] A few small changes in preparation for a larger patch
2023-02-18 17:03:50 -08:00
Michael Gottesman
969d776c15 [allocbox-to-stack] When we promote a heap -> stack of noncopyable type, move mark_must_check onto alloc_stack and always
ensure that we use consumable_to_assign.

What this patch is does is add an extra phase after alloc_box runs where we look
at uses of the alloc_stack and if we see any mark_must_check of any kind, we
delete them and rewrite a single mark_must_check [consumable_and_assignable] on
the alloc_stack and make all uses of the alloc_stack go through the
mark_must_check.

This has two effects:

1. In a subsequent PR when I add noncopyable semantics for escaping closures,
this will cause allocbox to stack to convert such boxes from having escaping
semantics to having non-escaping semantics. Escaping semantics means that we
always reproject out from the box and use mark_must_check
[assignable_but_not_consumable] (since we can't consume from the box, but can
assign to it). In contrast, non-escaping semantics means that the box becomes an
alloc_stack and we use the traditional var checker semantics. NOTE: We can do
this for lets represented as addresses and vars since the typechecker will
validate that the let is never actually written to even if at the SIL level we
would allow that.

2. In cases where we are implementing simple mark_must_check
[consumable_and_assignable] on one of the project_box and capture the box, we
used to have a problem where the direct box uses would be on the alloc_stack and
not go through the mark_must_check. Now, all uses after allocbox_to_stack occur
go through the mark_must_check. This is why I was able to remove instances of
the "compiler does not understand this pattern" errors... since the compiler
with this change can now understand them.
2023-02-18 12:38:38 -08:00
eeckstein
b8a4b874c1 Merge pull request #63748 from eeckstein/fix-keypath-inst
SIL: add type-dependent operands to the `keypath` instruction
2023-02-18 07:20:04 +01:00
Joe Groff
02385c895a AllocBoxToStack: Don't try to destroy promoted stack closure captures.
If the partial_apply is already [on_stack], then ClosureLifetimeFixup would
have already turned the captures into borrows and established their final
lifetimes.
2023-02-17 09:28:53 -08:00
Erik Eckstein
2c1d48b69c SIL: add type-dependent operands to the keypath instruction
It's need to correctly maintain dependencies from an open-existential instruction to a `keypath` instruction which uses the opened type.
Fixes a SILVerifier crash.

rdar://105517521
2023-02-17 17:48:55 +01:00
Nate Chandler
3019be9090 [Mem2Reg] Owned lexical lifetimes get moves. 2023-02-16 16:39:54 -08:00
Nate Chandler
66b8b2f827 [Mem2Reg] NFC: Split up lexical lifetime starts.
Split the beginning of lexical lifetimes up according to whether the
lifetimes (and alloc_stacks) are owned or guaranteed.
2023-02-16 16:39:54 -08:00
Nate Chandler
05642793ff [Mem2Reg] NFC: Entype'd LiveValues ownership.
Previously, LiveValues consisted always of three values: the value which
was stored, the borrow, and the copy.  For store_borrows, there never
was a copy.  Treating the two different scenarios as if they were the
same was confusing already.  It was only get when we switch to
representing owned lexical lifetimes with move_values.
2023-02-16 16:39:54 -08:00
Nate Chandler
a70aa13a43 [Gardening] Tweaked comment.
Fixed reference to renamed function argument.
2023-02-15 18:16:33 -08:00
Nate Chandler
1fada55c73 [Gardening] Described states variable could be in. 2023-02-15 18:16:33 -08:00
Nate Chandler
253888fbf8 [NFC] Eliminated spurious variable state.
The type Optional<Ty *> implied that there was a meaningful distinction
between None and Some(nullptr) but that was not the case here.  Replaced
it with a bare Ty *.
2023-02-15 18:16:33 -08:00