Skip to content

Commit e9a67c7

Browse files
committed
Propagates assume
1 parent 0051e31 commit e9a67c7

3 files changed

Lines changed: 82 additions & 0 deletions

File tree

compiler/rustc_mir_transform/src/ssa_range_prop.rs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,22 @@ impl<'tcx> MutVisitor<'tcx> for RangeSet<'tcx, '_, '_> {
140140
};
141141
}
142142

143+
fn visit_statement(&mut self, statement: &mut Statement<'tcx>, location: Location) {
144+
self.super_statement(statement, location);
145+
match &statement.kind {
146+
StatementKind::Intrinsic(box NonDivergingIntrinsic::Assume(operand)) => {
147+
if let Some(place) = operand.place()
148+
&& self.is_ssa(place)
149+
{
150+
let successor = location.successor_within_block();
151+
let range = WrappingRange { start: 1, end: 1 };
152+
self.insert_range(place, successor, range);
153+
}
154+
}
155+
_ => {}
156+
}
157+
}
158+
143159
fn visit_terminator(&mut self, terminator: &mut Terminator<'tcx>, location: Location) {
144160
self.super_terminator(terminator, location);
145161
match &terminator.kind {
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
- // MIR for `on_assume` before SsaRangePropagation
2+
+ // MIR for `on_assume` after SsaRangePropagation
3+
4+
fn on_assume(_1: usize, _2: &[u8]) -> u8 {
5+
debug i => _1;
6+
debug v => _2;
7+
let mut _0: u8;
8+
let _3: ();
9+
let _4: ();
10+
let mut _5: bool;
11+
let mut _6: usize;
12+
let mut _7: usize;
13+
let mut _8: &[u8];
14+
let _9: usize;
15+
let mut _10: usize;
16+
let mut _11: bool;
17+
scope 1 (inlined core::slice::<impl [u8]>::len) {
18+
scope 2 (inlined std::ptr::metadata::<[u8]>) {
19+
}
20+
}
21+
22+
bb0: {
23+
StorageLive(_3);
24+
StorageLive(_4);
25+
nop;
26+
StorageLive(_6);
27+
_6 = copy _1;
28+
nop;
29+
StorageLive(_8);
30+
_8 = &(*_2);
31+
_7 = PtrMetadata(copy _2);
32+
StorageDead(_8);
33+
_5 = Lt(copy _1, copy _7);
34+
nop;
35+
StorageDead(_6);
36+
assume(copy _5);
37+
nop;
38+
StorageDead(_4);
39+
_3 = const ();
40+
StorageDead(_3);
41+
StorageLive(_9);
42+
_9 = copy _1;
43+
_10 = copy _7;
44+
- _11 = copy _5;
45+
- assert(copy _5, "index out of bounds: the length is {} but the index is {}", copy _7, copy _1) -> [success: bb1, unwind unreachable];
46+
+ _11 = const true;
47+
+ assert(const true, "index out of bounds: the length is {} but the index is {}", copy _7, copy _1) -> [success: bb1, unwind unreachable];
48+
}
49+
50+
bb1: {
51+
_0 = copy (*_2)[_1];
52+
StorageDead(_9);
53+
return;
54+
}
55+
}
56+

tests/mir-opt/range/ssa_range.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,16 @@ pub fn on_assert(i: usize, v: &[u8]) -> u8 {
2020
v[i]
2121
}
2222

23+
// EMIT_MIR ssa_range.on_assume.SsaRangePropagation.diff
24+
pub fn on_assume(i: usize, v: &[u8]) -> u8 {
25+
// CHECK-LABEL: fn on_assume(
26+
// CHECK: assert(const true
27+
unsafe {
28+
std::intrinsics::assume(i < v.len());
29+
}
30+
v[i]
31+
}
32+
2333
// EMIT_MIR ssa_range.on_match.SsaRangePropagation.diff
2434
pub fn on_match(i: u8) -> u8 {
2535
// CHECK-LABEL: fn on_match(

0 commit comments

Comments
 (0)