Skip to content

Commit c288d95

Browse files
committed
[Autodiff] Separates out changes for using non-ossa instructions in the closure-spec optimization pass
The OSSA elimination pass has not yet been moved below all high level function passes. Until that work has been completed the Autodiff closure-spec optimization pass cannot solely support OSSA instructions.
1 parent 12faf79 commit c288d95

File tree

4 files changed

+56
-10
lines changed

4 files changed

+56
-10
lines changed

SwiftCompilerSources/Sources/Optimizer/FunctionPasses/ClosureSpecialization.swift

Lines changed: 28 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -255,21 +255,23 @@ private func rewriteApplyInstruction(using specializedCallee: Function, callSite
255255
let closureArgDesc = callSite.closureArgDesc(at: parentClosureArgIndex)!
256256
var builder = Builder(before: closureArgDesc.closure, context)
257257

258+
// TODO: Support only OSSA instructions once the OSSA elimination pass is moved after all function optimization
259+
// passes.
258260
if callSite.applySite.parentBlock != closureArgDesc.closure.parentBlock {
259261
// Emit the retain and release that keeps the argument live across the callee using the closure.
260-
builder.createCopyValue(operand: capturedArg)
262+
builder.createRetainValue(operand: capturedArg)
261263

262264
for instr in closureArgDesc.lifetimeFrontier {
263265
builder = Builder(before: instr, context)
264-
builder.createDestroyValue(operand: capturedArg)
266+
builder.createReleaseValue(operand: capturedArg)
265267
}
266268

267269
// Emit the retain that matches the captured argument by the partial_apply in the callee that is consumed by
268270
// the partial_apply.
269271
builder = Builder(before: callSite.applySite, context)
270-
builder.createCopyValue(operand: capturedArg)
272+
builder.createRetainValue(operand: capturedArg)
271273
} else {
272-
builder.createCopyValue(operand: capturedArg)
274+
builder.createRetainValue(operand: capturedArg)
273275
}
274276
}
275277
}
@@ -286,12 +288,14 @@ private func rewriteApplyInstruction(using specializedCallee: Function, callSite
286288
isOnStack: oldApply.isOnStack)
287289

288290
builder = Builder(before: callSite.applySite.next!, context)
291+
// TODO: Support only OSSA instructions once the OSSA elimination pass is moved after all function optimization
292+
// passes.
289293
for closureArgDesc in callSite.closureArgDescriptors {
290294
if closureArgDesc.isClosureConsumed,
291295
!closureArgDesc.isPartialApplyOnStack,
292296
!closureArgDesc.parameterInfo.isTrivialNoescapeClosure
293297
{
294-
builder.createDestroyValue(operand: closureArgDesc.closure)
298+
builder.createReleaseValue(operand: closureArgDesc.closure)
295299
}
296300
}
297301

@@ -825,7 +829,7 @@ private extension SpecializationCloner {
825829
{
826830
builder.destroyPartialApplyOnStack(paiOnStack: pai, self.context)
827831
} else {
828-
builder.createDestroyValue(operand: closure)
832+
builder.createReleaseValue(operand: closure)
829833
}
830834
}
831835
}
@@ -992,11 +996,25 @@ private extension Builder {
992996
func destroyPartialApplyOnStack(paiOnStack: PartialApplyInst, _ context: FunctionPassContext){
993997
precondition(paiOnStack.isOnStack, "Function must only be called for `partial_apply`s on stack!")
994998

995-
for arg in paiOnStack.arguments {
996-
self.createDestroyValue(operand: arg)
997-
}
999+
// TODO: Support only OSSA instructions once the OSSA elimination pass is moved after all function optimization
1000+
// passes.
1001+
//
1002+
// for arg in paiOnStack.arguments {
1003+
// self.createDestroyValue(operand: arg)
1004+
// }
9981005

999-
self.createDestroyValue(operand: paiOnStack)
1006+
// self.createDestroyValue(operand: paiOnStack)
1007+
1008+
if paiOnStack.parentFunction.hasOwnership {
1009+
// Under OSSA, the closure acts as an owned value whose lifetime is a borrow scope for the captures, so we need to
1010+
// end the borrow scope before ending the lifetimes of the captures themselves.
1011+
self.createDestroyValue(operand: paiOnStack)
1012+
self.destroyCapturedArgs(for: paiOnStack)
1013+
} else {
1014+
self.destroyCapturedArgs(for: paiOnStack)
1015+
self.createDeallocStack(paiOnStack)
1016+
context.notifyInvalidatedStackNesting()
1017+
}
10001018
}
10011019
}
10021020

SwiftCompilerSources/Sources/SIL/Builder.swift

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -151,6 +151,18 @@ public struct Builder {
151151
return notifyNew(endInit.getAs(EndInitLetRefInst.self))
152152
}
153153

154+
@discardableResult
155+
public func createRetainValue(operand: Value) -> RetainValueInst {
156+
let retain = bridged.createRetainValue(operand.bridged)
157+
return notifyNew(retain.getAs(RetainValueInst.self))
158+
}
159+
160+
@discardableResult
161+
public func createReleaseValue(operand: Value) -> ReleaseValueInst {
162+
let release = bridged.createReleaseValue(operand.bridged)
163+
return notifyNew(release.getAs(ReleaseValueInst.self))
164+
}
165+
154166
@discardableResult
155167
public func createStrongRetain(operand: Value) -> StrongRetainInst {
156168
let retain = bridged.createStrongRetain(operand.bridged)

include/swift/SIL/SILBridging.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1210,6 +1210,10 @@ struct BridgedBuilder{
12101210
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createBeginDeallocRef(BridgedValue reference,
12111211
BridgedValue allocation) const;
12121212
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createEndInitLetRef(BridgedValue op) const;
1213+
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction
1214+
createRetainValue(BridgedValue op) const;
1215+
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction
1216+
createReleaseValue(BridgedValue op) const;
12131217
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createStrongRetain(BridgedValue op) const;
12141218
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createStrongRelease(BridgedValue op) const;
12151219
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createUnownedRetain(BridgedValue op) const;

include/swift/SIL/SILBridgingImpl.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1590,6 +1590,18 @@ BridgedInstruction BridgedBuilder::createEndInitLetRef(BridgedValue op) const {
15901590
return {unbridged().createEndInitLetRef(regularLoc(), op.getSILValue())};
15911591
}
15921592

1593+
BridgedInstruction BridgedBuilder::createRetainValue(BridgedValue op) const {
1594+
auto b = unbridged();
1595+
return {b.createRetainValue(regularLoc(), op.getSILValue(),
1596+
b.getDefaultAtomicity())};
1597+
}
1598+
1599+
BridgedInstruction BridgedBuilder::createReleaseValue(BridgedValue op) const {
1600+
auto b = unbridged();
1601+
return {b.createReleaseValue(regularLoc(), op.getSILValue(),
1602+
b.getDefaultAtomicity())};
1603+
}
1604+
15931605
BridgedInstruction BridgedBuilder::createStrongRetain(BridgedValue op) const {
15941606
auto b = unbridged();
15951607
return {b.createStrongRetain(regularLoc(), op.getSILValue(), b.getDefaultAtomicity())};

0 commit comments

Comments
 (0)