Skip to content

Commit 63321ca

Browse files
committed
Turn break critical edges into a MIR pass
Also adds a new set of passes to run just before translation that "prepare" the MIR for codegen. Removal of landing pads, region erasure and break critical edges are run in this pass. Also fixes some merge/rebase errors.
1 parent 6935782 commit 63321ca

File tree

4 files changed

+36
-23
lines changed

4 files changed

+36
-23
lines changed

src/librustc_driver/driver.rs

+11-12
Original file line numberDiff line numberDiff line change
@@ -876,10 +876,7 @@ pub fn phase_3_run_analysis_passes<'tcx, F, R>(sess: &'tcx Session,
876876
passes.push_pass(box mir::transform::remove_dead_blocks::RemoveDeadBlocks);
877877
passes.push_pass(box mir::transform::type_check::TypeckMir);
878878
passes.push_pass(box mir::transform::simplify_cfg::SimplifyCfg);
879-
// Late passes
880-
passes.push_pass(box mir::transform::no_landing_pads::NoLandingPads);
881879
passes.push_pass(box mir::transform::remove_dead_blocks::RemoveDeadBlocks);
882-
passes.push_pass(box mir::transform::erase_regions::EraseRegions);
883880
// And run everything.
884881
passes.run_passes(tcx, &mut mir_map);
885882
});
@@ -933,22 +930,24 @@ pub fn phase_3_run_analysis_passes<'tcx, F, R>(sess: &'tcx Session,
933930
/// Run the translation phase to LLVM, after which the AST and analysis can
934931
pub fn phase_4_translate_to_llvm<'tcx>(tcx: &TyCtxt<'tcx>,
935932
mut mir_map: MirMap<'tcx>,
936-
analysis: ty::CrateAnalysis)
937-
-> trans::CrateTranslation {
933+
analysis: ty::CrateAnalysis) -> trans::CrateTranslation {
938934
let time_passes = tcx.sess.time_passes();
939935

940936
time(time_passes,
941937
"resolving dependency formats",
942938
|| dependency_format::calculate(&tcx.sess));
943939

944-
time(time_passes,
945-
"erasing regions from MIR",
946-
|| mir::transform::erase_regions::erase_regions(tcx, &mut mir_map));
947-
948-
time(time_passes, "breaking critical edges",
949-
|| mir::transform::break_critical_edges::break_critical_edges(&mut mir_map));
940+
// Run the passes that transform the MIR into a more suitable for translation
941+
// to LLVM code.
942+
time(time_passes, "Prepare MIR codegen passes", || {
943+
let mut passes = ::rustc::mir::transform::Passes::new();
944+
passes.push_pass(box mir::transform::no_landing_pads::NoLandingPads);
945+
passes.push_pass(box mir::transform::remove_dead_blocks::RemoveDeadBlocks);
946+
passes.push_pass(box mir::transform::erase_regions::EraseRegions);
947+
passes.push_pass(box mir::transform::break_critical_edges::BreakCriticalEdges);
948+
passes.run_passes(tcx, &mut mir_map);
949+
});
950950

951-
// Option dance to work around the lack of stack once closures.
952951
time(time_passes,
953952
"translation",
954953
move || trans::trans_crate(tcx, &mir_map, analysis))

src/librustc_mir/transform/break_critical_edges.rs

+23-9
Original file line numberDiff line numberDiff line change
@@ -7,11 +7,16 @@
77
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
88
// option. This file may not be copied, modified, or distributed
99
// except according to those terms.
10+
11+
use rustc::ty::TyCtxt;
1012
use rustc::mir::repr::*;
11-
use rustc::mir::mir_map::MirMap;
13+
use rustc::mir::transform::{MirPass, Pass};
14+
use syntax::ast::NodeId;
1215

1316
use traversal;
1417

18+
pub struct BreakCriticalEdges;
19+
1520
/**
1621
* Breaks critical edges in the MIR.
1722
*
@@ -34,13 +39,16 @@ use traversal;
3439
* NOTE: Simplify CFG will happily undo most of the work this pass does.
3540
*
3641
*/
37-
pub fn break_critical_edges<'tcx>(mir_map: &mut MirMap<'tcx>) {
38-
for (_, mir) in &mut mir_map.map {
39-
break_critical_edges_fn(mir);
42+
43+
impl<'tcx> MirPass<'tcx> for BreakCriticalEdges {
44+
fn run_pass(&mut self, _: &TyCtxt<'tcx>, _: NodeId, mir: &mut Mir<'tcx>) {
45+
break_critical_edges(mir);
4046
}
4147
}
4248

43-
fn break_critical_edges_fn(mir: &mut Mir) {
49+
impl Pass for BreakCriticalEdges {}
50+
51+
fn break_critical_edges(mir: &mut Mir) {
4452
let mut pred_count = vec![0u32; mir.basic_blocks.len()];
4553

4654
// Build the precedecessor map for the MIR
@@ -63,13 +71,19 @@ fn break_critical_edges_fn(mir: &mut Mir) {
6371

6472
if let Some(ref mut term) = data.terminator {
6573
let is_invoke = term_is_invoke(term);
74+
let term_span = term.span;
75+
let term_scope = term.scope;
6676
let succs = term.successors_mut();
6777
if succs.len() > 1 || (succs.len() > 0 && is_invoke) {
6878
for tgt in succs {
6979
let num_preds = pred_count[tgt.index()];
7080
if num_preds > 1 {
7181
// It's a critical edge, break it
72-
let goto = Terminator::Goto { target: *tgt };
82+
let goto = Terminator {
83+
span: term_span,
84+
scope: term_scope,
85+
kind: TerminatorKind::Goto { target: *tgt }
86+
};
7387
let data = BasicBlockData::new(Some(goto));
7488
// Get the index it will be when inserted into the MIR
7589
let idx = cur_len + new_blocks.len();
@@ -88,9 +102,9 @@ fn break_critical_edges_fn(mir: &mut Mir) {
88102

89103
// Returns true if the terminator would use an invoke in LLVM.
90104
fn term_is_invoke(term: &Terminator) -> bool {
91-
match *term {
92-
Terminator::Call { cleanup: Some(_), .. } |
93-
Terminator::Drop { unwind: Some(_), .. } => true,
105+
match term.kind {
106+
TerminatorKind::Call { cleanup: Some(_), .. } |
107+
TerminatorKind::Drop { unwind: Some(_), .. } => true,
94108
_ => false
95109
}
96110
}

src/librustc_mir/traversal.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -163,7 +163,7 @@ impl<'a, 'tcx> Postorder<'a, 'tcx> {
163163
// Now that the top of the stack has no successors we can traverse, each item will
164164
// be popped off during iteration until we get back to `A`. This yeilds [E, D, B].
165165
//
166-
// When we yeild `B` and call `traverse_successor`, We push `C` to the stack, but
166+
// When we yield `B` and call `traverse_successor`, we push `C` to the stack, but
167167
// since we've already visited `E`, that child isn't added to the stack. The last
168168
// two iterations yield `C` and finally `A` for a final traversal of [E, D, B, C, A]
169169
loop {

src/librustc_trans/mir/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ use common::{self, Block, BlockAndBuilder, FunctionContext};
1919
use std::ops::Deref;
2020
use std::rc::Rc;
2121

22-
use trans::basic_block::BasicBlock;
22+
use basic_block::BasicBlock;
2323

2424
use rustc_data_structures::bitvec::BitVector;
2525

0 commit comments

Comments
 (0)