@@ -155,12 +155,7 @@ impl MirLowerCtx<'_> {
155
155
if let Some ( p) = self . lower_expr_as_place ( expr_id) {
156
156
return Ok ( ( p, prev_block) ) ;
157
157
}
158
- let mut ty = self . expr_ty ( expr_id) ;
159
- if let Some ( x) = self . infer . expr_adjustments . get ( & expr_id) {
160
- if let Some ( x) = x. last ( ) {
161
- ty = x. target . clone ( ) ;
162
- }
163
- }
158
+ let ty = self . expr_ty_after_adjustments ( expr_id) ;
164
159
let place = self . temp ( ty) ?;
165
160
Ok ( ( place. into ( ) , self . lower_expr_to_place ( expr_id, place. into ( ) , prev_block) ?) )
166
161
}
@@ -323,7 +318,7 @@ impl MirLowerCtx<'_> {
323
318
current,
324
319
None ,
325
320
cond_place,
326
- self . expr_ty ( * expr) ,
321
+ self . expr_ty_after_adjustments ( * expr) ,
327
322
* pat,
328
323
BindingAnnotation :: Unannotated ,
329
324
) ?;
@@ -339,7 +334,53 @@ impl MirLowerCtx<'_> {
339
334
self . lower_block_to_place ( None , statements, current, * tail, place)
340
335
}
341
336
Expr :: Block { id : _, statements, tail, label } => {
342
- self . lower_block_to_place ( * label, statements, current, * tail, place)
337
+ if label. is_some ( ) {
338
+ not_supported ! ( "block with label" ) ;
339
+ }
340
+ for statement in statements. iter ( ) {
341
+ match statement {
342
+ hir_def:: expr:: Statement :: Let {
343
+ pat,
344
+ initializer,
345
+ else_branch,
346
+ type_ref : _,
347
+ } => match initializer {
348
+ Some ( expr_id) => {
349
+ let else_block;
350
+ let init_place;
351
+ ( init_place, current) =
352
+ self . lower_expr_to_some_place ( * expr_id, current) ?;
353
+ ( current, else_block) = self . pattern_match (
354
+ current,
355
+ None ,
356
+ init_place,
357
+ self . expr_ty_after_adjustments ( * expr_id) ,
358
+ * pat,
359
+ BindingAnnotation :: Unannotated ,
360
+ ) ?;
361
+ match ( else_block, else_branch) {
362
+ ( None , _) => ( ) ,
363
+ ( Some ( else_block) , None ) => {
364
+ self . set_terminator ( else_block, Terminator :: Unreachable ) ;
365
+ }
366
+ ( Some ( else_block) , Some ( else_branch) ) => {
367
+ let ( _, b) = self
368
+ . lower_expr_to_some_place ( * else_branch, else_block) ?;
369
+ self . set_terminator ( b, Terminator :: Unreachable ) ;
370
+ }
371
+ }
372
+ }
373
+ None => continue ,
374
+ } ,
375
+ hir_def:: expr:: Statement :: Expr { expr, has_semi : _ } => {
376
+ ( _, current) = self . lower_expr_to_some_place ( * expr, current) ?;
377
+ }
378
+ }
379
+ }
380
+ match tail {
381
+ Some ( tail) => self . lower_expr_to_place ( * tail, place, current) ,
382
+ None => Ok ( current) ,
383
+ }
343
384
}
344
385
Expr :: Loop { body, label } => self . lower_loop ( current, * label, |this, begin, _| {
345
386
let ( _, block) = this. lower_expr_to_some_place ( * body, begin) ?;
@@ -364,7 +405,7 @@ impl MirLowerCtx<'_> {
364
405
}
365
406
Expr :: For { .. } => not_supported ! ( "for loop" ) ,
366
407
Expr :: Call { callee, args, .. } => {
367
- let callee_ty = self . expr_ty ( * callee) ;
408
+ let callee_ty = self . expr_ty_after_adjustments ( * callee) ;
368
409
match & callee_ty. data ( Interner ) . kind {
369
410
chalk_ir:: TyKind :: FnDef ( ..) => {
370
411
let func = Operand :: from_bytes ( vec ! [ ] , callee_ty. clone ( ) ) ;
@@ -414,7 +455,7 @@ impl MirLowerCtx<'_> {
414
455
}
415
456
Expr :: Match { expr, arms } => {
416
457
let ( cond_place, mut current) = self . lower_expr_to_some_place ( * expr, current) ?;
417
- let cond_ty = self . expr_ty ( * expr) ;
458
+ let cond_ty = self . expr_ty_after_adjustments ( * expr) ;
418
459
let end = self . new_basic_block ( ) ;
419
460
for MatchArm { pat, guard, expr } in arms. iter ( ) {
420
461
if guard. is_some ( ) {
@@ -524,7 +565,7 @@ impl MirLowerCtx<'_> {
524
565
}
525
566
Expr :: Field { expr, name } => {
526
567
let ( mut current_place, current) = self . lower_expr_to_some_place ( * expr, current) ?;
527
- if let TyKind :: Tuple ( ..) = self . expr_ty ( * expr) . kind ( Interner ) {
568
+ if let TyKind :: Tuple ( ..) = self . expr_ty_after_adjustments ( * expr) . kind ( Interner ) {
528
569
let index = name
529
570
. as_tuple_index ( )
530
571
. ok_or ( MirLowerError :: TypeError ( "named field on tuple" ) ) ?;
@@ -623,7 +664,7 @@ impl MirLowerCtx<'_> {
623
664
Expr :: Index { base, index } => {
624
665
let mut p_base;
625
666
( p_base, current) = self . lower_expr_to_some_place ( * base, current) ?;
626
- let l_index = self . temp ( self . expr_ty ( * index) ) ?;
667
+ let l_index = self . temp ( self . expr_ty_after_adjustments ( * index) ) ?;
627
668
current = self . lower_expr_to_place ( * index, l_index. into ( ) , current) ?;
628
669
p_base. projection . push ( ProjectionElem :: Index ( l_index) ) ;
629
670
self . push_assignment ( current, place, Operand :: Copy ( p_base) . into ( ) ) ;
@@ -878,6 +919,16 @@ impl MirLowerCtx<'_> {
878
919
self . infer [ e] . clone ( )
879
920
}
880
921
922
+ fn expr_ty_after_adjustments ( & self , e : ExprId ) -> Ty {
923
+ let mut ty = None ;
924
+ if let Some ( x) = self . infer . expr_adjustments . get ( & e) {
925
+ if let Some ( x) = x. last ( ) {
926
+ ty = Some ( x. target . clone ( ) ) ;
927
+ }
928
+ }
929
+ ty. unwrap_or_else ( || self . expr_ty ( e) )
930
+ }
931
+
881
932
fn push_assignment ( & mut self , block : BasicBlockId , place : Place , rvalue : Rvalue ) {
882
933
self . result . basic_blocks [ block] . statements . push ( Statement :: Assign ( place, rvalue) ) ;
883
934
}
@@ -928,7 +979,25 @@ impl MirLowerCtx<'_> {
928
979
binding_mode,
929
980
) ?
930
981
}
931
- Pat :: Or ( _) => not_supported ! ( "or pattern" ) ,
982
+ Pat :: Or ( pats) => {
983
+ let then_target = self . new_basic_block ( ) ;
984
+ let mut finished = false ;
985
+ for pat in & * * pats {
986
+ let ( next, next_else) =
987
+ self . pattern_match ( current, None , cond_place. clone ( ) , cond_ty. clone ( ) , * pat, binding_mode) ?;
988
+ self . set_goto ( next, then_target) ;
989
+ match next_else {
990
+ Some ( t) => {
991
+ current = t;
992
+ }
993
+ None => {
994
+ finished = true ;
995
+ break ;
996
+ }
997
+ }
998
+ }
999
+ ( then_target, ( !finished) . then_some ( current) )
1000
+ }
932
1001
Pat :: Record { .. } => not_supported ! ( "record pattern" ) ,
933
1002
Pat :: Range { .. } => not_supported ! ( "range pattern" ) ,
934
1003
Pat :: Slice { .. } => not_supported ! ( "slice pattern" ) ,
0 commit comments