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