@@ -44,6 +44,8 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
44
44
candidate : & mut Candidate < ' pat , ' tcx > ,
45
45
) -> bool {
46
46
// repeatedly simplify match pairs until fixed point is reached
47
+ debug ! ( "simplify_candidate(candidate={:?})" , candidate) ;
48
+ let mut new_bindings = Vec :: new ( ) ;
47
49
loop {
48
50
let match_pairs = mem:: take ( & mut candidate. match_pairs ) ;
49
51
@@ -56,7 +58,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
56
58
57
59
let mut changed = false ;
58
60
for match_pair in match_pairs {
59
- match self . simplify_match_pair ( match_pair, candidate) {
61
+ match self . simplify_match_pair ( match_pair, candidate, & mut new_bindings ) {
60
62
Ok ( ( ) ) => {
61
63
changed = true ;
62
64
}
@@ -65,13 +67,31 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
65
67
}
66
68
}
67
69
}
70
+ // issue #69971: the binding order should be right to left if there are more
71
+ // bindings after `@` to please the borrow checker
72
+ // Ex
73
+ // struct NonCopyStruct {
74
+ // copy_field: u32,
75
+ // }
76
+ //
77
+ // fn foo1(x: NonCopyStruct) {
78
+ // let y @ NonCopyStruct { copy_field: z } = x;
79
+ // // the above should turn into
80
+ // let z = x.copy_field;
81
+ // let y = x;
82
+ // }
83
+ new_bindings. extend_from_slice ( & candidate. bindings ) ;
84
+ mem:: swap ( & mut candidate. bindings , & mut new_bindings) ;
85
+ new_bindings. clear ( ) ;
86
+
68
87
if !changed {
69
88
// Move or-patterns to the end, because they can result in us
70
89
// creating additional candidates, so we want to test them as
71
90
// late as possible.
72
91
candidate
73
92
. match_pairs
74
93
. sort_by_key ( |pair| matches ! ( * pair. pattern. kind, PatKind :: Or { .. } ) ) ;
94
+ debug ! ( "simplify_candidate: simplifed {:?}" , candidate) ;
75
95
return false ; // if we were not able to simplify any, done.
76
96
}
77
97
}
@@ -104,6 +124,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
104
124
& mut self ,
105
125
match_pair : MatchPair < ' pat , ' tcx > ,
106
126
candidate : & mut Candidate < ' pat , ' tcx > ,
127
+ bindings : & mut Vec < Binding < ' tcx > > ,
107
128
) -> Result < ( ) , MatchPair < ' pat , ' tcx > > {
108
129
let tcx = self . hir . tcx ( ) ;
109
130
match * match_pair. pattern . kind {
@@ -131,20 +152,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
131
152
}
132
153
133
154
PatKind :: Binding { name, mutability, mode, var, ty, ref subpattern, is_primary : _ } => {
134
- // issue #69971: the binding order should be right to left if there are more
135
- // bindings after `@` to please the borrow checker
136
- // Ex
137
- // struct NonCopyStruct {
138
- // copy_field: u32,
139
- // }
140
- //
141
- // fn foo1(x: NonCopyStruct) {
142
- // let y @ NonCopyStruct { copy_field: z } = x;
143
- // // the above should turn into
144
- // let z = x.copy_field;
145
- // let y = x;
146
- // }
147
- candidate. bindings . insert ( 0 , Binding {
155
+ bindings. push ( Binding {
148
156
name,
149
157
mutability,
150
158
span : match_pair. pattern . span ,
0 commit comments