Skip to content

Commit 653a5aa

Browse files
committed
Prevent begin_borrow on addresses and cleanup address access utils.
1 parent ef149d5 commit 653a5aa

File tree

3 files changed

+32
-21
lines changed

3 files changed

+32
-21
lines changed

include/swift/SIL/MemAccessUtils.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,14 @@ namespace swift {
5353
/// (pointer-to-address is not stripped).
5454
SILValue stripAccessMarkers(SILValue v);
5555

56+
/// Return a non-null address-type SingleValueInstruction if \p v is the result
57+
/// of an address projection that may be inside of a formal access, such as
58+
/// (begin_borrow, struct_element_addr, tuple_element_addr).
59+
///
60+
/// The resulting projection must have an address-type operand at index zero
61+
/// representing the projected address.
62+
SingleValueInstruction *isAccessProjection(SILValue v);
63+
5664
/// Attempt to return the address corresponding to a variable's formal access
5765
/// by stripping indexing and address projections.
5866
///

include/swift/SIL/SILBuilder.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -728,6 +728,7 @@ class SILBuilder {
728728
}
729729

730730
BeginBorrowInst *createBeginBorrow(SILLocation Loc, SILValue LV) {
731+
assert(!LV->getType().isAddress());
731732
return insert(new (getModule())
732733
BeginBorrowInst(getSILDebugLocation(Loc), LV));
733734
}

lib/SIL/MemAccessUtils.cpp

Lines changed: 23 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -22,37 +22,39 @@
2222
using namespace swift;
2323

2424
SILValue swift::stripAccessMarkers(SILValue v) {
25-
while (true) {
26-
switch (v->getKind()) {
27-
default:
28-
return v;
29-
30-
case ValueKind::BeginBorrowInst:
31-
case ValueKind::BeginAccessInst:
32-
v = cast<SingleValueInstruction>(v)->getOperand(0);
33-
}
25+
while (auto *bai = dyn_cast<BeginAccessInst>(v)) {
26+
v = bai->getOperand();
3427
}
28+
return v;
29+
}
30+
31+
// The resulting projection must have an address-type operand at index zero
32+
// representing the projected address.
33+
SingleValueInstruction *swift::isAccessProjection(SILValue v) {
34+
switch (v->getKind()) {
35+
default:
36+
return nullptr;
37+
38+
case ValueKind::StructElementAddrInst:
39+
case ValueKind::TupleElementAddrInst:
40+
case ValueKind::UncheckedTakeEnumDataAddrInst:
41+
case ValueKind::TailAddrInst:
42+
case ValueKind::IndexAddrInst:
43+
return cast<SingleValueInstruction>(v);
44+
};
3545
}
3646

3747
// TODO: When the optimizer stops stripping begin_access markers, then we should
3848
// be able to assert that the result is a BeginAccessInst and the default case
3949
// is unreachable.
4050
SILValue swift::getAccessedAddress(SILValue v) {
41-
assert(v->getType().isAddress());
4251
while (true) {
43-
switch (v->getKind()) {
44-
default:
52+
assert(v->getType().isAddress());
53+
auto *projection = isAccessProjection(v);
54+
if (!projection)
4555
return v;
4656

47-
case ValueKind::BeginBorrowInst:
48-
case ValueKind::StructElementAddrInst:
49-
case ValueKind::TupleElementAddrInst:
50-
case ValueKind::UncheckedTakeEnumDataAddrInst:
51-
case ValueKind::TailAddrInst:
52-
case ValueKind::IndexAddrInst:
53-
v = cast<SingleValueInstruction>(v)->getOperand(0);
54-
continue;
55-
};
57+
v = projection->getOperand(0);
5658
}
5759
}
5860

0 commit comments

Comments
 (0)