@@ -112,7 +112,7 @@ use self::VarKind::*;
112
112
use dep_graph:: DepNode ;
113
113
use hir:: def:: * ;
114
114
use hir:: pat_util;
115
- use ty:: { self , TyCtxt , ParameterEnvironment } ;
115
+ use ty:: { self , Ty , TyCtxt , ParameterEnvironment } ;
116
116
use traits:: { self , Reveal } ;
117
117
use ty:: subst:: Subst ;
118
118
use lint;
@@ -1111,8 +1111,9 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
1111
1111
}
1112
1112
1113
1113
hir:: ExprCall ( ref f, ref args) => {
1114
+ // FIXME(canndrew): This is_never should really be an is_uninhabited
1114
1115
let diverges = !self . ir . tcx . is_method_call ( expr. id ) &&
1115
- self . ir . tcx . expr_ty_adjusted ( & f) . fn_ret ( ) . diverges ( ) ;
1116
+ self . ir . tcx . expr_ty_adjusted ( & f) . fn_ret ( ) . 0 . is_never ( ) ;
1116
1117
let succ = if diverges {
1117
1118
self . s . exit_ln
1118
1119
} else {
@@ -1125,7 +1126,8 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
1125
1126
hir:: ExprMethodCall ( _, _, ref args) => {
1126
1127
let method_call = ty:: MethodCall :: expr ( expr. id ) ;
1127
1128
let method_ty = self . ir . tcx . tables . borrow ( ) . method_map [ & method_call] . ty ;
1128
- let succ = if method_ty. fn_ret ( ) . diverges ( ) {
1129
+ // FIXME(canndrew): This is_never should really be an is_uninhabited
1130
+ let succ = if method_ty. fn_ret ( ) . 0 . is_never ( ) {
1129
1131
self . s . exit_ln
1130
1132
} else {
1131
1133
succ
@@ -1454,7 +1456,7 @@ fn check_fn(_v: &Liveness,
1454
1456
}
1455
1457
1456
1458
impl < ' a , ' tcx > Liveness < ' a , ' tcx > {
1457
- fn fn_ret ( & self , id : NodeId ) -> ty:: PolyFnOutput < ' tcx > {
1459
+ fn fn_ret ( & self , id : NodeId ) -> ty:: Binder < Ty < ' tcx > > {
1458
1460
let fn_ty = self . ir . tcx . node_id_to_type ( id) ;
1459
1461
match fn_ty. sty {
1460
1462
ty:: TyClosure ( closure_def_id, substs) =>
@@ -1477,55 +1479,44 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
1477
1479
self . ir . tcx . region_maps . call_site_extent ( id, body. id ) ,
1478
1480
& self . fn_ret ( id) ) ;
1479
1481
1480
- match fn_ret {
1481
- ty:: FnConverging ( t_ret)
1482
- if self . live_on_entry ( entry_ln, self . s . no_ret_var ) . is_some ( ) => {
1483
-
1484
- let param_env = ParameterEnvironment :: for_item ( self . ir . tcx , id) ;
1485
- let t_ret_subst = t_ret. subst ( self . ir . tcx , & param_env. free_substs ) ;
1486
- let is_nil = self . ir . tcx . infer_ctxt ( None , Some ( param_env) ,
1487
- Reveal :: All ) . enter ( |infcx| {
1488
- let cause = traits:: ObligationCause :: dummy ( ) ;
1489
- traits:: fully_normalize ( & infcx, cause, & t_ret_subst) . unwrap ( ) . is_nil ( )
1490
- } ) ;
1491
-
1492
- // for nil return types, it is ok to not return a value expl.
1493
- if !is_nil {
1494
- let ends_with_stmt = match body. expr {
1495
- None if !body. stmts . is_empty ( ) =>
1496
- match body. stmts . last ( ) . unwrap ( ) . node {
1497
- hir:: StmtSemi ( ref e, _) => {
1498
- self . ir . tcx . expr_ty ( & e) == t_ret
1499
- } ,
1500
- _ => false
1482
+ if self . live_on_entry ( entry_ln, self . s . no_ret_var ) . is_some ( ) {
1483
+ let param_env = ParameterEnvironment :: for_item ( self . ir . tcx , id) ;
1484
+ let t_ret_subst = fn_ret. subst ( self . ir . tcx , & param_env. free_substs ) ;
1485
+ let is_nil = self . ir . tcx . infer_ctxt ( None , Some ( param_env) ,
1486
+ Reveal :: All ) . enter ( |infcx| {
1487
+ let cause = traits:: ObligationCause :: dummy ( ) ;
1488
+ traits:: fully_normalize ( & infcx, cause, & t_ret_subst) . unwrap ( ) . is_nil ( )
1489
+ } ) ;
1490
+
1491
+ // for nil return types, it is ok to not return a value expl.
1492
+ if !is_nil {
1493
+ let ends_with_stmt = match body. expr {
1494
+ None if !body. stmts . is_empty ( ) =>
1495
+ match body. stmts . last ( ) . unwrap ( ) . node {
1496
+ hir:: StmtSemi ( ref e, _) => {
1497
+ self . ir . tcx . expr_ty ( & e) == fn_ret
1501
1498
} ,
1502
- _ => false
1499
+ _ => false
1500
+ } ,
1501
+ _ => false
1502
+ } ;
1503
+ let mut err = struct_span_err ! ( self . ir. tcx. sess,
1504
+ sp,
1505
+ E0269 ,
1506
+ "not all control paths return a value" ) ;
1507
+ if ends_with_stmt {
1508
+ let last_stmt = body. stmts . last ( ) . unwrap ( ) ;
1509
+ let original_span = original_sp ( self . ir . tcx . sess . codemap ( ) ,
1510
+ last_stmt. span , sp) ;
1511
+ let span_semicolon = Span {
1512
+ lo : original_span. hi - BytePos ( 1 ) ,
1513
+ hi : original_span. hi ,
1514
+ expn_id : original_span. expn_id
1503
1515
} ;
1504
- let mut err = struct_span_err ! ( self . ir. tcx. sess,
1505
- sp,
1506
- E0269 ,
1507
- "not all control paths return a value" ) ;
1508
- if ends_with_stmt {
1509
- let last_stmt = body. stmts . last ( ) . unwrap ( ) ;
1510
- let original_span = original_sp ( self . ir . tcx . sess . codemap ( ) ,
1511
- last_stmt. span , sp) ;
1512
- let span_semicolon = Span {
1513
- lo : original_span. hi - BytePos ( 1 ) ,
1514
- hi : original_span. hi ,
1515
- expn_id : original_span. expn_id
1516
- } ;
1517
- err. span_help ( span_semicolon, "consider removing this semicolon:" ) ;
1518
- }
1519
- err. emit ( ) ;
1516
+ err. span_help ( span_semicolon, "consider removing this semicolon:" ) ;
1520
1517
}
1518
+ err. emit ( ) ;
1521
1519
}
1522
- ty:: FnDiverging
1523
- if self . live_on_entry ( entry_ln, self . s . clean_exit_var ) . is_some ( ) => {
1524
- span_err ! ( self . ir. tcx. sess, sp, E0270 ,
1525
- "computation may converge in a function marked as diverging" ) ;
1526
- }
1527
-
1528
- _ => { }
1529
1520
}
1530
1521
}
1531
1522
0 commit comments