diff --git a/src/librustc_trans/trans/controlflow.rs b/src/librustc_trans/trans/controlflow.rs index 85d0bc0319f30..9093f56d33acc 100644 --- a/src/librustc_trans/trans/controlflow.rs +++ b/src/librustc_trans/trans/controlflow.rs @@ -40,6 +40,10 @@ pub fn trans_stmt<'blk, 'tcx>(cx: Block<'blk, 'tcx>, let fcx = cx.fcx; debug!("trans_stmt({})", s.repr(cx.tcx())); + if cx.unreachable.get() { + return cx; + } + if cx.sess().asm_comments() { add_span_comment(cx, s.span, &s.repr(cx.tcx())); } @@ -76,6 +80,11 @@ pub fn trans_stmt<'blk, 'tcx>(cx: Block<'blk, 'tcx>, pub fn trans_stmt_semi<'blk, 'tcx>(cx: Block<'blk, 'tcx>, e: &ast::Expr) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_stmt_semi"); + + if cx.unreachable.get() { + return cx; + } + let ty = expr_ty(cx, e); if cx.fcx.type_needs_drop(ty) { expr::trans_to_lvalue(cx, e, "stmt").bcx @@ -89,6 +98,11 @@ pub fn trans_block<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, mut dest: expr::Dest) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_block"); + + if bcx.unreachable.get() { + return bcx; + } + let fcx = bcx.fcx; let mut bcx = bcx; @@ -141,6 +155,11 @@ pub fn trans_if<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, bcx.to_str(), if_id, bcx.expr_to_string(cond), thn.id, dest.to_string(bcx.ccx())); let _icx = push_ctxt("trans_if"); + + if bcx.unreachable.get() { + return bcx; + } + let mut bcx = bcx; let cond_val = unpack_result!(bcx, expr::trans(bcx, cond).to_llbool()); @@ -214,6 +233,11 @@ pub fn trans_while<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, body: &ast::Block) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_while"); + + if bcx.unreachable.get() { + return bcx; + } + let fcx = bcx.fcx; // bcx @@ -257,6 +281,11 @@ pub fn trans_loop<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, body: &ast::Block) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_loop"); + + if bcx.unreachable.get() { + return bcx; + } + let fcx = bcx.fcx; // bcx @@ -296,12 +325,13 @@ pub fn trans_break_cont<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, exit: uint) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_break_cont"); - let fcx = bcx.fcx; if bcx.unreachable.get() { return bcx; } + let fcx = bcx.fcx; + // Locate loop that we will break to let loop_id = match opt_label { None => fcx.top_loop_scope(), @@ -341,6 +371,11 @@ pub fn trans_ret<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, retval_expr: Option<&ast::Expr>) -> Block<'blk, 'tcx> { let _icx = push_ctxt("trans_ret"); + + if bcx.unreachable.get() { + return bcx; + } + let fcx = bcx.fcx; let mut bcx = bcx; let dest = match (fcx.llretslotptr.get(), retval_expr) { @@ -372,6 +407,10 @@ pub fn trans_fail<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, let ccx = bcx.ccx(); let _icx = push_ctxt("trans_fail_value"); + if bcx.unreachable.get() { + return bcx; + } + let v_str = C_str_slice(ccx, fail_str); let loc = bcx.sess().codemap().lookup_char_pos(call_info.span.lo); let filename = token::intern_and_get_ident(&loc.file.name); @@ -399,6 +438,10 @@ pub fn trans_fail_bounds_check<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, let ccx = bcx.ccx(); let _icx = push_ctxt("trans_fail_bounds_check"); + if bcx.unreachable.get() { + return bcx; + } + // Extract the file/line from the span let loc = bcx.sess().codemap().lookup_char_pos(call_info.span.lo); let filename = token::intern_and_get_ident(&loc.file.name); diff --git a/src/test/debuginfo/unreachable-locals.rs b/src/test/debuginfo/unreachable-locals.rs index 309848d6cedc9..63536b1383475 100644 --- a/src/test/debuginfo/unreachable-locals.rs +++ b/src/test/debuginfo/unreachable-locals.rs @@ -26,6 +26,22 @@ fn after_return() { (a, ref b) => {} } for a in &[111i32] {} + let test = if some_predicate() { 1 } else { 2 }; + while some_predicate() { + let abc = !some_predicate(); + } + loop { + let abc = !some_predicate(); + break; + } + // nested block + { + let abc = !some_predicate(); + + { + let def = !some_predicate(); + } + } } fn after_panic() { @@ -36,6 +52,22 @@ fn after_panic() { (a, ref b) => {} } for a in &[111i32] {} + let test = if some_predicate() { 1 } else { 2 }; + while some_predicate() { + let abc = !some_predicate(); + } + loop { + let abc = !some_predicate(); + break; + } + // nested block + { + let abc = !some_predicate(); + + { + let def = !some_predicate(); + } + } } fn after_diverging_function() { @@ -46,6 +78,22 @@ fn after_diverging_function() { (a, ref b) => {} } for a in &[111i32] {} + let test = if some_predicate() { 1 } else { 2 }; + while some_predicate() { + let abc = !some_predicate(); + } + loop { + let abc = !some_predicate(); + break; + } + // nested block + { + let abc = !some_predicate(); + + { + let def = !some_predicate(); + } + } } fn after_break() { @@ -57,18 +105,50 @@ fn after_break() { (a, ref b) => {} } for a in &[111i32] {} + let test = if some_predicate() { 1 } else { 2 }; + while some_predicate() { + let abc = !some_predicate(); + } + loop { + let abc = !some_predicate(); + break; + } + // nested block + { + let abc = !some_predicate(); + + { + let def = !some_predicate(); + } + } } } fn after_continue() { for _ in 0..10i32 { - break; + continue; let x = "0"; let (ref y,z) = (1i32, 2u32); match (20i32, 'c') { (a, ref b) => {} } for a in &[111i32] {} + let test = if some_predicate() { 1 } else { 2 }; + while some_predicate() { + let abc = !some_predicate(); + } + loop { + let abc = !some_predicate(); + break; + } + // nested block + { + let abc = !some_predicate(); + + { + let def = !some_predicate(); + } + } } } @@ -83,3 +163,6 @@ fn main() { fn diverge() -> ! { panic!(); } + +fn some_predicate() -> bool { true || false } +