@@ -445,6 +445,11 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
445445 fn lower_pattern_unadjusted ( & mut self , pat : & ' tcx hir:: Pat ) -> Pat < ' tcx > {
446446 let mut ty = self . tables . node_type ( pat. hir_id ) ;
447447
448+ if let ty:: Error = ty. kind {
449+ // Avoid ICEs (e.g., #50577 and #50585).
450+ return Pat { span : pat. span , ty, kind : Box :: new ( PatKind :: Wild ) } ;
451+ }
452+
448453 let kind = match pat. kind {
449454 hir:: PatKind :: Wild => PatKind :: Wild ,
450455
@@ -544,57 +549,19 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
544549 }
545550
546551 hir:: PatKind :: Slice ( ref prefix, ref slice, ref suffix) => {
547- match ty. kind {
548- ty:: Ref ( _, ty, _) =>
549- PatKind :: Deref {
550- subpattern : Pat {
551- ty,
552- span : pat. span ,
553- kind : Box :: new ( self . slice_or_array_pattern (
554- pat. span , ty, prefix, slice, suffix) )
555- } ,
556- } ,
557- ty:: Slice ( ..) |
558- ty:: Array ( ..) =>
559- self . slice_or_array_pattern ( pat. span , ty, prefix, slice, suffix) ,
560- ty:: Error => { // Avoid ICE
561- return Pat { span : pat. span , ty, kind : Box :: new ( PatKind :: Wild ) } ;
562- }
563- _ =>
564- span_bug ! (
565- pat. span,
566- "unexpanded type for vector pattern: {:?}" ,
567- ty) ,
568- }
552+ self . slice_or_array_pattern ( pat. span , ty, prefix, slice, suffix)
569553 }
570554
571- hir:: PatKind :: Tuple ( ref subpatterns, ddpos) => {
572- match ty. kind {
573- ty:: Tuple ( ref tys) => {
574- let subpatterns =
575- subpatterns. iter ( )
576- . enumerate_and_adjust ( tys. len ( ) , ddpos)
577- . map ( |( i, subpattern) | FieldPat {
578- field : Field :: new ( i) ,
579- pattern : self . lower_pattern ( subpattern)
580- } )
581- . collect ( ) ;
582-
583- PatKind :: Leaf { subpatterns }
584- }
585- ty:: Error => { // Avoid ICE (#50577)
586- return Pat { span : pat. span , ty, kind : Box :: new ( PatKind :: Wild ) } ;
587- }
555+ hir:: PatKind :: Tuple ( ref pats, ddpos) => {
556+ let tys = match ty. kind {
557+ ty:: Tuple ( ref tys) => tys,
588558 _ => span_bug ! ( pat. span, "unexpected type for tuple pattern: {:?}" , ty) ,
589- }
559+ } ;
560+ let subpatterns = self . lower_tuple_subpats ( pats, tys. len ( ) , ddpos) ;
561+ PatKind :: Leaf { subpatterns }
590562 }
591563
592564 hir:: PatKind :: Binding ( _, id, ident, ref sub) => {
593- let var_ty = self . tables . node_type ( pat. hir_id ) ;
594- if let ty:: Error = var_ty. kind {
595- // Avoid ICE
596- return Pat { span : pat. span , ty, kind : Box :: new ( PatKind :: Wild ) } ;
597- } ;
598565 let bm = * self . tables . pat_binding_modes ( ) . get ( pat. hir_id )
599566 . expect ( "missing binding mode" ) ;
600567 let ( mutability, mode) = match bm {
@@ -609,13 +576,14 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
609576
610577 // A ref x pattern is the same node used for x, and as such it has
611578 // x's type, which is &T, where we want T (the type being matched).
579+ let var_ty = ty;
612580 if let ty:: BindByReference ( _) = bm {
613581 if let ty:: Ref ( _, rty, _) = ty. kind {
614582 ty = rty;
615583 } else {
616584 bug ! ( "`ref {}` has wrong type {}" , ident, ty) ;
617585 }
618- }
586+ } ;
619587
620588 PatKind :: Binding {
621589 mutability,
@@ -627,28 +595,14 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
627595 }
628596 }
629597
630- hir:: PatKind :: TupleStruct ( ref qpath, ref subpatterns , ddpos) => {
598+ hir:: PatKind :: TupleStruct ( ref qpath, ref pats , ddpos) => {
631599 let res = self . tables . qpath_res ( qpath, pat. hir_id ) ;
632600 let adt_def = match ty. kind {
633601 ty:: Adt ( adt_def, _) => adt_def,
634- ty:: Error => { // Avoid ICE (#50585)
635- return Pat { span : pat. span , ty, kind : Box :: new ( PatKind :: Wild ) } ;
636- }
637- _ => span_bug ! ( pat. span,
638- "tuple struct pattern not applied to an ADT {:?}" ,
639- ty) ,
602+ _ => span_bug ! ( pat. span, "tuple struct pattern not applied to an ADT {:?}" , ty) ,
640603 } ;
641604 let variant_def = adt_def. variant_of_res ( res) ;
642-
643- let subpatterns =
644- subpatterns. iter ( )
645- . enumerate_and_adjust ( variant_def. fields . len ( ) , ddpos)
646- . map ( |( i, field) | FieldPat {
647- field : Field :: new ( i) ,
648- pattern : self . lower_pattern ( field) ,
649- } )
650- . collect ( ) ;
651-
605+ let subpatterns = self . lower_tuple_subpats ( pats, variant_def. fields . len ( ) , ddpos) ;
652606 self . lower_variant_or_leaf ( res, pat. hir_id , pat. span , ty, subpatterns)
653607 }
654608
@@ -668,11 +622,7 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
668622 self . lower_variant_or_leaf ( res, pat. hir_id , pat. span , ty, subpatterns)
669623 }
670624
671- hir:: PatKind :: Or ( ref pats) => {
672- PatKind :: Or {
673- pats : pats. iter ( ) . map ( |p| self . lower_pattern ( p) ) . collect ( ) ,
674- }
675- }
625+ hir:: PatKind :: Or ( ref pats) => PatKind :: Or { pats : self . lower_patterns ( pats) } ,
676626 } ;
677627
678628 Pat {
@@ -682,80 +632,50 @@ impl<'a, 'tcx> PatCtxt<'a, 'tcx> {
682632 }
683633 }
684634
635+ fn lower_tuple_subpats (
636+ & mut self ,
637+ pats : & ' tcx [ P < hir:: Pat > ] ,
638+ expected_len : usize ,
639+ gap_pos : Option < usize > ,
640+ ) -> Vec < FieldPat < ' tcx > > {
641+ pats. iter ( )
642+ . enumerate_and_adjust ( expected_len, gap_pos)
643+ . map ( |( i, subpattern) | FieldPat {
644+ field : Field :: new ( i) ,
645+ pattern : self . lower_pattern ( subpattern)
646+ } )
647+ . collect ( )
648+ }
649+
685650 fn lower_patterns ( & mut self , pats : & ' tcx [ P < hir:: Pat > ] ) -> Vec < Pat < ' tcx > > {
686651 pats. iter ( ) . map ( |p| self . lower_pattern ( p) ) . collect ( )
687652 }
688653
689- fn lower_opt_pattern ( & mut self , pat : & ' tcx Option < P < hir:: Pat > > ) -> Option < Pat < ' tcx > >
690- {
654+ fn lower_opt_pattern ( & mut self , pat : & ' tcx Option < P < hir:: Pat > > ) -> Option < Pat < ' tcx > > {
691655 pat. as_ref ( ) . map ( |p| self . lower_pattern ( p) )
692656 }
693657
694- fn flatten_nested_slice_patterns (
695- & mut self ,
696- prefix : Vec < Pat < ' tcx > > ,
697- slice : Option < Pat < ' tcx > > ,
698- suffix : Vec < Pat < ' tcx > > )
699- -> ( Vec < Pat < ' tcx > > , Option < Pat < ' tcx > > , Vec < Pat < ' tcx > > )
700- {
701- let orig_slice = match slice {
702- Some ( orig_slice) => orig_slice,
703- None => return ( prefix, slice, suffix)
704- } ;
705- let orig_prefix = prefix;
706- let orig_suffix = suffix;
707-
708- // dance because of intentional borrow-checker stupidity.
709- let kind = * orig_slice. kind ;
710- match kind {
711- PatKind :: Slice { prefix, slice, mut suffix } |
712- PatKind :: Array { prefix, slice, mut suffix } => {
713- let mut orig_prefix = orig_prefix;
714-
715- orig_prefix. extend ( prefix) ;
716- suffix. extend ( orig_suffix) ;
717-
718- ( orig_prefix, slice, suffix)
719- }
720- _ => {
721- ( orig_prefix, Some ( Pat {
722- kind : box kind, ..orig_slice
723- } ) , orig_suffix)
724- }
725- }
726- }
727-
728658 fn slice_or_array_pattern (
729659 & mut self ,
730660 span : Span ,
731661 ty : Ty < ' tcx > ,
732662 prefix : & ' tcx [ P < hir:: Pat > ] ,
733663 slice : & ' tcx Option < P < hir:: Pat > > ,
734- suffix : & ' tcx [ P < hir:: Pat > ] )
735- -> PatKind < ' tcx >
736- {
664+ suffix : & ' tcx [ P < hir:: Pat > ] ,
665+ ) -> PatKind < ' tcx > {
737666 let prefix = self . lower_patterns ( prefix) ;
738667 let slice = self . lower_opt_pattern ( slice) ;
739668 let suffix = self . lower_patterns ( suffix) ;
740- let ( prefix, slice, suffix) =
741- self . flatten_nested_slice_patterns ( prefix, slice, suffix) ;
742-
743669 match ty. kind {
744- ty:: Slice ( ..) => {
745- // matching a slice or fixed-length array
746- PatKind :: Slice { prefix : prefix, slice : slice, suffix : suffix }
747- }
748-
670+ // Matching a slice, `[T]`.
671+ ty:: Slice ( ..) => PatKind :: Slice { prefix, slice, suffix } ,
672+ // Fixed-length array, `[T; len]`.
749673 ty:: Array ( _, len) => {
750- // fixed-length array
751674 let len = len. eval_usize ( self . tcx , self . param_env ) ;
752675 assert ! ( len >= prefix. len( ) as u64 + suffix. len( ) as u64 ) ;
753- PatKind :: Array { prefix : prefix, slice : slice, suffix : suffix }
754- }
755-
756- _ => {
757- span_bug ! ( span, "bad slice pattern type {:?}" , ty) ;
676+ PatKind :: Array { prefix, slice, suffix }
758677 }
678+ _ => span_bug ! ( span, "bad slice pattern type {:?}" , ty) ,
759679 }
760680 }
761681
0 commit comments