From 5ffc9197264a07a50bfb27e436fe284ae8c0687c Mon Sep 17 00:00:00 2001 From: Matthew Jasper Date: Sun, 10 Feb 2019 16:49:26 +0000 Subject: [PATCH] Move the exit block of the match to the end --- src/librustc_mir/build/matches/mod.rs | 14 ++- src/test/mir-opt/issue-49232.rs | 38 ++++---- src/test/mir-opt/match_false_edges.rs | 120 ++++++++++++------------ src/test/mir-opt/match_test.rs | 40 ++++---- src/test/mir-opt/remove_fake_borrows.rs | 44 ++++----- 5 files changed, 130 insertions(+), 126 deletions(-) diff --git a/src/librustc_mir/build/matches/mod.rs b/src/librustc_mir/build/matches/mod.rs index 07c179ded593f..2c4eb0bc091c3 100644 --- a/src/librustc_mir/build/matches/mod.rs +++ b/src/librustc_mir/build/matches/mod.rs @@ -250,12 +250,8 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { // Step 5. Create everything else: the guards and the arms. - // all the arm blocks will rejoin here - let end_block = self.cfg.start_new_block(); - let outer_source_info = self.source_info(span); - - for (arm, candidates) in arm_candidates { + let arm_end_blocks: Vec<_> = arm_candidates.into_iter().map(|(arm, candidates)| { let mut arm_block = self.cfg.start_new_block(); let body = self.hir.mirror(arm.body.clone()); @@ -283,6 +279,14 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { } unpack!(arm_block = self.into(destination, arm_block, body)); + + arm_block + }).collect(); + + // all the arm blocks will rejoin here + let end_block = self.cfg.start_new_block(); + + for arm_block in arm_end_blocks { self.cfg.terminate( arm_block, outer_source_info, diff --git a/src/test/mir-opt/issue-49232.rs b/src/test/mir-opt/issue-49232.rs index 5b4ec483277ac..0f0401a55eaca 100644 --- a/src/test/mir-opt/issue-49232.rs +++ b/src/test/mir-opt/issue-49232.rs @@ -47,10 +47,10 @@ fn main() { // resume; // } // bb5: { -// falseEdges -> [real: bb12, imaginary: bb6]; +// falseEdges -> [real: bb11, imaginary: bb6]; // } // bb6: { -// falseEdges -> [real: bb14, imaginary: bb7]; +// falseEdges -> [real: bb13, imaginary: bb7]; // } // bb7: { // unreachable; @@ -62,41 +62,41 @@ fn main() { // goto -> bb5; // } // bb10: { -// FakeRead(ForLet, _2); -// StorageDead(_3); -// StorageLive(_6); -// _6 = &_2; -// _5 = const std::mem::drop(move _6) -> [return: bb19, unwind: bb4]; +// _2 = const 4i32; +// goto -> bb18; // } // bb11: { -// _2 = const 4i32; // goto -> bb10; // } // bb12: { -// goto -> bb11; +// _0 = (); +// goto -> bb14; // } // bb13: { -// _0 = (); -// goto -> bb15; +// goto -> bb12; // } // bb14: { -// goto -> bb13; -// } -// bb15: { // StorageDead(_3); -// goto -> bb16; +// goto -> bb15; // } -// bb16: { +// bb15: { // StorageDead(_2); // goto -> bb2; // } -// bb17: { +// bb16: { // _4 = (); // unreachable; // } -// bb18: { +// bb17: { // StorageDead(_4); -// goto -> bb10; +// goto -> bb18; +// } +// bb18: { +// FakeRead(ForLet, _2); +// StorageDead(_3); +// StorageLive(_6); +// _6 = &_2; +// _5 = const std::mem::drop(move _6) -> [return: bb19, unwind: bb4]; // } // bb19: { // StorageDead(_6); diff --git a/src/test/mir-opt/match_false_edges.rs b/src/test/mir-opt/match_false_edges.rs index cf650b5a0ba58..ab6de71d2894d 100644 --- a/src/test/mir-opt/match_false_edges.rs +++ b/src/test/mir-opt/match_false_edges.rs @@ -51,13 +51,13 @@ fn main() { // resume; // } // bb2: { -// falseEdges -> [real: bb9, imaginary: bb3]; //pre_binding1 +// falseEdges -> [real: bb8, imaginary: bb3]; //pre_binding1 // } // bb3: { -// falseEdges -> [real: bb12, imaginary: bb4]; //pre_binding2 +// falseEdges -> [real: bb11, imaginary: bb4]; //pre_binding2 // } // bb4: { -// falseEdges -> [real: bb13, imaginary: bb5]; //pre_binding3 +// falseEdges -> [real: bb12, imaginary: bb5]; //pre_binding3 // } // bb5: { // unreachable; @@ -68,43 +68,43 @@ fn main() { // bb7: { // unreachable; // } -// bb8: { -// ... -// return; -// } -// bb9: { // binding1 and guard +// bb8: { // binding1 and guard // StorageLive(_6); // _6 = &(((promoted[1]: std::option::Option) as Some).0: i32); // _4 = &shallow (promoted[0]: std::option::Option); // StorageLive(_7); -// _7 = const guard() -> [return: bb10, unwind: bb1]; +// _7 = const guard() -> [return: bb9, unwind: bb1]; // } -// bb10: { +// bb9: { // FakeRead(ForMatchGuard, _4); // FakeRead(ForGuardBinding, _6); -// switchInt(move _7) -> [false: bb6, otherwise: bb11]; +// switchInt(move _7) -> [false: bb6, otherwise: bb10]; // } -// bb11: { +// bb10: { // StorageLive(_5); // _5 = ((_2 as Some).0: i32); // StorageLive(_8); // _8 = _5; // _1 = (const 1i32, move _8); // StorageDead(_8); -// goto -> bb8; +// goto -> bb13; // } -// bb12: { +// bb11: { // StorageLive(_9); // _9 = ((_2 as Some).0: i32); // StorageLive(_10); // _10 = _9; // _1 = (const 2i32, move _10); // StorageDead(_10); -// goto -> bb8; +// goto -> bb13; // } -// bb13: { +// bb12: { // _1 = (const 3i32, const 3i32); -// goto -> bb8; +// goto -> bb13; +// } +// bb13: { +// ... +// return; // } // END rustc.full_tested_match.QualifyAndPromoteConstants.after.mir // @@ -120,13 +120,13 @@ fn main() { // resume; // } // bb2: { -// falseEdges -> [real: bb9, imaginary: bb3]; +// falseEdges -> [real: bb8, imaginary: bb3]; // } // bb3: { -// falseEdges -> [real: bb12, imaginary: bb4]; +// falseEdges -> [real: bb11, imaginary: bb4]; // } // bb4: { -// falseEdges -> [real: bb13, imaginary: bb5]; +// falseEdges -> [real: bb12, imaginary: bb5]; // } // bb5: { // unreachable; @@ -137,43 +137,43 @@ fn main() { // bb7: { // unreachable; // } -// bb8: { -// ... -// return; -// } -// bb9: { // binding1 and guard +// bb8: { // binding1 and guard // StorageLive(_6); // _6 = &((_2 as Some).0: i32); // _4 = &shallow _2; // StorageLive(_7); -// _7 = const guard() -> [return: bb10, unwind: bb1]; +// _7 = const guard() -> [return: bb9, unwind: bb1]; // } -// bb10: { // end of guard +// bb9: { // end of guard // FakeRead(ForMatchGuard, _4); // FakeRead(ForGuardBinding, _6); -// switchInt(move _7) -> [false: bb6, otherwise: bb11]; +// switchInt(move _7) -> [false: bb6, otherwise: bb10]; // } -// bb11: { // arm1 +// bb10: { // arm1 // StorageLive(_5); // _5 = ((_2 as Some).0: i32); // StorageLive(_8); // _8 = _5; // _1 = (const 1i32, move _8); // StorageDead(_8); -// goto -> bb8; +// goto -> bb13; // } -// bb12: { // arm2 +// bb11: { // arm2 // _1 = (const 3i32, const 3i32); -// goto -> bb8; +// goto -> bb13; // } -// bb13: { // binding3 and arm3 +// bb12: { // binding3 and arm3 // StorageLive(_9); // _9 = ((_2 as Some).0: i32); // StorageLive(_10); // _10 = _9; // _1 = (const 2i32, move _10); // StorageDead(_10); -// goto -> bb8; +// goto -> bb13; +// } +// bb13: { +// ... +// return; // } // END rustc.full_tested_match2.QualifyAndPromoteConstants.before.mir // @@ -189,79 +189,79 @@ fn main() { // resume; // } // bb2: { -// falseEdges -> [real: bb10, imaginary: bb3]; //pre_binding1 +// falseEdges -> [real: bb9, imaginary: bb3]; // } // bb3: { -// falseEdges -> [real: bb13, imaginary: bb4]; //pre_binding2 +// falseEdges -> [real: bb12, imaginary: bb4]; // } // bb4: { -// falseEdges -> [real: bb14, imaginary: bb5]; //pre_binding3 +// falseEdges -> [real: bb13, imaginary: bb5]; // } // bb5: { -// falseEdges -> [real: bb17, imaginary: bb6]; //pre_binding4 +// falseEdges -> [real: bb16, imaginary: bb6]; // } // bb6: { // unreachable; // } -// bb7: { // to pre_binding2 +// bb7: { // falseEdges -> [real: bb3, imaginary: bb3]; // } -// bb8: { // to pre_binding4 +// bb8: { // falseEdges -> [real: bb5, imaginary: bb5]; // } -// bb9: { -// ... -// return; -// } -// bb10: { // binding1: Some(w) if guard() +// bb9: { // binding1: Some(w) if guard() // StorageLive(_7); // _7 = &((_2 as Some).0: i32); // _5 = &shallow _2; // StorageLive(_8); -// _8 = const guard() -> [return: bb11, unwind: bb1]; +// _8 = const guard() -> [return: bb10, unwind: bb1]; // } -// bb11: { //end of guard +// bb10: { //end of guard // FakeRead(ForMatchGuard, _5); // FakeRead(ForGuardBinding, _7); -// switchInt(move _8) -> [false: bb7, otherwise: bb12]; +// switchInt(move _8) -> [false: bb7, otherwise: bb11]; // } -// bb12: { // set up bindings for arm1 +// bb11: { // set up bindings for arm1 // StorageLive(_6); // _6 = ((_2 as Some).0: i32); // _1 = const 1i32; -// goto -> bb9; +// goto -> bb17; // } -// bb13: { // binding2 & arm2 +// bb12: { // binding2 & arm2 // StorageLive(_9); // _9 = _2; // _1 = const 2i32; -// goto -> bb9; +// goto -> bb17; // } -// bb14: { // binding3: Some(y) if guard2(y) +// bb13: { // binding3: Some(y) if guard2(y) // StorageLive(_11); // _11 = &((_2 as Some).0: i32); // _5 = &shallow _2; // StorageLive(_12); // StorageLive(_13); // _13 = (*_11); -// _12 = const guard2(move _13) -> [return: bb15, unwind: bb1]; +// _12 = const guard2(move _13) -> [return: bb14, unwind: bb1]; // } -// bb15: { // end of guard2 +// bb14: { // end of guard2 // StorageDead(_13); // FakeRead(ForMatchGuard, _5); // FakeRead(ForGuardBinding, _11); -// switchInt(move _12) -> [false: bb8, otherwise: bb16]; +// switchInt(move _12) -> [false: bb8, otherwise: bb15]; // } -// bb16: { // binding4 & arm4 +// bb15: { // binding4 & arm4 // StorageLive(_10); // _10 = ((_2 as Some).0: i32); // _1 = const 3i32; -// goto -> bb9; +// goto -> bb17; // } -// bb17: { +// bb16: { // StorageLive(_14); // _14 = _2; // _1 = const 4i32; -// goto -> bb9; +// goto -> bb17; +// } +// bb17: { +// ... +// return; // } // END rustc.main.QualifyAndPromoteConstants.before.mir diff --git a/src/test/mir-opt/match_test.rs b/src/test/mir-opt/match_test.rs index 835a5ce1200b9..3f248f3d41a64 100644 --- a/src/test/mir-opt/match_test.rs +++ b/src/test/mir-opt/match_test.rs @@ -23,16 +23,16 @@ fn main() { // switchInt(move _4) -> [false: bb7, otherwise: bb8]; // } // bb1: { -// falseEdges -> [real: bb13, imaginary: bb2]; +// falseEdges -> [real: bb12, imaginary: bb2]; // } // bb2: { -// falseEdges -> [real: bb14, imaginary: bb3]; +// falseEdges -> [real: bb13, imaginary: bb3]; // } // bb3: { -// falseEdges -> [real: bb15, imaginary: bb4]; +// falseEdges -> [real: bb14, imaginary: bb4]; // } // bb4: { -// falseEdges -> [real: bb16, imaginary: bb5]; +// falseEdges -> [real: bb15, imaginary: bb5]; // } // bb5: { // unreachable; @@ -56,31 +56,31 @@ fn main() { // switchInt(move _7) -> [false: bb9, otherwise: bb2]; // } // bb11: { -// StorageDead(_8); -// _0 = (); -// StorageDead(_2); -// StorageDead(_1); -// return; -// } -// bb12: { // _3 = const 0i32; -// goto -> bb11; +// goto -> bb16; // } -// bb13: { +// bb12: { // StorageLive(_8); // _8 = _2; -// switchInt(move _8) -> [false: bb6, otherwise: bb12]; +// switchInt(move _8) -> [false: bb6, otherwise: bb11]; // } -// bb14: { +// bb13: { // _3 = const 1i32; -// goto -> bb11; +// goto -> bb16; // } -// bb15: { +// bb14: { // _3 = const 2i32; -// goto -> bb11; +// goto -> bb16; // } -// bb16: { +// bb15: { // _3 = const 3i32; -// goto -> bb11; +// goto -> bb16; +// } +// bb16: { +// StorageDead(_8); +// _0 = (); +// StorageDead(_2); +// StorageDead(_1); +// return; // } // END rustc.main.SimplifyCfg-initial.after.mir diff --git a/src/test/mir-opt/remove_fake_borrows.rs b/src/test/mir-opt/remove_fake_borrows.rs index ebb1ef2f430b5..48d1c991b623e 100644 --- a/src/test/mir-opt/remove_fake_borrows.rs +++ b/src/test/mir-opt/remove_fake_borrows.rs @@ -24,10 +24,10 @@ fn main() { // switchInt(move _3) -> [1isize: bb5, otherwise: bb2]; // } // bb1: { -// goto -> bb8; +// goto -> bb7; // } // bb2: { -// goto -> bb9; +// goto -> bb8; // } // bb3: { // unreachable; @@ -39,14 +39,10 @@ fn main() { // switchInt((*(*((_1 as Some).0: &' &' i32)))) -> [0i32: bb1, otherwise: bb2]; // } // bb6: { -// StorageDead(_8); -// return; -// } -// bb7: { // _0 = const 0i32; -// goto -> bb6; +// goto -> bb9; // } -// bb8: { +// bb7: { // _4 = &shallow _1; // _5 = &shallow ((_1 as Some).0: &' &' i32); // _6 = &shallow (*((_1 as Some).0: &' &' i32)); @@ -57,11 +53,15 @@ fn main() { // FakeRead(ForMatchGuard, _5); // FakeRead(ForMatchGuard, _6); // FakeRead(ForMatchGuard, _7); -// switchInt(move _8) -> [false: bb4, otherwise: bb7]; +// switchInt(move _8) -> [false: bb4, otherwise: bb6]; // } -// bb9: { +// bb8: { // _0 = const 1i32; -// goto -> bb6; +// goto -> bb9; +// } +// bb9: { +// StorageDead(_8); +// return; // } // bb10: { // resume; @@ -75,10 +75,10 @@ fn main() { // switchInt(move _3) -> [1isize: bb5, otherwise: bb2]; // } // bb1: { -// goto -> bb8; +// goto -> bb7; // } // bb2: { -// goto -> bb9; +// goto -> bb8; // } // bb3: { // unreachable; @@ -90,14 +90,10 @@ fn main() { // switchInt((*(*((_1 as Some).0: &' &' i32)))) -> [0i32: bb1, otherwise: bb2]; // } // bb6: { -// StorageDead(_8); -// return; -// } -// bb7: { // _0 = const 0i32; -// goto -> bb6; +// goto -> bb9; // } -// bb8: { +// bb7: { // nop; // nop; // nop; @@ -108,11 +104,15 @@ fn main() { // nop; // nop; // nop; -// switchInt(move _8) -> [false: bb4, otherwise: bb7]; +// switchInt(move _8) -> [false: bb4, otherwise: bb6]; // } -// bb9: { +// bb8: { // _0 = const 1i32; -// goto -> bb6; +// goto -> bb9; +// } +// bb9: { +// StorageDead(_8); +// return; // } // bb10: { // resume;