Skip to content

Commit

Permalink
Auto merge of rust-lang#96549 - ouz-a:mir-opt, r=oli-obk
Browse files Browse the repository at this point in the history
Move Derefer before Retag

_Follow up work to rust-lang#96116 rust-lang#95857 #95649_

This moves `Derefer` before `Retag` and creates a new `LocalInfo` called `Temp` to avoid retagging created temp values.

Zulip discussion [link](https://rust-lang.zulipchat.com/#narrow/stream/189540-t-compiler.2Fwg-mir-opt/topic/deref.20as.20first.20and.20only.20projection)

r? `@oli-obk`
  • Loading branch information
bors committed May 1, 2022
2 parents 508e058 + d9ddb64 commit 6eda764
Show file tree
Hide file tree
Showing 35 changed files with 69 additions and 148 deletions.
2 changes: 2 additions & 0 deletions compiler/rustc_middle/src/mir/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1087,6 +1087,8 @@ pub enum LocalInfo<'tcx> {
/// A temporary created during the creation of an aggregate
/// (e.g. a temporary for `foo` in `MyStruct { my_field: foo }`)
AggregateTemp,
/// A temporary created during the pass `Derefer` to avoid it's retagging
DerefTemp,
}

impl<'tcx> LocalDecl<'tcx> {
Expand Down
15 changes: 13 additions & 2 deletions compiler/rustc_middle/src/mir/patch.rs
Original file line number Diff line number Diff line change
Expand Up @@ -78,13 +78,24 @@ impl<'tcx> MirPatch<'tcx> {
Location { block: bb, statement_index: offset }
}

pub fn new_temp(&mut self, ty: Ty<'tcx>, span: Span) -> Local {
pub fn new_local_with_info(
&mut self,
ty: Ty<'tcx>,
span: Span,
local_info: Option<Box<LocalInfo<'tcx>>>,
) -> Local {
let index = self.next_local;
self.next_local += 1;
self.new_locals.push(LocalDecl::new(ty, span));
let mut new_decl = LocalDecl::new(ty, span);
new_decl.local_info = local_info;
self.new_locals.push(new_decl);
Local::new(index as usize)
}

pub fn new_temp(&mut self, ty: Ty<'tcx>, span: Span) -> Local {
self.new_local_with_info(ty, span, None)
}

pub fn new_internal(&mut self, ty: Ty<'tcx>, span: Span) -> Local {
let index = self.next_local;
self.next_local += 1;
Expand Down
15 changes: 14 additions & 1 deletion compiler/rustc_mir_transform/src/add_retag.rs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,17 @@ fn may_be_reference(ty: Ty<'_>) -> bool {
}
}

/// Determines whether or not this LocalDecl is temp, if not it needs retagging.
fn is_not_temp<'tcx>(local_decl: &LocalDecl<'tcx>) -> bool {
if let Some(local_info) = &local_decl.local_info {
match local_info.as_ref() {
LocalInfo::DerefTemp => return false,
_ => (),
};
}
return true;
}

impl<'tcx> MirPass<'tcx> for AddRetag {
fn is_enabled(&self, sess: &rustc_session::Session) -> bool {
sess.opts.debugging_opts.mir_emit_retag
Expand All @@ -71,7 +82,9 @@ impl<'tcx> MirPass<'tcx> for AddRetag {
let needs_retag = |place: &Place<'tcx>| {
// FIXME: Instead of giving up for unstable places, we should introduce
// a temporary and retag on that.
is_stable(place.as_ref()) && may_be_reference(place.ty(&*local_decls, tcx).ty)
is_stable(place.as_ref())
&& may_be_reference(place.ty(&*local_decls, tcx).ty)
&& is_not_temp(&local_decls[place.local])
};
let place_base_raw = |place: &Place<'tcx>| {
// If this is a `Deref`, get the type of what we are deref'ing.
Expand Down
11 changes: 7 additions & 4 deletions compiler/rustc_mir_transform/src/deref_separator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,21 +33,24 @@ impl<'tcx> MutVisitor<'tcx> for DerefChecker<'tcx> {
for (idx, (p_ref, p_elem)) in place.iter_projections().enumerate() {
if p_elem == ProjectionElem::Deref && !p_ref.projection.is_empty() {
let ty = p_ref.ty(&self.local_decls, self.tcx).ty;
let temp =
self.patcher.new_temp(ty, self.local_decls[p_ref.local].source_info.span);
let temp = self.patcher.new_local_with_info(
ty,
self.local_decls[p_ref.local].source_info.span,
Some(Box::new(LocalInfo::DerefTemp)),
);

self.patcher.add_statement(loc, StatementKind::StorageLive(temp));

// We are adding current p_ref's projections to our
// temp value, excluding projections we already covered.
let deref_place = Place::from(place_local)
.project_deeper(&p_ref.projection[last_len..], self.tcx);

self.patcher.add_assign(
loc,
Place::from(temp),
Rvalue::Use(Operand::Move(deref_place)),
);

place_local = temp;
last_len = p_ref.projection.len();

Expand All @@ -58,7 +61,7 @@ impl<'tcx> MutVisitor<'tcx> for DerefChecker<'tcx> {
*place = temp_place;
}

// We are destroying last temp since it's no longer used.
// We are destroying the previous temp since it's no longer used.
if let Some(prev_temp) = prev_temp {
self.patcher.add_statement(loc, StatementKind::StorageDead(prev_temp));
}
Expand Down
2 changes: 1 addition & 1 deletion compiler/rustc_mir_transform/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -426,13 +426,13 @@ fn run_post_borrowck_cleanup_passes<'tcx>(tcx: TyCtxt<'tcx>, body: &mut Body<'tc
&add_moves_for_packed_drops::AddMovesForPackedDrops,
// `AddRetag` needs to run after `ElaborateDrops`. Otherwise it should run fairly late,
// but before optimizations begin.
&deref_separator::Derefer,
&add_retag::AddRetag,
&lower_intrinsics::LowerIntrinsics,
&simplify::SimplifyCfg::new("elaborate-drops"),
// `Deaggregator` is conceptually part of MIR building, some backends rely on it happening
// and it can help optimizations.
&deaggregator::Deaggregator,
&deref_separator::Derefer,
&Lint(const_prop_lint::ConstProp),
];

Expand Down
8 changes: 4 additions & 4 deletions src/test/mir-opt/derefer_complex_case.main.Derefer.diff
Original file line number Diff line number Diff line change
Expand Up @@ -102,10 +102,10 @@
StorageDead(_6); // scope 1 at $DIR/derefer_complex_case.rs:4:39: 4:40
_5 = const (); // scope 1 at $DIR/derefer_complex_case.rs:4:5: 4:40
goto -> bb2; // scope 1 at $DIR/derefer_complex_case.rs:4:5: 4:40
+ }
+
+ bb8 (cleanup): {
+ resume; // scope 0 at $DIR/derefer_complex_case.rs:3:1: 5:2
}
bb8 (cleanup): {
resume; // scope 0 at $DIR/derefer_complex_case.rs:3:1: 5:2
}
}

8 changes: 4 additions & 4 deletions src/test/mir-opt/derefer_terminator_test.main.Derefer.diff
Original file line number Diff line number Diff line change
Expand Up @@ -94,10 +94,10 @@
StorageDead(_2); // scope 1 at $DIR/derefer_terminator_test.rs:10:1: 10:2
StorageDead(_1); // scope 0 at $DIR/derefer_terminator_test.rs:10:1: 10:2
return; // scope 0 at $DIR/derefer_terminator_test.rs:10:2: 10:2
+ }
+
+ bb6 (cleanup): {
+ resume; // scope 0 at $DIR/derefer_terminator_test.rs:2:1: 10:2
}
bb6 (cleanup): {
resume; // scope 0 at $DIR/derefer_terminator_test.rs:2:1: 10:2
}
}

16 changes: 6 additions & 10 deletions src/test/mir-opt/derefer_test.main.Derefer.diff
Original file line number Diff line number Diff line change
Expand Up @@ -25,15 +25,11 @@

bb0: {
StorageLive(_1); // scope 0 at $DIR/derefer_test.rs:3:9: 3:14
Deinit(_1); // scope 0 at $DIR/derefer_test.rs:3:17: 3:24
(_1.0: i32) = const 42_i32; // scope 0 at $DIR/derefer_test.rs:3:17: 3:24
(_1.1: i32) = const 43_i32; // scope 0 at $DIR/derefer_test.rs:3:17: 3:24
_1 = (const 42_i32, const 43_i32); // scope 0 at $DIR/derefer_test.rs:3:17: 3:24
StorageLive(_2); // scope 1 at $DIR/derefer_test.rs:4:9: 4:14
StorageLive(_3); // scope 1 at $DIR/derefer_test.rs:4:22: 4:28
_3 = &mut _1; // scope 1 at $DIR/derefer_test.rs:4:22: 4:28
Deinit(_2); // scope 1 at $DIR/derefer_test.rs:4:17: 4:29
(_2.0: i32) = const 99_i32; // scope 1 at $DIR/derefer_test.rs:4:17: 4:29
(_2.1: &mut (i32, i32)) = move _3; // scope 1 at $DIR/derefer_test.rs:4:17: 4:29
_2 = (const 99_i32, move _3); // scope 1 at $DIR/derefer_test.rs:4:17: 4:29
StorageDead(_3); // scope 1 at $DIR/derefer_test.rs:4:28: 4:29
StorageLive(_4); // scope 2 at $DIR/derefer_test.rs:5:9: 5:10
- _4 = &mut ((*(_2.1: &mut (i32, i32))).0: i32); // scope 2 at $DIR/derefer_test.rs:5:13: 5:26
Expand All @@ -53,10 +49,10 @@
StorageDead(_2); // scope 1 at $DIR/derefer_test.rs:7:1: 7:2
StorageDead(_1); // scope 0 at $DIR/derefer_test.rs:7:1: 7:2
return; // scope 0 at $DIR/derefer_test.rs:7:2: 7:2
+ }
+
+ bb1 (cleanup): {
+ resume; // scope 0 at $DIR/derefer_test.rs:2:1: 7:2
}
bb1 (cleanup): {
resume; // scope 0 at $DIR/derefer_test.rs:2:1: 7:2
}
}

24 changes: 8 additions & 16 deletions src/test/mir-opt/derefer_test_multiple.main.Derefer.diff
Original file line number Diff line number Diff line change
Expand Up @@ -39,29 +39,21 @@

bb0: {
StorageLive(_1); // scope 0 at $DIR/derefer_test_multiple.rs:3:9: 3:14
Deinit(_1); // scope 0 at $DIR/derefer_test_multiple.rs:3:17: 3:25
(_1.0: i32) = const 42_i32; // scope 0 at $DIR/derefer_test_multiple.rs:3:17: 3:25
(_1.1: i32) = const 43_i32; // scope 0 at $DIR/derefer_test_multiple.rs:3:17: 3:25
_1 = (const 42_i32, const 43_i32); // scope 0 at $DIR/derefer_test_multiple.rs:3:17: 3:25
StorageLive(_2); // scope 1 at $DIR/derefer_test_multiple.rs:4:9: 4:14
StorageLive(_3); // scope 1 at $DIR/derefer_test_multiple.rs:4:22: 4:28
_3 = &mut _1; // scope 1 at $DIR/derefer_test_multiple.rs:4:22: 4:28
Deinit(_2); // scope 1 at $DIR/derefer_test_multiple.rs:4:17: 4:29
(_2.0: i32) = const 99_i32; // scope 1 at $DIR/derefer_test_multiple.rs:4:17: 4:29
(_2.1: &mut (i32, i32)) = move _3; // scope 1 at $DIR/derefer_test_multiple.rs:4:17: 4:29
_2 = (const 99_i32, move _3); // scope 1 at $DIR/derefer_test_multiple.rs:4:17: 4:29
StorageDead(_3); // scope 1 at $DIR/derefer_test_multiple.rs:4:28: 4:29
StorageLive(_4); // scope 2 at $DIR/derefer_test_multiple.rs:5:9: 5:14
StorageLive(_5); // scope 2 at $DIR/derefer_test_multiple.rs:5:22: 5:28
_5 = &mut _2; // scope 2 at $DIR/derefer_test_multiple.rs:5:22: 5:28
Deinit(_4); // scope 2 at $DIR/derefer_test_multiple.rs:5:17: 5:29
(_4.0: i32) = const 11_i32; // scope 2 at $DIR/derefer_test_multiple.rs:5:17: 5:29
(_4.1: &mut (i32, &mut (i32, i32))) = move _5; // scope 2 at $DIR/derefer_test_multiple.rs:5:17: 5:29
_4 = (const 11_i32, move _5); // scope 2 at $DIR/derefer_test_multiple.rs:5:17: 5:29
StorageDead(_5); // scope 2 at $DIR/derefer_test_multiple.rs:5:28: 5:29
StorageLive(_6); // scope 3 at $DIR/derefer_test_multiple.rs:6:9: 6:14
StorageLive(_7); // scope 3 at $DIR/derefer_test_multiple.rs:6:22: 6:28
_7 = &mut _4; // scope 3 at $DIR/derefer_test_multiple.rs:6:22: 6:28
Deinit(_6); // scope 3 at $DIR/derefer_test_multiple.rs:6:17: 6:29
(_6.0: i32) = const 13_i32; // scope 3 at $DIR/derefer_test_multiple.rs:6:17: 6:29
(_6.1: &mut (i32, &mut (i32, &mut (i32, i32)))) = move _7; // scope 3 at $DIR/derefer_test_multiple.rs:6:17: 6:29
_6 = (const 13_i32, move _7); // scope 3 at $DIR/derefer_test_multiple.rs:6:17: 6:29
StorageDead(_7); // scope 3 at $DIR/derefer_test_multiple.rs:6:28: 6:29
StorageLive(_8); // scope 4 at $DIR/derefer_test_multiple.rs:7:9: 7:10
- _8 = &mut ((*((*((*(_6.1: &mut (i32, &mut (i32, &mut (i32, i32))))).1: &mut (i32, &mut (i32, i32)))).1: &mut (i32, i32))).1: i32); // scope 4 at $DIR/derefer_test_multiple.rs:7:13: 7:30
Expand Down Expand Up @@ -95,10 +87,10 @@
StorageDead(_2); // scope 1 at $DIR/derefer_test_multiple.rs:9:1: 9:2
StorageDead(_1); // scope 0 at $DIR/derefer_test_multiple.rs:9:1: 9:2
return; // scope 0 at $DIR/derefer_test_multiple.rs:9:2: 9:2
+ }
+
+ bb1 (cleanup): {
+ resume; // scope 0 at $DIR/derefer_test_multiple.rs:2:1: 9:2
}
bb1 (cleanup): {
resume; // scope 0 at $DIR/derefer_test_multiple.rs:2:1: 9:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -68,10 +68,8 @@
+ bb3: {
StorageDead(_3); // scope 0 at $DIR/early_otherwise_branch.rs:8:1: 8:2
return; // scope 0 at $DIR/early_otherwise_branch.rs:8:2: 8:2
}

- bb5 (cleanup): {
- resume; // scope 0 at $DIR/early_otherwise_branch.rs:3:1: 8:2
+ }
+
+ bb4: {
+ StorageDead(_11); // scope 0 at $DIR/early_otherwise_branch.rs:4:5: 4:17
+ switchInt(_7) -> [1_isize: bb2, otherwise: bb1]; // scope 0 at $DIR/early_otherwise_branch.rs:4:5: 4:17
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -82,10 +82,8 @@
+ bb4: {
StorageDead(_3); // scope 0 at $DIR/early_otherwise_branch.rs:17:1: 17:2
return; // scope 0 at $DIR/early_otherwise_branch.rs:17:2: 17:2
}

- bb7 (cleanup): {
- resume; // scope 0 at $DIR/early_otherwise_branch.rs:11:1: 17:2
+ }
+
+ bb5: {
+ StorageDead(_12); // scope 0 at $DIR/early_otherwise_branch.rs:12:5: 12:17
+ switchInt(_8) -> [0_isize: bb3, 1_isize: bb2, otherwise: bb1]; // scope 0 at $DIR/early_otherwise_branch.rs:12:5: 12:17
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,10 +68,8 @@
+ bb3: {
StorageDead(_3); // scope 0 at $DIR/early_otherwise_branch.rs:26:1: 26:2
return; // scope 0 at $DIR/early_otherwise_branch.rs:26:2: 26:2
}

- bb5 (cleanup): {
- resume; // scope 0 at $DIR/early_otherwise_branch.rs:21:1: 26:2
+ }
+
+ bb4: {
+ StorageDead(_11); // scope 0 at $DIR/early_otherwise_branch.rs:22:5: 22:17
+ switchInt(_7) -> [1_isize: bb2, otherwise: bb1]; // scope 0 at $DIR/early_otherwise_branch.rs:22:5: 22:17
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -90,10 +90,8 @@
+ bb4: {
StorageDead(_4); // scope 0 at $DIR/early_otherwise_branch_3_element_tuple.rs:9:1: 9:2
return; // scope 0 at $DIR/early_otherwise_branch_3_element_tuple.rs:9:2: 9:2
}

- bb6 (cleanup): {
- resume; // scope 0 at $DIR/early_otherwise_branch_3_element_tuple.rs:4:1: 9:2
+ }
+
+ bb5: {
+ StorageDead(_15); // scope 0 at $DIR/early_otherwise_branch_3_element_tuple.rs:5:5: 5:20
+ switchInt(_10) -> [1_isize: bb2, otherwise: bb1]; // scope 0 at $DIR/early_otherwise_branch_3_element_tuple.rs:5:5: 5:20
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -91,9 +91,5 @@
StorageDead(_3); // scope 0 at $DIR/early_otherwise_branch_noopt.rs:14:1: 14:2
return; // scope 0 at $DIR/early_otherwise_branch_noopt.rs:14:2: 14:2
}

bb9 (cleanup): {
resume; // scope 0 at $DIR/early_otherwise_branch_noopt.rs:7:1: 14:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,5 @@
bb5: {
return; // scope 0 at $DIR/early_otherwise_branch_soundness.rs:27:2: 27:2
}

bb6 (cleanup): {
resume; // scope 0 at $DIR/early_otherwise_branch_soundness.rs:18:1: 27:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,5 @@
bb4: {
return; // scope 0 at $DIR/early_otherwise_branch_soundness.rs:14:2: 14:2
}

bb5 (cleanup): {
resume; // scope 0 at $DIR/early_otherwise_branch_soundness.rs:12:1: 14:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:17:25: 17:26
return; // scope 0 at $DIR/if-condition-int.rs:18:2: 18:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:16:1: 18:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:53:34: 53:35
return; // scope 0 at $DIR/if-condition-int.rs:54:2: 54:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:52:1: 54:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -54,9 +54,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:49:1: 49:2
return; // scope 0 at $DIR/if-condition-int.rs:49:2: 49:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:43:1: 49:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:21:32: 21:33
return; // scope 0 at $DIR/if-condition-int.rs:22:2: 22:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:20:1: 22:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:25:31: 25:32
return; // scope 0 at $DIR/if-condition-int.rs:26:2: 26:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:24:1: 26:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -61,9 +61,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:39:5: 39:6
return; // scope 0 at $DIR/if-condition-int.rs:40:2: 40:2
}

bb7 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:32:1: 40:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:29:32: 29:33
return; // scope 0 at $DIR/if-condition-int.rs:30:2: 30:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:28:1: 30:2
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,5 @@
StorageDead(_2); // scope 0 at $DIR/if-condition-int.rs:12:31: 12:32
return; // scope 0 at $DIR/if-condition-int.rs:13:2: 13:2
}

bb4 (cleanup): {
resume; // scope 0 at $DIR/if-condition-int.rs:11:1: 13:2
}
}

Loading

0 comments on commit 6eda764

Please sign in to comment.