Skip to content

Commit 7c25466

Browse files
committed
Avoid unnecessary insertion of mark_unresolved_noncopyable_value
SILGen inserts mark_unresolved_noncopyable_value at the introducer in some cases and at uses in other cases. This inconsistency can causes insertion of a redundant mark* instruction which crashes the move-only checker. This change avoids inserting a redundant mark* instruction.
1 parent 9fed041 commit 7c25466

File tree

2 files changed

+33
-4
lines changed

2 files changed

+33
-4
lines changed

lib/SILGen/SILGenFunction.cpp

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -807,10 +807,16 @@ void SILGenFunction::emitCaptures(SILLocation loc,
807807
// If we have a mutable binding for a 'let', such as 'self' in an
808808
// 'init' method, load it.
809809
if (val->getType().isMoveOnly()) {
810-
val = B.createMarkUnresolvedNonCopyableValueInst(
811-
loc, val,
812-
MarkUnresolvedNonCopyableValueInst::CheckKind::
813-
NoConsumeOrAssign);
810+
auto *moveOnlyIntroducer =
811+
dyn_cast_or_null<MarkUnresolvedNonCopyableValueInst>(val);
812+
if (!moveOnlyIntroducer || moveOnlyIntroducer->getCheckKind() !=
813+
MarkUnresolvedNonCopyableValueInst::
814+
CheckKind::NoConsumeOrAssign) {
815+
val = B.createMarkUnresolvedNonCopyableValueInst(
816+
loc, val,
817+
MarkUnresolvedNonCopyableValueInst::CheckKind::
818+
NoConsumeOrAssign);
819+
}
814820
}
815821
val = emitLoad(loc, val, tl, SGFContext(), IsNotTake).forward(*this);
816822
}

test/SILGen/addressable_read.swift

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// RUN: %target-swift-frontend -emit-sil -verify -enable-experimental-feature AddressableParameters %s
2+
3+
// REQUIRES: swift_feature_AddressableParameters
4+
5+
public struct Container<Element: ~Copyable >: ~Copyable {
6+
var _storage: UnsafeMutableBufferPointer<Element>
7+
var _count: Int
8+
9+
public subscript(index: Int) -> Element {
10+
@_addressableSelf
11+
_read {
12+
precondition(index >= 0 && index < _count, "Index out of bounds")
13+
yield _storage.baseAddress.unsafelyUnwrapped.advanced(by: index).pointee
14+
}
15+
_modify {
16+
precondition(index >= 0 && index < _count, "Index out of bounds")
17+
yield &_storage.baseAddress.unsafelyUnwrapped.advanced(by: index).pointee
18+
}
19+
}
20+
}
21+
22+
extension Container: Copyable where Element: Copyable {}
23+

0 commit comments

Comments
 (0)