Skip to content

Commit 30221a4

Browse files
authored
Merge pull request #62758 from eeckstein/fix-cowopt
COWOpts: fix a crash in case a buffer "escapes" to a cond_br condition
2 parents 45aea1e + ef12ec7 commit 30221a4

File tree

2 files changed

+32
-2
lines changed

2 files changed

+32
-2
lines changed

lib/SILOptimizer/Transforms/COWOpts.cpp

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -267,8 +267,10 @@ void COWOptsPass::collectEscapePoints(SILValue v,
267267
escapePoints, handled);
268268
break;
269269
case SILInstructionKind::CondBranchInst:
270-
collectEscapePoints(cast<CondBranchInst>(user)->getArgForOperand(use),
271-
escapePoints, handled);
270+
if (use->getOperandNumber() != CondBranchInst::ConditionIdx) {
271+
collectEscapePoints(cast<CondBranchInst>(user)->getArgForOperand(use),
272+
escapePoints, handled);
273+
}
272274
break;
273275
case SILInstructionKind::StructInst:
274276
case SILInstructionKind::StructExtractInst:

test/SILOptimizer/cow_opts.sil

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,11 @@ struct Str {
1515
@_hasStorage var b: Buffer { get set }
1616
}
1717

18+
struct BufferAndBool {
19+
@_hasStorage var b: Buffer { get set }
20+
@_hasStorage var x: Bool { get set }
21+
}
22+
1823
sil @unknown : $@convention(thin) (@guaranteed Buffer) -> ()
1924

2025
// CHECK-LABEL: sil @test_simple
@@ -109,6 +114,29 @@ bb2:
109114
return %t : $(Builtin.Int1, Buffer)
110115
}
111116

117+
// CHECK-LABEL: sil @test_cond_br_condition
118+
// CHECK: [[I:%[0-9]+]] = integer_literal $Builtin.Int1, -1
119+
// CHECK: ({{.*}}, [[B:%[0-9]+]]) = begin_cow_mutation
120+
// CHECK: [[T:%[0-9]+]] = tuple ([[I]] : $Builtin.Int1, [[B]] : $Buffer)
121+
// CHECK: return [[T]]
122+
// CHECK: } // end sil function 'test_cond_br_condition'
123+
sil @test_cond_br_condition : $@convention(thin) (@owned Buffer, Bool) -> (Builtin.Int1, @owned Buffer) {
124+
bb0(%0 : $Buffer, %1 : $Bool):
125+
%e = end_cow_mutation %0 : $Buffer
126+
%s1 = struct $BufferAndBool (%e: $Buffer, %1 : $Bool)
127+
%x = struct_extract %s1 : $BufferAndBool, #BufferAndBool.x
128+
%c = struct_extract %x : $Bool, #Bool._value
129+
cond_br %c, bb1, bb2
130+
bb1:
131+
br bb3
132+
bb2:
133+
br bb3
134+
bb3:
135+
(%u, %b) = begin_cow_mutation %e : $Buffer
136+
%t = tuple (%u : $Builtin.Int1, %b : $Buffer)
137+
return %t : $(Builtin.Int1, Buffer)
138+
}
139+
112140
// CHECK-LABEL: sil @not_all_incoming_values_are_end_cow_mutation
113141
// CHECK: ([[U:%[0-9]+]], {{.*}}) = begin_cow_mutation
114142
// CHECK: [[B:%[0-9]+]] = end_cow_mutation

0 commit comments

Comments
 (0)