@@ -87,16 +87,15 @@ impl<'a> InferenceContext<'a> {
87
87
let expected = & expected. adjust_for_branches ( & mut self . table ) ;
88
88
self . infer_expr (
89
89
condition,
90
- & Expectation :: has_type ( TyKind :: Scalar ( Scalar :: Bool ) . intern ( Interner ) ) ,
90
+ & Expectation :: HasType ( self . result . standard_types . bool_ . clone ( ) ) ,
91
91
) ;
92
92
93
93
let condition_diverges = mem:: replace ( & mut self . diverges , Diverges :: Maybe ) ;
94
94
let mut both_arms_diverge = Diverges :: Always ;
95
95
96
- let result_ty = self . table . new_type_var ( ) ;
97
96
let then_ty = self . infer_expr_inner ( then_branch, expected) ;
98
97
both_arms_diverge &= mem:: replace ( & mut self . diverges , Diverges :: Maybe ) ;
99
- let mut coerce = CoerceMany :: new ( result_ty ) ;
98
+ let mut coerce = CoerceMany :: new ( expected . coercion_target_type ( & mut self . table ) ) ;
100
99
coerce. coerce ( self , Some ( then_branch) , & then_ty) ;
101
100
let else_ty = match else_branch {
102
101
Some ( else_branch) => self . infer_expr_inner ( else_branch, expected) ,
@@ -113,7 +112,7 @@ impl<'a> InferenceContext<'a> {
113
112
& Expr :: Let { pat, expr } => {
114
113
let input_ty = self . infer_expr ( expr, & Expectation :: none ( ) ) ;
115
114
self . infer_pat ( pat, & input_ty, BindingMode :: default ( ) ) ;
116
- TyKind :: Scalar ( Scalar :: Bool ) . intern ( Interner )
115
+ self . result . standard_types . bool_ . clone ( )
117
116
}
118
117
Expr :: Block { statements, tail, label, id : _ } => {
119
118
let old_resolver = mem:: replace (
@@ -188,27 +187,29 @@ impl<'a> InferenceContext<'a> {
188
187
. intern ( Interner )
189
188
}
190
189
& Expr :: Loop { body, label } => {
190
+ // FIXME: should be:
191
+ // let ty = expected.coercion_target_type(&mut self.table);
191
192
let ty = self . table . new_type_var ( ) ;
192
193
let ( breaks, ( ) ) =
193
194
self . with_breakable_ctx ( BreakableKind :: Loop , ty, label, |this| {
194
- this. infer_expr ( body, & Expectation :: has_type ( TyBuilder :: unit ( ) ) ) ;
195
+ this. infer_expr ( body, & Expectation :: HasType ( TyBuilder :: unit ( ) ) ) ;
195
196
} ) ;
196
197
197
198
match breaks {
198
199
Some ( breaks) => {
199
200
self . diverges = Diverges :: Maybe ;
200
201
breaks
201
202
}
202
- None => TyKind :: Never . intern ( Interner ) ,
203
+ None => self . result . standard_types . never . clone ( ) ,
203
204
}
204
205
}
205
206
& Expr :: While { condition, body, label } => {
206
207
self . with_breakable_ctx ( BreakableKind :: Loop , self . err_ty ( ) , label, |this| {
207
208
this. infer_expr (
208
209
condition,
209
- & Expectation :: has_type ( TyKind :: Scalar ( Scalar :: Bool ) . intern ( Interner ) ) ,
210
+ & Expectation :: HasType ( this . result . standard_types . bool_ . clone ( ) ) ,
210
211
) ;
211
- this. infer_expr ( body, & Expectation :: has_type ( TyBuilder :: unit ( ) ) ) ;
212
+ this. infer_expr ( body, & Expectation :: HasType ( TyBuilder :: unit ( ) ) ) ;
212
213
} ) ;
213
214
214
215
// the body may not run, so it diverging doesn't mean we diverge
@@ -224,7 +225,7 @@ impl<'a> InferenceContext<'a> {
224
225
225
226
self . infer_pat ( pat, & pat_ty, BindingMode :: default ( ) ) ;
226
227
self . with_breakable_ctx ( BreakableKind :: Loop , self . err_ty ( ) , label, |this| {
227
- this. infer_expr ( body, & Expectation :: has_type ( TyBuilder :: unit ( ) ) ) ;
228
+ this. infer_expr ( body, & Expectation :: HasType ( TyBuilder :: unit ( ) ) ) ;
228
229
} ) ;
229
230
230
231
// the body may not run, so it diverging doesn't mean we diverge
@@ -234,7 +235,7 @@ impl<'a> InferenceContext<'a> {
234
235
Expr :: Closure { body, args, ret_type, arg_types, closure_kind } => {
235
236
assert_eq ! ( args. len( ) , arg_types. len( ) ) ;
236
237
237
- let mut sig_tys = Vec :: new ( ) ;
238
+ let mut sig_tys = Vec :: with_capacity ( arg_types . len ( ) + 1 ) ;
238
239
239
240
// collect explicitly written argument types
240
241
for arg_type in arg_types. iter ( ) {
@@ -255,7 +256,8 @@ impl<'a> InferenceContext<'a> {
255
256
num_binders : 0 ,
256
257
sig : FnSig { abi : ( ) , safety : chalk_ir:: Safety :: Safe , variadic : false } ,
257
258
substitution : FnSubst (
258
- Substitution :: from_iter ( Interner , sig_tys. clone ( ) ) . shifted_in ( Interner ) ,
259
+ Substitution :: from_iter ( Interner , sig_tys. iter ( ) . cloned ( ) )
260
+ . shifted_in ( Interner ) ,
259
261
) ,
260
262
} )
261
263
. intern ( Interner ) ;
@@ -317,16 +319,16 @@ impl<'a> InferenceContext<'a> {
317
319
Expr :: Call { callee, args, .. } => {
318
320
let callee_ty = self . infer_expr ( * callee, & Expectation :: none ( ) ) ;
319
321
let mut derefs = Autoderef :: new ( & mut self . table , callee_ty. clone ( ) ) ;
320
- let mut res = None ;
321
- let mut derefed_callee = callee_ty. clone ( ) ;
322
- // manual loop to be able to access `derefs.table`
323
- while let Some ( ( callee_deref_ty, _) ) = derefs. next ( ) {
324
- res = derefs. table . callable_sig ( & callee_deref_ty, args. len ( ) ) ;
325
- if res. is_some ( ) {
326
- derefed_callee = callee_deref_ty;
327
- break ;
322
+ let ( res, derefed_callee) = ' b: {
323
+ // manual loop to be able to access `derefs.table`
324
+ while let Some ( ( callee_deref_ty, _) ) = derefs. next ( ) {
325
+ let res = derefs. table . callable_sig ( & callee_deref_ty, args. len ( ) ) ;
326
+ if res. is_some ( ) {
327
+ break ' b ( res, callee_deref_ty) ;
328
+ }
328
329
}
329
- }
330
+ ( None , callee_ty. clone ( ) )
331
+ } ;
330
332
// if the function is unresolved, we use is_varargs=true to
331
333
// suppress the arg count diagnostic here
332
334
let is_varargs =
@@ -382,12 +384,9 @@ impl<'a> InferenceContext<'a> {
382
384
let expected = expected. adjust_for_branches ( & mut self . table ) ;
383
385
384
386
let result_ty = if arms. is_empty ( ) {
385
- TyKind :: Never . intern ( Interner )
387
+ self . result . standard_types . never . clone ( )
386
388
} else {
387
- match & expected {
388
- Expectation :: HasType ( ty) => ty. clone ( ) ,
389
- _ => self . table . new_type_var ( ) ,
390
- }
389
+ expected. coercion_target_type ( & mut self . table )
391
390
} ;
392
391
let mut coerce = CoerceMany :: new ( result_ty) ;
393
392
@@ -400,7 +399,7 @@ impl<'a> InferenceContext<'a> {
400
399
if let Some ( guard_expr) = arm. guard {
401
400
self . infer_expr (
402
401
guard_expr,
403
- & Expectation :: has_type ( TyKind :: Scalar ( Scalar :: Bool ) . intern ( Interner ) ) ,
402
+ & Expectation :: HasType ( self . result . standard_types . bool_ . clone ( ) ) ,
404
403
) ;
405
404
}
406
405
@@ -425,7 +424,7 @@ impl<'a> InferenceContext<'a> {
425
424
is_break : false ,
426
425
} ) ;
427
426
} ;
428
- TyKind :: Never . intern ( Interner )
427
+ self . result . standard_types . never . clone ( )
429
428
}
430
429
Expr :: Break { expr, label } => {
431
430
let val_ty = if let Some ( expr) = * expr {
@@ -439,7 +438,7 @@ impl<'a> InferenceContext<'a> {
439
438
// avoiding the borrowck
440
439
let mut coerce = mem:: replace (
441
440
& mut ctxt. coerce ,
442
- CoerceMany :: new ( self . result . standard_types . unknown . clone ( ) ) ,
441
+ CoerceMany :: new ( expected . coercion_target_type ( & mut self . table ) ) ,
443
442
) ;
444
443
445
444
// FIXME: create a synthetic `()` during lowering so we have something to refer to here?
@@ -457,7 +456,7 @@ impl<'a> InferenceContext<'a> {
457
456
} ) ;
458
457
}
459
458
}
460
- TyKind :: Never . intern ( Interner )
459
+ self . result . standard_types . never . clone ( )
461
460
}
462
461
Expr :: Return { expr } => {
463
462
if let Some ( expr) = expr {
@@ -466,7 +465,7 @@ impl<'a> InferenceContext<'a> {
466
465
let unit = TyBuilder :: unit ( ) ;
467
466
let _ = self . coerce ( Some ( tgt_expr) , & unit, & self . return_ty . clone ( ) ) ;
468
467
}
469
- TyKind :: Never . intern ( Interner )
468
+ self . result . standard_types . never . clone ( )
470
469
}
471
470
Expr :: Yield { expr } => {
472
471
if let Some ( ( resume_ty, yield_ty) ) = self . resume_yield_tys . clone ( ) {
@@ -479,14 +478,14 @@ impl<'a> InferenceContext<'a> {
479
478
resume_ty
480
479
} else {
481
480
// FIXME: report error (yield expr in non-generator)
482
- TyKind :: Error . intern ( Interner )
481
+ self . result . standard_types . unknown . clone ( )
483
482
}
484
483
}
485
484
Expr :: Yeet { expr } => {
486
485
if let & Some ( expr) = expr {
487
486
self . infer_expr_inner ( expr, & Expectation :: None ) ;
488
487
}
489
- TyKind :: Never . intern ( Interner )
488
+ self . result . standard_types . never . clone ( )
490
489
}
491
490
Expr :: RecordLit { path, fields, spread, .. } => {
492
491
let ( ty, def_id) = self . resolve_variant ( path. as_deref ( ) , false ) ;
@@ -611,8 +610,8 @@ impl<'a> InferenceContext<'a> {
611
610
}
612
611
Expr :: Cast { expr, type_ref } => {
613
612
let cast_ty = self . make_ty ( type_ref) ;
614
- let _inner_ty =
615
- self . infer_expr_inner ( * expr, & Expectation :: Castable ( cast_ty . clone ( ) ) ) ;
613
+ // FIXME: propagate the "castable to" expectation
614
+ let _inner_ty = self . infer_expr_inner ( * expr, & Expectation :: None ) ;
616
615
// FIXME check the cast...
617
616
cast_ty
618
617
}
@@ -829,7 +828,7 @@ impl<'a> InferenceContext<'a> {
829
828
self . infer_expr_coerce ( initializer, & Expectation :: has_type ( elem_ty) ) ;
830
829
self . infer_expr (
831
830
repeat,
832
- & Expectation :: has_type (
831
+ & Expectation :: HasType (
833
832
TyKind :: Scalar ( Scalar :: Uint ( UintTy :: Usize ) ) . intern ( Interner ) ,
834
833
) ,
835
834
) ;
@@ -852,7 +851,7 @@ impl<'a> InferenceContext<'a> {
852
851
TyKind :: Array ( coerce. complete ( ) , len) . intern ( Interner )
853
852
}
854
853
Expr :: Literal ( lit) => match lit {
855
- Literal :: Bool ( ..) => TyKind :: Scalar ( Scalar :: Bool ) . intern ( Interner ) ,
854
+ Literal :: Bool ( ..) => self . result . standard_types . bool_ . clone ( ) ,
856
855
Literal :: String ( ..) => {
857
856
TyKind :: Ref ( Mutability :: Not , static_lifetime ( ) , TyKind :: Str . intern ( Interner ) )
858
857
. intern ( Interner )
@@ -1148,7 +1147,7 @@ impl<'a> InferenceContext<'a> {
1148
1147
if let Some ( expr) = else_branch {
1149
1148
self . infer_expr_coerce (
1150
1149
* expr,
1151
- & Expectation :: has_type ( Ty :: new ( Interner , TyKind :: Never ) ) ,
1150
+ & Expectation :: HasType ( self . result . standard_types . never . clone ( ) ) ,
1152
1151
) ;
1153
1152
}
1154
1153
0 commit comments