diff options
| author | Simonas Kazlauskas <git@kazlauskas.me> | 2015-12-19 00:44:32 +0200 |
|---|---|---|
| committer | Simonas Kazlauskas <git@kazlauskas.me> | 2016-01-06 13:57:51 +0200 |
| commit | 4e86dcdb7295e88d3ccc28b508ba69a24fefa371 (patch) | |
| tree | b68f30dd6698552c9b331693e6b73968ad42d02f /src/librustc_mir/transform | |
| parent | 5b34690842474019c0a1c6cd4d0a7b75108e9d2d (diff) | |
| download | rust-4e86dcdb7295e88d3ccc28b508ba69a24fefa371.tar.gz rust-4e86dcdb7295e88d3ccc28b508ba69a24fefa371.zip | |
Remove diverge terminator
Unreachable terminator can be contained all within the trans.
Diffstat (limited to 'src/librustc_mir/transform')
| -rw-r--r-- | src/librustc_mir/transform/erase_regions.rs | 3 | ||||
| -rw-r--r-- | src/librustc_mir/transform/simplify_cfg.rs | 26 | ||||
| -rw-r--r-- | src/librustc_mir/transform/util.rs | 2 |
3 files changed, 12 insertions, 19 deletions
diff --git a/src/librustc_mir/transform/erase_regions.rs b/src/librustc_mir/transform/erase_regions.rs index 90bb73dbe28..01d873abc6f 100644 --- a/src/librustc_mir/transform/erase_regions.rs +++ b/src/librustc_mir/transform/erase_regions.rs @@ -59,7 +59,7 @@ impl<'a, 'tcx> EraseRegions<'a, 'tcx> { self.erase_regions_statement(statement); } - self.erase_regions_terminator(&mut basic_block.terminator); + self.erase_regions_terminator(basic_block.terminator_mut()); } fn erase_regions_statement(&mut self, @@ -79,7 +79,6 @@ impl<'a, 'tcx> EraseRegions<'a, 'tcx> { terminator: &mut Terminator<'tcx>) { match *terminator { Terminator::Goto { .. } | - Terminator::Diverge | Terminator::Resume | Terminator::Return => { /* nothing to do */ diff --git a/src/librustc_mir/transform/simplify_cfg.rs b/src/librustc_mir/transform/simplify_cfg.rs index d0c0afc80a6..7a5a00a8d56 100644 --- a/src/librustc_mir/transform/simplify_cfg.rs +++ b/src/librustc_mir/transform/simplify_cfg.rs @@ -10,7 +10,6 @@ use rustc::middle::const_eval::ConstVal; use rustc::mir::repr::*; -use std::mem; use transform::util; use transform::MirPass; @@ -27,11 +26,10 @@ impl SimplifyCfg { // These blocks are always required. seen[START_BLOCK.index()] = true; seen[END_BLOCK.index()] = true; - seen[DIVERGE_BLOCK.index()] = true; let mut worklist = vec![START_BLOCK]; while let Some(bb) = worklist.pop() { - for succ in mir.basic_block_data(bb).terminator.successors() { + for succ in mir.basic_block_data(bb).terminator().successors() { if !seen[succ.index()] { seen[succ.index()] = true; worklist.push(*succ); @@ -51,7 +49,7 @@ impl SimplifyCfg { while mir.basic_block_data(target).statements.is_empty() { match mir.basic_block_data(target).terminator { - Terminator::Goto { target: next } => { + Some(Terminator::Goto { target: next }) => { if seen.contains(&next) { return None; } @@ -67,9 +65,9 @@ impl SimplifyCfg { let mut changed = false; for bb in mir.all_basic_blocks() { - // Temporarily swap out the terminator we're modifying to keep borrowck happy - let mut terminator = Terminator::Diverge; - mem::swap(&mut terminator, &mut mir.basic_block_data_mut(bb).terminator); + // Temporarily take ownership of the terminator we're modifying to keep borrowck happy + let mut terminator = mir.basic_block_data_mut(bb).terminator.take() + .expect("invalid terminator state"); for target in terminator.successors_mut() { let new_target = match final_target(mir, *target) { @@ -80,10 +78,8 @@ impl SimplifyCfg { changed |= *target != new_target; *target = new_target; } - - mir.basic_block_data_mut(bb).terminator = terminator; + mir.basic_block_data_mut(bb).terminator = Some(terminator); } - changed } @@ -91,11 +87,10 @@ impl SimplifyCfg { let mut changed = false; for bb in mir.all_basic_blocks() { - // Temporarily swap out the terminator we're modifying to keep borrowck happy - let mut terminator = Terminator::Diverge; - mem::swap(&mut terminator, &mut mir.basic_block_data_mut(bb).terminator); + let basic_block = mir.basic_block_data_mut(bb); + let mut terminator = basic_block.terminator_mut(); - mir.basic_block_data_mut(bb).terminator = match terminator { + *terminator = match *terminator { Terminator::If { ref targets, .. } if targets.0 == targets.1 => { changed = true; Terminator::Goto { target: targets.0 } @@ -115,7 +110,7 @@ impl SimplifyCfg { Terminator::SwitchInt { ref targets, .. } if targets.len() == 1 => { Terminator::Goto { target: targets[0] } } - _ => terminator + _ => continue } } @@ -131,7 +126,6 @@ impl<'tcx> MirPass<'tcx> for SimplifyCfg { changed |= self.remove_goto_chains(mir); self.remove_dead_blocks(mir); } - // FIXME: Should probably be moved into some kind of pass manager mir.basic_blocks.shrink_to_fit(); } diff --git a/src/librustc_mir/transform/util.rs b/src/librustc_mir/transform/util.rs index 95102694544..7e44beb18a2 100644 --- a/src/librustc_mir/transform/util.rs +++ b/src/librustc_mir/transform/util.rs @@ -15,7 +15,7 @@ use rustc::mir::repr::*; /// in a single pass pub fn update_basic_block_ids(mir: &mut Mir, replacements: &[BasicBlock]) { for bb in mir.all_basic_blocks() { - for target in mir.basic_block_data_mut(bb).terminator.successors_mut() { + for target in mir.basic_block_data_mut(bb).terminator_mut().successors_mut() { *target = replacements[target.index()]; } } |
