1+ #![ allow( dead_code) ]
2+
3+ // This tests the various kinds of assignments there are. Polonius used to generate `killed`
4+ // facts only on simple assigments, but not projections, incorrectly causing errors to be emitted
5+ // for code accepted by NLL. They are all variations from example code in the NLL RFC.
6+
7+ // check-pass
8+ // compile-flags: -Z borrowck=mir -Z polonius
9+ // ignore-compare-mode-nll
10+
11+ struct List < T > {
12+ value : T ,
13+ next : Option < Box < List < T > > > ,
14+ }
15+
16+ // Assignment to a local: the `list` assignment should clear the existing
17+ // borrows of `list.value` and `list.next`
18+ fn assignment_to_local < T > ( mut list : & mut List < T > ) -> Vec < & mut T > {
19+ let mut result = vec ! [ ] ;
20+ loop {
21+ result. push ( & mut list. value ) ;
22+ if let Some ( n) = list. next . as_mut ( ) {
23+ list = n;
24+ } else {
25+ return result;
26+ }
27+ }
28+ }
29+
30+ // Assignment to a deref projection: the `*list` assignment should clear the existing
31+ // borrows of `list.value` and `list.next`
32+ fn assignment_to_deref_projection < T > ( mut list : Box < & mut List < T > > ) -> Vec < & mut T > {
33+ let mut result = vec ! [ ] ;
34+ loop {
35+ result. push ( & mut list. value ) ;
36+ if let Some ( n) = list. next . as_mut ( ) {
37+ * list = n;
38+ } else {
39+ return result;
40+ }
41+ }
42+ }
43+
44+ // Assignment to a field projection: the `list.0` assignment should clear the existing
45+ // borrows of `list.0.value` and `list.0.next`
46+ fn assignment_to_field_projection < T > ( mut list : ( & mut List < T > , ) ) -> Vec < & mut T > {
47+ let mut result = vec ! [ ] ;
48+ loop {
49+ result. push ( & mut list. 0 . value ) ;
50+ if let Some ( n) = list. 0 . next . as_mut ( ) {
51+ list. 0 = n;
52+ } else {
53+ return result;
54+ }
55+ }
56+ }
57+
58+ // Assignment to a deref field projection: the `*list.0` assignment should clear the existing
59+ // borrows of `list.0.value` and `list.0.next`
60+ fn assignment_to_deref_field_projection < T > ( mut list : ( Box < & mut List < T > > , ) ) -> Vec < & mut T > {
61+ let mut result = vec ! [ ] ;
62+ loop {
63+ result. push ( & mut list. 0 . value ) ;
64+ if let Some ( n) = list. 0 . next . as_mut ( ) {
65+ * list. 0 = n;
66+ } else {
67+ return result;
68+ }
69+ }
70+ }
71+
72+ // Similar to `assignment_to_deref_field_projection` but through a longer projection chain
73+ fn assignment_through_projection_chain < T > (
74+ mut list : ( ( ( ( ( Box < & mut List < T > > , ) , ) , ) , ) , ) ,
75+ ) -> Vec < & mut T > {
76+ let mut result = vec ! [ ] ;
77+ loop {
78+ result. push ( & mut ( ( ( ( list. 0 ) . 0 ) . 0 ) . 0 ) . 0 . value ) ;
79+ if let Some ( n) = ( ( ( ( list. 0 ) . 0 ) . 0 ) . 0 ) . 0 . next . as_mut ( ) {
80+ * ( ( ( ( list. 0 ) . 0 ) . 0 ) . 0 ) . 0 = n;
81+ } else {
82+ return result;
83+ }
84+ }
85+ }
86+
87+ fn main ( ) {
88+ }
0 commit comments