@@ -10,82 +10,90 @@ use rustc_span::symbol::Ident;
10
10
use rustc_span:: { source_map:: Spanned , Span } ;
11
11
12
12
impl < ' a , ' hir > LoweringContext < ' a , ' hir > {
13
- crate fn lower_pat ( & mut self , p : & Pat ) -> & ' hir hir:: Pat < ' hir > {
13
+ crate fn lower_pat ( & mut self , mut pattern : & Pat ) -> & ' hir hir:: Pat < ' hir > {
14
14
ensure_sufficient_stack ( || {
15
- let node = match p. kind {
16
- PatKind :: Wild => hir:: PatKind :: Wild ,
17
- PatKind :: Ident ( ref binding_mode, ident, ref sub) => {
18
- let lower_sub = |this : & mut Self | sub. as_ref ( ) . map ( |s| this. lower_pat ( & * s) ) ;
19
- let node = self . lower_pat_ident ( p, binding_mode, ident, lower_sub) ;
20
- node
21
- }
22
- PatKind :: Lit ( ref e) => hir:: PatKind :: Lit ( self . lower_expr ( e) ) ,
23
- PatKind :: TupleStruct ( ref path, ref pats) => {
24
- let qpath = self . lower_qpath (
25
- p. id ,
26
- & None ,
27
- path,
28
- ParamMode :: Optional ,
29
- ImplTraitContext :: disallowed ( ) ,
30
- ) ;
31
- let ( pats, ddpos) = self . lower_pat_tuple ( pats, "tuple struct" ) ;
32
- hir:: PatKind :: TupleStruct ( qpath, pats, ddpos)
33
- }
34
- PatKind :: Or ( ref pats) => hir:: PatKind :: Or (
35
- self . arena . alloc_from_iter ( pats. iter ( ) . map ( |x| self . lower_pat ( x) ) ) ,
36
- ) ,
37
- PatKind :: Path ( ref qself, ref path) => {
38
- let qpath = self . lower_qpath (
39
- p. id ,
40
- qself,
41
- path,
42
- ParamMode :: Optional ,
43
- ImplTraitContext :: disallowed ( ) ,
44
- ) ;
45
- hir:: PatKind :: Path ( qpath)
46
- }
47
- PatKind :: Struct ( ref path, ref fields, etc) => {
48
- let qpath = self . lower_qpath (
49
- p. id ,
50
- & None ,
51
- path,
52
- ParamMode :: Optional ,
53
- ImplTraitContext :: disallowed ( ) ,
54
- ) ;
15
+ // loop here to avoid recursion
16
+ let node = loop {
17
+ match pattern. kind {
18
+ PatKind :: Wild => break hir:: PatKind :: Wild ,
19
+ PatKind :: Ident ( ref binding_mode, ident, ref sub) => {
20
+ let lower_sub = |this : & mut Self | sub. as_ref ( ) . map ( |s| this. lower_pat ( & * s) ) ;
21
+ break self . lower_pat_ident ( pattern, binding_mode, ident, lower_sub) ;
22
+ }
23
+ PatKind :: Lit ( ref e) => break hir:: PatKind :: Lit ( self . lower_expr ( e) ) ,
24
+ PatKind :: TupleStruct ( ref path, ref pats) => {
25
+ let qpath = self . lower_qpath (
26
+ pattern. id ,
27
+ & None ,
28
+ path,
29
+ ParamMode :: Optional ,
30
+ ImplTraitContext :: disallowed ( ) ,
31
+ ) ;
32
+ let ( pats, ddpos) = self . lower_pat_tuple ( pats, "tuple struct" ) ;
33
+ break hir:: PatKind :: TupleStruct ( qpath, pats, ddpos) ;
34
+ }
35
+ PatKind :: Or ( ref pats) => {
36
+ break hir:: PatKind :: Or (
37
+ self . arena . alloc_from_iter ( pats. iter ( ) . map ( |x| self . lower_pat ( x) ) ) ,
38
+ ) ;
39
+ }
40
+ PatKind :: Path ( ref qself, ref path) => {
41
+ let qpath = self . lower_qpath (
42
+ pattern. id ,
43
+ qself,
44
+ path,
45
+ ParamMode :: Optional ,
46
+ ImplTraitContext :: disallowed ( ) ,
47
+ ) ;
48
+ break hir:: PatKind :: Path ( qpath) ;
49
+ }
50
+ PatKind :: Struct ( ref path, ref fields, etc) => {
51
+ let qpath = self . lower_qpath (
52
+ pattern. id ,
53
+ & None ,
54
+ path,
55
+ ParamMode :: Optional ,
56
+ ImplTraitContext :: disallowed ( ) ,
57
+ ) ;
55
58
56
- let fs = self . arena . alloc_from_iter ( fields. iter ( ) . map ( |f| hir:: FieldPat {
57
- hir_id : self . next_id ( ) ,
58
- ident : f. ident ,
59
- pat : self . lower_pat ( & f. pat ) ,
60
- is_shorthand : f. is_shorthand ,
61
- span : f. span ,
62
- } ) ) ;
63
- hir:: PatKind :: Struct ( qpath, fs, etc)
64
- }
65
- PatKind :: Tuple ( ref pats) => {
66
- let ( pats, ddpos) = self . lower_pat_tuple ( pats, "tuple" ) ;
67
- hir:: PatKind :: Tuple ( pats, ddpos)
68
- }
69
- PatKind :: Box ( ref inner) => hir:: PatKind :: Box ( self . lower_pat ( inner) ) ,
70
- PatKind :: Ref ( ref inner, mutbl) => hir:: PatKind :: Ref ( self . lower_pat ( inner) , mutbl) ,
71
- PatKind :: Range ( ref e1, ref e2, Spanned { node : ref end, .. } ) => {
72
- hir:: PatKind :: Range (
73
- e1. as_deref ( ) . map ( |e| self . lower_expr ( e) ) ,
74
- e2. as_deref ( ) . map ( |e| self . lower_expr ( e) ) ,
75
- self . lower_range_end ( end, e2. is_some ( ) ) ,
76
- )
77
- }
78
- PatKind :: Slice ( ref pats) => self . lower_pat_slice ( pats) ,
79
- PatKind :: Rest => {
80
- // If we reach here the `..` pattern is not semantically allowed.
81
- self . ban_illegal_rest_pat ( p. span )
59
+ let fs = self . arena . alloc_from_iter ( fields. iter ( ) . map ( |f| hir:: FieldPat {
60
+ hir_id : self . next_id ( ) ,
61
+ ident : f. ident ,
62
+ pat : self . lower_pat ( & f. pat ) ,
63
+ is_shorthand : f. is_shorthand ,
64
+ span : f. span ,
65
+ } ) ) ;
66
+ break hir:: PatKind :: Struct ( qpath, fs, etc) ;
67
+ }
68
+ PatKind :: Tuple ( ref pats) => {
69
+ let ( pats, ddpos) = self . lower_pat_tuple ( pats, "tuple" ) ;
70
+ break hir:: PatKind :: Tuple ( pats, ddpos) ;
71
+ }
72
+ PatKind :: Box ( ref inner) => {
73
+ break hir:: PatKind :: Box ( self . lower_pat ( inner) ) ;
74
+ }
75
+ PatKind :: Ref ( ref inner, mutbl) => {
76
+ break hir:: PatKind :: Ref ( self . lower_pat ( inner) , mutbl) ;
77
+ }
78
+ PatKind :: Range ( ref e1, ref e2, Spanned { node : ref end, .. } ) => {
79
+ break hir:: PatKind :: Range (
80
+ e1. as_deref ( ) . map ( |e| self . lower_expr ( e) ) ,
81
+ e2. as_deref ( ) . map ( |e| self . lower_expr ( e) ) ,
82
+ self . lower_range_end ( end, e2. is_some ( ) ) ,
83
+ ) ;
84
+ }
85
+ PatKind :: Slice ( ref pats) => break self . lower_pat_slice ( pats) ,
86
+ PatKind :: Rest => {
87
+ // If we reach here the `..` pattern is not semantically allowed.
88
+ break self . ban_illegal_rest_pat ( pattern. span ) ;
89
+ }
90
+ // return inner to be processed in next loop
91
+ PatKind :: Paren ( ref inner) => pattern = inner,
92
+ PatKind :: MacCall ( _) => panic ! ( "{:?} shouldn't exist here" , pattern. span) ,
82
93
}
83
- // FIXME: consider not using recursion to lower this.
84
- PatKind :: Paren ( ref inner) => return self . lower_pat ( inner) ,
85
- PatKind :: MacCall ( _) => panic ! ( "{:?} shouldn't exist here" , p. span) ,
86
94
} ;
87
95
88
- self . pat_with_node_id_of ( p , node)
96
+ self . pat_with_node_id_of ( pattern , node)
89
97
} )
90
98
}
91
99
0 commit comments