diff --git a/lib/SILGen/SILGenFunction.cpp b/lib/SILGen/SILGenFunction.cpp index 70d937781dd1c..6d6f7524f33af 100644 --- a/lib/SILGen/SILGenFunction.cpp +++ b/lib/SILGen/SILGenFunction.cpp @@ -795,18 +795,14 @@ void SILGenFunction::emitCaptures(SILLocation loc, case CaptureKind::Box: { assert(!isPack); - auto entryValue = getAddressValue(val, /*forceCopy=*/false); - // LValues are captured as both the box owning the value and the - // address of the value. - assert(entryValue->getType().isAddress() && "no address for captured var!"); + assert(val->getType().isAddress() && + "no address for captured var!"); // Boxes of opaque return values stay opaque. auto minimalLoweredType = SGM.Types.getLoweredRValueType( TypeExpansionContext::minimal(), type->getCanonicalType()); // If this is a boxed variable, we can use it directly. if (Entry.box && - entryValue->getType().getASTType() == minimalLoweredType) { - // If our captured value is a box with a moveonlywrapped type inside, - // unwrap it. + val->getType().getASTType() == minimalLoweredType) { auto box = ManagedValue::forBorrowedObjectRValue(Entry.box); // We can guarantee our own box to the callee. if (canGuarantee) { @@ -815,6 +811,8 @@ void SILGenFunction::emitCaptures(SILLocation loc, box = box.copy(*this, loc); } + // If our captured value is a box with a moveonlywrapped type inside, + // unwrap it. if (box.getType().isBoxedMoveOnlyWrappedType(&F)) { CleanupCloner cloner(*this, box); box = cloner.clone( @@ -824,7 +822,7 @@ void SILGenFunction::emitCaptures(SILLocation loc, capturedArgs.push_back(box); if (captureCanEscape) - escapesToMark.push_back(entryValue); + escapesToMark.push_back(val); } else { // Address only 'let' values are passed by box. This isn't great, in // that a variable captured by multiple closures will be boxed for each @@ -838,12 +836,13 @@ void SILGenFunction::emitCaptures(SILLocation loc, // in-place. // TODO: Use immutable box for immutable captures. auto boxTy = SGM.Types.getContextBoxTypeForCapture( - vd, minimalLoweredType, FunctionDC->getGenericEnvironmentOfContext(), + vd, minimalLoweredType, + FunctionDC->getGenericEnvironmentOfContext(), /*mutable*/ true); AllocBoxInst *allocBox = B.createAllocBox(loc, boxTy); ProjectBoxInst *boxAddress = B.createProjectBox(loc, allocBox, 0); - B.createCopyAddr(loc, entryValue, boxAddress, IsNotTake, + B.createCopyAddr(loc, val, boxAddress, IsNotTake, IsInitialization); if (canGuarantee) capturedArgs.push_back( @@ -857,17 +856,14 @@ void SILGenFunction::emitCaptures(SILLocation loc, case CaptureKind::ImmutableBox: { assert(!isPack); - auto entryValue = getAddressValue(val, /*forceCopy=*/false); - // LValues are captured as both the box owning the value and the - // address of the value. - assert(entryValue->getType().isAddress() && + assert(val->getType().isAddress() && "no address for captured var!"); // Boxes of opaque return values stay opaque. auto minimalLoweredType = SGM.Types.getLoweredRValueType( TypeExpansionContext::minimal(), type->getCanonicalType()); // If this is a boxed variable, we can use it directly. if (Entry.box && - entryValue->getType().getASTType() == minimalLoweredType) { + val->getType().getASTType() == minimalLoweredType) { // We can guarantee our own box to the callee. if (canGuarantee) { capturedArgs.push_back( @@ -876,7 +872,7 @@ void SILGenFunction::emitCaptures(SILLocation loc, capturedArgs.push_back(emitManagedRetain(loc, Entry.box)); } if (captureCanEscape) - escapesToMark.push_back(entryValue); + escapesToMark.push_back(val); } else { // Address only 'let' values are passed by box. This isn't great, in // that a variable captured by multiple closures will be boxed for each @@ -896,7 +892,7 @@ void SILGenFunction::emitCaptures(SILLocation loc, AllocBoxInst *allocBox = B.createAllocBox(loc, boxTy); ProjectBoxInst *boxAddress = B.createProjectBox(loc, allocBox, 0); - B.createCopyAddr(loc, entryValue, boxAddress, IsNotTake, + B.createCopyAddr(loc, val, boxAddress, IsNotTake, IsInitialization); if (canGuarantee) capturedArgs.push_back(