Skip to content

Commit 5a772d7

Browse files
authored
Merge pull request swiftlang#5661 from gottesmm/forward-copy-value
[semantic-arc] In SILGen always assign a copy_value's argument to its result.
2 parents 2c54a7b + 2ccc251 commit 5a772d7

File tree

84 files changed

+2612
-1664
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

84 files changed

+2612
-1664
lines changed

lib/SIL/TypeLowering.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -718,7 +718,7 @@ namespace {
718718
void emitDestroyValue(SILBuilder &B, SILLocation loc,
719719
SILValue aggValue) const override {
720720
if (B.getFunction().hasQualifiedOwnership()) {
721-
B.emitDestroyValueAndFold(loc, aggValue);
721+
B.createDestroyValue(loc, aggValue);
722722
return;
723723
}
724724

@@ -838,7 +838,7 @@ namespace {
838838
void emitDestroyValue(SILBuilder &B, SILLocation loc,
839839
SILValue value) const override {
840840
if (B.getFunction().hasQualifiedOwnership()) {
841-
B.emitDestroyValueAndFold(loc, value);
841+
B.createDestroyValue(loc, value);
842842
return;
843843
}
844844
B.emitReleaseValueAndFold(loc, value);
@@ -850,7 +850,7 @@ namespace {
850850
"This method should never be called when performing a shallow "
851851
"destroy value.");
852852
if (B.getFunction().hasQualifiedOwnership()) {
853-
B.emitDestroyValueAndFold(loc, value);
853+
B.createDestroyValue(loc, value);
854854
return;
855855
}
856856
B.emitReleaseValueAndFold(loc, value);
@@ -896,7 +896,7 @@ namespace {
896896
void emitDestroyValue(SILBuilder &B, SILLocation loc,
897897
SILValue value) const override {
898898
if (B.getFunction().hasQualifiedOwnership()) {
899-
B.emitDestroyValueAndFold(loc, value);
899+
B.createDestroyValue(loc, value);
900900
return;
901901
}
902902
B.emitStrongReleaseAndFold(loc, value);

lib/SILGen/ManagedValue.cpp

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,7 @@ ManagedValue ManagedValue::copy(SILGenFunction &gen, SILLocation l) {
3333
assert(!lowering.isTrivial() && "trivial value has cleanup?");
3434

3535
if (!lowering.isAddressOnly()) {
36-
lowering.emitCopyValue(gen.B, l, getValue());
37-
return gen.emitManagedRValueWithCleanup(getValue(), lowering);
36+
return gen.emitManagedRetain(l, getValue(), lowering);
3837
}
3938

4039
SILValue buf = gen.emitTemporaryAllocation(l, getType());
@@ -66,8 +65,7 @@ ManagedValue ManagedValue::copyUnmanaged(SILGenFunction &gen, SILLocation loc) {
6665

6766
SILValue result;
6867
if (!lowering.isAddressOnly()) {
69-
lowering.emitCopyValue(gen.B, loc, getValue());
70-
result = getValue();
68+
result = lowering.emitCopyValue(gen.B, loc, getValue());
7169
} else {
7270
result = gen.emitTemporaryAllocation(loc, getType());
7371
gen.B.createCopyAddr(loc, getValue(), result, IsNotTake,IsInitialization);

lib/SILGen/SILGenApply.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2344,7 +2344,7 @@ RValue SILGenFunction::emitApply(
23442344
case ParameterConvention::Direct_Owned:
23452345
// If the callee will consume the 'self' parameter, let's retain it so we
23462346
// can keep it alive.
2347-
B.emitCopyValueOperation(loc, lifetimeExtendedSelf);
2347+
lifetimeExtendedSelf = B.emitCopyValueOperation(loc, lifetimeExtendedSelf);
23482348
break;
23492349
case ParameterConvention::Direct_Guaranteed:
23502350
case ParameterConvention::Direct_Unowned:
@@ -2425,7 +2425,7 @@ RValue SILGenFunction::emitApply(
24252425

24262426
case ResultConvention::Unowned:
24272427
// Unretained. Retain the value.
2428-
resultTL.emitCopyValue(B, loc, result);
2428+
result = resultTL.emitCopyValue(B, loc, result);
24292429
break;
24302430
}
24312431

@@ -5448,7 +5448,7 @@ static SILValue emitDynamicPartialApply(SILGenFunction &gen,
54485448
// Retain 'self' because the partial apply will take ownership.
54495449
// We can't simply forward 'self' because the partial apply is conditional.
54505450
if (!self->getType().isAddress())
5451-
gen.B.emitCopyValueOperation(loc, self);
5451+
self = gen.B.emitCopyValueOperation(loc, self);
54525452

54535453
SILValue result = gen.B.createPartialApply(loc, method, method->getType(), {},
54545454
self, partialApplyTy);

lib/SILGen/SILGenBridging.cpp

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -883,8 +883,7 @@ static SILValue emitObjCUnconsumedArgument(SILGenFunction &gen,
883883
return tmp;
884884
}
885885

886-
lowering.emitCopyValue(gen.B, loc, arg);
887-
return arg;
886+
return lowering.emitCopyValue(gen.B, loc, arg);
888887
}
889888

890889
/// Bridge argument types and adjust retain count conventions for an ObjC thunk.

lib/SILGen/SILGenBuiltin.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -236,7 +236,7 @@ static ManagedValue emitBuiltinDestroy(SILGenFunction &gen,
236236

237237
// Destroy the value indirectly. Canonicalization will promote to loads
238238
// and releases if appropriate.
239-
gen.B.emitDestroyAddrAndFold(loc, addr);
239+
gen.B.createDestroyAddr(loc, addr);
240240

241241
return ManagedValue::forUnmanaged(gen.emitEmptyTuple(loc));
242242
}

lib/SILGen/SILGenConstructor.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -279,7 +279,7 @@ void SILGenFunction::emitValueConstructor(ConstructorDecl *ctor) {
279279
B.createLoad(cleanupLoc, selfLV, LoadOwnershipQualifier::Unqualified);
280280

281281
// Emit a retain of the loaded value, since we return it +1.
282-
lowering.emitCopyValue(B, cleanupLoc, selfValue);
282+
selfValue = lowering.emitCopyValue(B, cleanupLoc, selfValue);
283283

284284
// Inject the self value into an optional if the constructor is failable.
285285
if (ctor->getFailability() != OTK_None) {
@@ -675,7 +675,7 @@ void SILGenFunction::emitClassConstructorInitializer(ConstructorDecl *ctor) {
675675
}
676676

677677
// We have to do a retain because we are returning the pointer +1.
678-
B.emitCopyValueOperation(cleanupLoc, selfArg);
678+
selfArg = B.emitCopyValueOperation(cleanupLoc, selfArg);
679679

680680
// Inject the self value into an optional if the constructor is failable.
681681
if (ctor->getFailability() != OTK_None) {

lib/SILGen/SILGenConvert.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -719,7 +719,7 @@ ManagedValue SILGenFunction::emitProtocolMetatypeToObject(SILLocation loc,
719719
// reference when we use it to prevent it being released and attempting to
720720
// deallocate itself. It doesn't matter if we ever actually clean up that
721721
// retain though.
722-
B.createCopyValue(loc, value);
722+
value = B.createCopyValue(loc, value);
723723
return ManagedValue::forUnmanaged(value);
724724
}
725725

lib/SILGen/SILGenDecl.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@ namespace {
116116
public:
117117
CleanupClosureConstant(SILValue closure) : closure(closure) {}
118118
void emit(SILGenFunction &gen, CleanupLocation l) override {
119-
gen.B.emitDestroyValueAndFold(l, closure);
119+
gen.B.emitDestroyValueOperation(l, closure);
120120
}
121121
};
122122
}
@@ -208,7 +208,7 @@ class ReleaseValueCleanup : public Cleanup {
208208

209209
void emit(SILGenFunction &gen, CleanupLocation l) override {
210210
if (v->getType().isAddress())
211-
gen.B.emitDestroyAddrAndFold(l, v);
211+
gen.B.createDestroyAddr(l, v);
212212
else
213213
gen.B.emitDestroyValueOperation(l, v);
214214
}
@@ -1304,7 +1304,7 @@ void SILGenFunction::destroyLocalVariable(SILLocation silLoc, VarDecl *vd) {
13041304
// For a heap variable, the box is responsible for the value. We just need
13051305
// to give up our retain count on it.
13061306
if (loc.box) {
1307-
B.emitDestroyValueAndFold(silLoc, loc.box);
1307+
B.emitDestroyValueOperation(silLoc, loc.box);
13081308
return;
13091309
}
13101310

@@ -1314,7 +1314,7 @@ void SILGenFunction::destroyLocalVariable(SILLocation silLoc, VarDecl *vd) {
13141314
if (!Val->getType().isAddress())
13151315
B.emitDestroyValueOperation(silLoc, Val);
13161316
else
1317-
B.emitDestroyAddrAndFold(silLoc, Val);
1317+
B.createDestroyAddr(silLoc, Val);
13181318
}
13191319

13201320
void SILGenFunction::deallocateUninitializedLocalVariable(SILLocation silLoc,

lib/SILGen/SILGenDestructor.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,7 @@ void SILGenFunction::emitClassMemberDestruction(SILValue selfValue,
134134
if (!ti.isTrivial()) {
135135
SILValue addr = B.createRefElementAddr(cleanupLoc, selfValue, vd,
136136
ti.getLoweredType().getAddressType());
137-
B.emitDestroyAddrAndFold(cleanupLoc, addr);
137+
B.createDestroyAddr(cleanupLoc, addr);
138138
}
139139
}
140140
}

lib/SILGen/SILGenDynamicCast.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -234,7 +234,7 @@ namespace {
234234
SGFContext ctx) {
235235
// Retain the result if this is copy-on-success.
236236
if (!shouldTakeOnSuccess(consumption))
237-
origTargetTL.emitCopyValue(SGF.B, Loc, value);
237+
value = origTargetTL.emitCopyValue(SGF.B, Loc, value);
238238

239239
// Enter a cleanup for the +1 result.
240240
ManagedValue result

lib/SILGen/SILGenExpr.cpp

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ ManagedValue SILGenFunction::emitManagedRetain(SILLocation loc,
5959
return ManagedValue::forUnmanaged(v);
6060
assert(!lowering.isAddressOnly() && "cannot retain an unloadable type");
6161

62-
lowering.emitCopyValue(B, loc, v);
62+
v = lowering.emitCopyValue(B, loc, v);
6363
return emitManagedRValueWithCleanup(v, lowering);
6464
}
6565

@@ -546,7 +546,7 @@ emitRValueWithAccessor(SILGenFunction &SGF, SILLocation loc,
546546
case AddressorKind::Owning:
547547
case AddressorKind::NativeOwning:
548548
// Emit the release immediately.
549-
SGF.B.emitDestroyValueAndFold(loc, addressorResult.second.forward(SGF));
549+
SGF.B.emitDestroyValueOperation(loc, addressorResult.second.forward(SGF));
550550
break;
551551
case AddressorKind::NativePinning:
552552
// Emit the unpin immediately.
@@ -3234,8 +3234,7 @@ class AutoreleasingWritebackComponent : public LogicalPathComponent {
32343234
auto strongType = SILType::getPrimitiveObjectType(
32353235
unowned->getType().castTo<UnmanagedStorageType>().getReferentType());
32363236
auto owned = gen.B.createUnmanagedToRef(loc, unowned, strongType);
3237-
gen.B.createCopyValue(loc, owned);
3238-
auto ownedMV = gen.emitManagedRValueWithCleanup(owned);
3237+
auto ownedMV = gen.emitManagedRetain(loc, owned);
32393238

32403239
// Reassign the +1 storage with it.
32413240
ownedMV.assignInto(gen, loc, base.getUnmanagedValue());

lib/SILGen/SILGenFunction.cpp

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -279,7 +279,7 @@ void SILGenFunction::emitCaptures(SILLocation loc,
279279
}
280280

281281
// Just retain a by-val let.
282-
B.emitCopyValueOperation(loc, Val);
282+
Val = B.emitCopyValueOperation(loc, Val);
283283
} else {
284284
// If we have a mutable binding for a 'let', such as 'self' in an
285285
// 'init' method, load it.
@@ -321,8 +321,7 @@ void SILGenFunction::emitCaptures(SILLocation loc,
321321
if (canGuarantee) {
322322
capturedArgs.push_back(ManagedValue::forUnmanaged(vl.box));
323323
} else {
324-
B.createCopyValue(loc, vl.box);
325-
capturedArgs.push_back(emitManagedRValueWithCleanup(vl.box));
324+
capturedArgs.push_back(emitManagedRetain(loc, vl.box));
326325
}
327326
escapesToMark.push_back(vl.value);
328327
} else {

lib/SILGen/SILGenLValue.cpp

Lines changed: 9 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1171,7 +1171,7 @@ namespace {
11711171
// we've still got a release active.
11721172
SILValue baseValue = (isFinal ? base.forward(gen) : base.getValue());
11731173
if (!isFinal)
1174-
gen.B.createCopyValue(loc, baseValue);
1174+
baseValue = gen.B.createCopyValue(loc, baseValue);
11751175

11761176
gen.B.createStrongUnpin(loc, baseValue, Atomicity::Atomic);
11771177
}
@@ -2162,8 +2162,7 @@ SILValue SILGenFunction::emitConversionToSemanticRValue(SILLocation loc,
21622162
auto result = B.createUnmanagedToRef(loc, src,
21632163
SILType::getPrimitiveObjectType(unmanagedType.getReferentType()));
21642164
// SEMANTIC ARC TODO: Does this need a cleanup?
2165-
B.createCopyValue(loc, result);
2166-
return result;
2165+
return B.createCopyValue(loc, result);
21672166
}
21682167

21692168
llvm_unreachable("unexpected storage type that differs from type-of-rvalue");
@@ -2207,8 +2206,7 @@ static SILValue emitLoadOfSemanticRValue(SILGenFunction &gen,
22072206
auto result = gen.B.createUnmanagedToRef(loc, value,
22082207
SILType::getPrimitiveObjectType(unmanagedType.getReferentType()));
22092208
// SEMANTIC ARC TODO: Does this need a cleanup?
2210-
gen.B.createCopyValue(loc, result);
2211-
return result;
2209+
return gen.B.createCopyValue(loc, result);
22122210
}
22132211

22142212
// NSString * must be bridged to String.
@@ -2242,7 +2240,7 @@ static void emitStoreOfSemanticRValue(SILGenFunction &gen,
22422240
gen.B.createStoreWeak(loc, value, dest, isInit);
22432241

22442242
// store_weak doesn't take ownership of the input, so cancel it out.
2245-
gen.B.emitDestroyValueAndFold(loc, value);
2243+
gen.B.emitDestroyValueOperation(loc, value);
22462244
return;
22472245
}
22482246

@@ -2254,15 +2252,15 @@ static void emitStoreOfSemanticRValue(SILGenFunction &gen,
22542252
gen.B.createStoreUnowned(loc, value, dest, isInit);
22552253

22562254
// store_unowned doesn't take ownership of the input, so cancel it out.
2257-
gen.B.emitDestroyValueAndFold(loc, value);
2255+
gen.B.emitDestroyValueOperation(loc, value);
22582256
return;
22592257
}
22602258

22612259
auto unownedValue =
22622260
gen.B.createRefToUnowned(loc, value, storageType.getObjectType());
22632261
gen.B.createUnownedRetain(loc, unownedValue, Atomicity::Atomic);
22642262
emitUnloweredStoreOfCopy(gen.B, loc, unownedValue, dest, isInit);
2265-
gen.B.emitDestroyValueAndFold(loc, value);
2263+
gen.B.emitDestroyValueOperation(loc, value);
22662264
return;
22672265
}
22682266

@@ -2272,7 +2270,7 @@ static void emitStoreOfSemanticRValue(SILGenFunction &gen,
22722270
auto unmanagedValue =
22732271
gen.B.createRefToUnmanaged(loc, value, storageType.getObjectType());
22742272
emitUnloweredStoreOfCopy(gen.B, loc, unmanagedValue, dest, isInit);
2275-
gen.B.emitDestroyValueAndFold(loc, value);
2273+
gen.B.emitDestroyValueOperation(loc, value);
22762274
return;
22772275
}
22782276

@@ -2362,15 +2360,15 @@ SILValue SILGenFunction::emitConversionFromSemanticValue(SILLocation loc,
23622360

23632361
SILValue unowned = B.createRefToUnowned(loc, semanticValue, storageType);
23642362
B.createUnownedRetain(loc, unowned, Atomicity::Atomic);
2365-
B.emitDestroyValueAndFold(loc, semanticValue);
2363+
B.emitDestroyValueOperation(loc, semanticValue);
23662364
return unowned;
23672365
}
23682366

23692367
// For @unmanaged types, place into an unmanaged box.
23702368
if (storageType.is<UnmanagedStorageType>()) {
23712369
SILValue unmanaged =
23722370
B.createRefToUnmanaged(loc, semanticValue, storageType);
2373-
B.emitDestroyValueAndFold(loc, semanticValue);
2371+
B.emitDestroyValueOperation(loc, semanticValue);
23742372
return unmanaged;
23752373
}
23762374

lib/SILGen/SILGenPoly.cpp

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -738,7 +738,7 @@ static ManagedValue manageParam(SILGenFunction &gen,
738738
// Unowned parameters are only guaranteed at the instant of the call, so we
739739
// must retain them even if we're in a context that can accept a +0 value.
740740
case ParameterConvention::Direct_Unowned:
741-
gen.getTypeLowering(paramValue->getType())
741+
paramValue = gen.getTypeLowering(paramValue->getType())
742742
.emitCopyValue(gen.B, loc, paramValue);
743743
SWIFT_FALLTHROUGH;
744744
case ParameterConvention::Direct_Owned:
@@ -2121,8 +2121,7 @@ void ResultPlanner::execute(ArrayRef<SILValue> innerDirectResults,
21212121
"reabstraction of returns_inner_pointer function");
21222122
SWIFT_FALLTHROUGH;
21232123
case ResultConvention::Unowned:
2124-
resultTL.emitCopyValue(Gen.B, Loc, resultValue);
2125-
return Gen.emitManagedRValueWithCleanup(resultValue, resultTL);
2124+
return Gen.emitManagedRetain(Loc, resultValue, resultTL);
21262125
}
21272126
llvm_unreachable("bad result convention!");
21282127
};

lib/SILGen/SILGenProlog.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ class StrongReleaseCleanup : public Cleanup {
6161
public:
6262
StrongReleaseCleanup(SILValue box) : box(box) {}
6363
void emit(SILGenFunction &gen, CleanupLocation l) override {
64-
gen.B.emitDestroyValueAndFold(l, box);
64+
gen.B.emitDestroyValueOperation(l, box);
6565
}
6666
};
6767
} // end anonymous namespace

test/ClangImporter/optional.swift

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,11 @@ class A {
1212
return ""
1313
}
1414
// CHECK-LABEL: sil hidden [thunk] @_TToFC8optional1A3foofT_GSqSS_ : $@convention(objc_method) (A) -> @autoreleased Optional<NSString>
15+
// CHECK: bb0([[SELF:%.*]] : $A):
16+
// CHECK: [[SELF_COPY:%.*]] = copy_value [[SELF]]
1517
// CHECK: [[T0:%.*]] = function_ref @_TFC8optional1A3foofT_GSqSS_
16-
// CHECK-NEXT: [[T1:%.*]] = apply [[T0]](%0)
17-
// CHECK-NEXT: destroy_value
18+
// CHECK-NEXT: [[T1:%.*]] = apply [[T0]]([[SELF_COPY]])
19+
// CHECK-NEXT: destroy_value [[SELF_COPY]]
1820
// CHECK: [[T2:%.*]] = select_enum [[T1]]
1921
// CHECK-NEXT: cond_br [[T2]]
2022
// Something branch: project value, translate, inject into result.
@@ -33,10 +35,13 @@ class A {
3335

3436
@objc func bar(x x : String?) {}
3537
// CHECK-LABEL: sil hidden [thunk] @_TToFC8optional1A3barfT1xGSqSS__T_ : $@convention(objc_method) (Optional<NSString>, A) -> ()
36-
// CHECK: [[T1:%.*]] = select_enum %0
38+
// CHECK: bb0([[ARG:%.*]] : $Optional<NSString>, [[SELF:%.*]] : $A):
39+
// CHECK: [[ARG_COPY:%.*]] = copy_value [[ARG]]
40+
// CHECK: [[SELF_COPY:%.*]] = copy_value [[SELF]]
41+
// CHECK: [[T1:%.*]] = select_enum [[ARG_COPY]]
3742
// CHECK-NEXT: cond_br [[T1]]
3843
// Something branch: project value, translate, inject into result.
39-
// CHECK: [[NSSTR:%.*]] = unchecked_enum_data %0
44+
// CHECK: [[NSSTR:%.*]] = unchecked_enum_data [[ARG_COPY]]
4045
// CHECK: [[T0:%.*]] = function_ref @_TZFE10FoundationSS36_unconditionallyBridgeFromObjectiveCfGSqCSo8NSString_SS
4146
// Make a temporary initialized string that we're going to clobber as part of the conversion process (?).
4247
// CHECK-NEXT: [[NSSTR_BOX:%.*]] = enum $Optional<NSString>, #Optional.some!enumelt.1, [[NSSTR]] : $NSString
@@ -50,8 +55,8 @@ class A {
5055
// Continuation.
5156
// CHECK: bb3([[T0:%.*]] : $Optional<String>):
5257
// CHECK: [[T1:%.*]] = function_ref @_TFC8optional1A3barfT1xGSqSS__T_
53-
// CHECK-NEXT: [[T2:%.*]] = apply [[T1]]([[T0]], %1)
54-
// CHECK-NEXT: destroy_value %1
58+
// CHECK-NEXT: [[T2:%.*]] = apply [[T1]]([[T0]], [[SELF_COPY]])
59+
// CHECK-NEXT: destroy_value [[SELF_COPY]]
5560
// CHECK-NEXT: return [[T2]] : $()
5661
}
5762

0 commit comments

Comments
 (0)