diff options
| -rw-r--r-- | src/librustc_borrowck/borrowck/mir/elaborate_drops.rs | 65 | ||||
| -rw-r--r-- | src/librustc_mir/build/matches/test.rs | 21 |
2 files changed, 32 insertions, 54 deletions
diff --git a/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs b/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs index d7ffe538c24..5899c9f31d1 100644 --- a/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs +++ b/src/librustc_borrowck/borrowck/mir/elaborate_drops.rs @@ -620,48 +620,11 @@ impl<'b, 'tcx> ElaborateDropsCtxt<'b, 'tcx> { self.elaborated_drop_block(&inner_c) } - fn open_drop_for_variant<'a>(&mut self, - c: &DropCtxt<'a, 'tcx>, - drop_block: &mut Option<BasicBlock>, - adt: &'tcx ty::AdtDef, - substs: &'tcx Substs<'tcx>, - variant_index: usize) - -> (BasicBlock, bool) - { - let subpath = super::move_path_children_matching( - self.move_data(), c.path, |proj| match proj { - &Projection { - elem: ProjectionElem::Downcast(_, idx), .. - } => idx == variant_index, - _ => false - }); - - if let Some(variant_path) = subpath { - let base_lv = c.lvalue.clone().elem( - ProjectionElem::Downcast(adt, variant_index) - ); - let fields = self.move_paths_for_fields( - &base_lv, - variant_path, - &adt.variants[variant_index], - substs); - (self.drop_ladder(c, fields), true) - } else { - // variant not found - drop the entire enum - if let None = *drop_block { - *drop_block = Some(self.complete_drop(c, true)); - } - (drop_block.unwrap(), false) - } - } - fn open_drop_for_adt<'a>(&mut self, c: &DropCtxt<'a, 'tcx>, adt: &'tcx ty::AdtDef, substs: &'tcx Substs<'tcx>) -> BasicBlock { debug!("open_drop_for_adt({:?}, {:?}, {:?})", c, adt, substs); - let mut drop_block = None; - match adt.variants.len() { 1 => { let fields = self.move_paths_for_fields( @@ -676,17 +639,33 @@ impl<'b, 'tcx> ElaborateDropsCtxt<'b, 'tcx> { let mut values = Vec::with_capacity(adt.variants.len()); let mut blocks = Vec::with_capacity(adt.variants.len()); let mut otherwise = None; - for (idx, variant) in adt.variants.iter().enumerate() { + for (variant_index, variant) in adt.variants.iter().enumerate() { let discr = ConstInt::new_inttype(variant.disr_val, adt.discr_ty, self.tcx.sess.target.uint_type, self.tcx.sess.target.int_type).unwrap(); - let (blk, is_ladder) = self.open_drop_for_variant(c, &mut drop_block, adt, - substs, idx); - if is_ladder { + let subpath = super::move_path_children_matching( + self.move_data(), c.path, |proj| match proj { + &Projection { + elem: ProjectionElem::Downcast(_, idx), .. + } => idx == variant_index, + _ => false + }); + if let Some(variant_path) = subpath { + let base_lv = c.lvalue.clone().elem( + ProjectionElem::Downcast(adt, variant_index) + ); + let fields = self.move_paths_for_fields( + &base_lv, + variant_path, + &adt.variants[variant_index], + substs); values.push(discr); - blocks.push(blk); + blocks.push(self.drop_ladder(c, fields)); } else { - otherwise = Some(blk) + // variant not found - drop the entire enum + if let None = otherwise { + otherwise = Some(self.complete_drop(c, true)); + } } } if let Some(block) = otherwise { diff --git a/src/librustc_mir/build/matches/test.rs b/src/librustc_mir/build/matches/test.rs index 7e47e173c51..01c0433112b 100644 --- a/src/librustc_mir/build/matches/test.rs +++ b/src/librustc_mir/build/matches/test.rs @@ -227,8 +227,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { } TestKind::SwitchInt { switch_ty, ref options, indices: _ } => { - let (values, targets, ret) = if switch_ty.sty == ty::TyBool { - static BOOL_SWITCH_FALSE: &'static [ConstInt] = &[ConstInt::Infer(0)]; + let (ret, terminator) = if switch_ty.sty == ty::TyBool { assert!(options.len() > 0 && options.len() <= 2); let (true_bb, false_bb) = (self.cfg.start_new_block(), self.cfg.start_new_block()); @@ -237,7 +236,8 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { &ConstVal::Bool(false) => vec![false_bb, true_bb], v => span_bug!(test.span, "expected boolean value but got {:?}", v) }; - (From::from(BOOL_SWITCH_FALSE), vec![false_bb, true_bb], ret) + (ret, TerminatorKind::if_(self.hir.tcx(), Operand::Consume(lvalue.clone()), + true_bb, false_bb)) } else { // The switch may be inexhaustive so we // add a catch all block @@ -250,15 +250,14 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { let values: Vec<_> = options.iter().map(|v| v.to_const_int().expect("switching on integral") ).collect(); - (From::from(values), targets.clone(), targets) + (targets.clone(), TerminatorKind::SwitchInt { + discr: Operand::Consume(lvalue.clone()), + switch_ty: switch_ty, + values: From::from(values), + targets: targets, + }) }; - - self.cfg.terminate(block, source_info, TerminatorKind::SwitchInt { - discr: Operand::Consume(lvalue.clone()), - switch_ty: switch_ty, - values: values, - targets: targets.clone(), - }); + self.cfg.terminate(block, source_info, terminator); ret } |
