]> git.lizzy.rs Git - rust.git/blob - tests/ui/borrowck/borrowck-describe-lvalue.rs
Rollup merge of #106726 - cmorin6:fix-comment-typos, r=Nilstrieb
[rust.git] / tests / ui / borrowck / borrowck-describe-lvalue.rs
1 pub struct Foo {
2   x: u32
3 }
4
5 pub struct Bar(u32);
6
7 pub enum Baz {
8     X(u32)
9 }
10
11 union U {
12     a: u8,
13     b: u64,
14 }
15
16 impl Foo {
17   fn x(&mut self) -> &mut u32 { &mut self.x }
18 }
19
20 impl Bar {
21     fn x(&mut self) -> &mut u32 { &mut self.0 }
22 }
23
24 impl Baz {
25     fn x(&mut self) -> &mut u32 {
26         match *self {
27             Baz::X(ref mut value) => value
28         }
29     }
30 }
31
32 fn main() {
33     // Local and field from struct
34     {
35         let mut f = Foo { x: 22 };
36         let x = f.x();
37         f.x; //~ ERROR cannot use `f.x` because it was mutably borrowed
38         drop(x);
39     }
40     // Local and field from tuple-struct
41     {
42         let mut g = Bar(22);
43         let x = g.x();
44         g.0; //~ ERROR cannot use `g.0` because it was mutably borrowed
45         drop(x);
46     }
47     // Local and field from tuple
48     {
49         let mut h = (22, 23);
50         let x = &mut h.0;
51         h.0; //~ ERROR cannot use `h.0` because it was mutably borrowed
52         drop(x);
53     }
54     // Local and field from enum
55     {
56         let mut e = Baz::X(2);
57         let x = e.x();
58         match e {
59             Baz::X(value) => value //~ ERROR cannot use `e.0` because it was mutably borrowed
60         };
61         drop(x);
62     }
63     // Local and field from union
64     unsafe {
65         let mut u = U { b: 0 };
66         let x = &mut u.a;
67         u.a; //~ ERROR cannot use `u.a` because it was mutably borrowed
68         drop(x);
69     }
70     // Deref and field from struct
71     {
72         let mut f = Box::new(Foo { x: 22 });
73         let x = f.x();
74         f.x; //~ ERROR cannot use `f.x` because it was mutably borrowed
75         drop(x);
76     }
77     // Deref and field from tuple-struct
78     {
79         let mut g = Box::new(Bar(22));
80         let x = g.x();
81         g.0; //~ ERROR cannot use `g.0` because it was mutably borrowed
82         drop(x);
83     }
84     // Deref and field from tuple
85     {
86         let mut h = Box::new((22, 23));
87         let x = &mut h.0;
88         h.0; //~ ERROR cannot use `h.0` because it was mutably borrowed
89         drop(x);
90     }
91     // Deref and field from enum
92     {
93         let mut e = Box::new(Baz::X(3));
94         let x = e.x();
95         match *e {
96             Baz::X(value) => value
97             //~^ ERROR cannot use `e.0` because it was mutably borrowed
98         };
99         drop(x);
100     }
101     // Deref and field from union
102     unsafe {
103         let mut u = Box::new(U { b: 0 });
104         let x = &mut u.a;
105         u.a; //~ ERROR cannot use `u.a` because it was mutably borrowed
106         drop(x);
107     }
108     // Constant index
109     {
110         let mut v = &[1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
111         let x = &mut v;
112         match v {
113             &[x, _, .., _, _] => println!("{}", x),
114                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
115                             _ => panic!("other case"),
116         }
117         match v {
118             &[_, x, .., _, _] => println!("{}", x),
119                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
120                             _ => panic!("other case"),
121         }
122         match v {
123             &[_, _, .., x, _] => println!("{}", x),
124                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
125                             _ => panic!("other case"),
126         }
127         match v {
128             &[_, _, .., _, x] => println!("{}", x),
129                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
130                             _ => panic!("other case"),
131         }
132         drop(x);
133     }
134     // Subslices
135     {
136         let mut v = &[1, 2, 3, 4, 5];
137         let x = &mut v;
138         match v {
139             &[x @ ..] => println!("{:?}", x),
140                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
141             _ => panic!("other case"),
142         }
143         match v {
144             &[_, x @ ..] => println!("{:?}", x),
145                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
146             _ => panic!("other case"),
147         }
148         match v {
149             &[x @ .., _] => println!("{:?}", x),
150                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
151             _ => panic!("other case"),
152         }
153         match v {
154             &[_, x @ .., _] => println!("{:?}", x),
155                 //~^ ERROR cannot use `v[..]` because it was mutably borrowed
156             _ => panic!("other case"),
157         }
158         drop(x);
159     }
160     // Downcasted field
161     {
162         enum E<X> { A(X), B { x: X } }
163
164         let mut e = E::A(3);
165         let x = &mut e;
166         match e {
167             //~^ ERROR cannot use `e` because it was mutably borrowed
168             E::A(ref ax) =>
169                 //~^ ERROR cannot borrow `e.0` as immutable because it is also borrowed as mutable
170                 println!("e.ax: {:?}", ax),
171             E::B { x: ref bx } =>
172                 //~^ ERROR cannot borrow `e.x` as immutable because it is also borrowed as mutable
173                 println!("e.bx: {:?}", bx),
174         }
175         drop(x);
176     }
177     // Field in field
178     {
179         struct F { x: u32, y: u32 };
180         struct S { x: F, y: (u32, u32), };
181         let mut s = S { x: F { x: 1, y: 2}, y: (999, 998) };
182         let x = &mut s;
183         match s {
184             S  { y: (ref y0, _), .. } =>
185                 //~^ ERROR cannot borrow `s.y.0` as immutable because it is also borrowed as mutable
186                 println!("y0: {:?}", y0),
187             _ => panic!("other case"),
188         }
189         match s {
190             S  { x: F { y: ref x0, .. }, .. } =>
191                 //~^ ERROR cannot borrow `s.x.y` as immutable because it is also borrowed as mutable
192                 println!("x0: {:?}", x0),
193             _ => panic!("other case"),
194         }
195         drop(x);
196     }
197     // Field of ref
198     {
199         struct Block<'a> {
200             current: &'a u8,
201             unrelated: &'a u8,
202         };
203
204         fn bump<'a>(mut block: &mut Block<'a>) {
205             let x = &mut block;
206             let p: &'a u8 = &*block.current;
207             //~^ ERROR cannot borrow `*block.current` as immutable because it is also borrowed as mutable
208             // See issue rust#38899
209             drop(x);
210         }
211     }
212     // Field of ptr
213     {
214         struct Block2 {
215             current: *const u8,
216             unrelated: *const u8,
217         }
218
219         unsafe fn bump2(mut block: *mut Block2) {
220             let x = &mut block;
221             let p : *const u8 = &*(*block).current;
222             //~^ ERROR cannot borrow `*block.current` as immutable because it is also borrowed as mutable
223             // See issue rust#38899
224             drop(x);
225         }
226     }
227     // Field of index
228     {
229         struct F {x: u32, y: u32};
230         let mut v = &[F{x: 1, y: 2}, F{x: 3, y: 4}];
231         let x = &mut v;
232         v[0].y;
233         //~^ ERROR cannot use `v[_].y` because it was mutably borrowed
234         //~| ERROR cannot use `*v` because it was mutably borrowed
235         drop(x);
236     }
237     // Field of constant index
238     {
239         struct F {x: u32, y: u32};
240         let mut v = &[F{x: 1, y: 2}, F{x: 3, y: 4}];
241         let x = &mut v;
242         match v {
243             &[_, F {x: ref xf, ..}] => println!("{}", xf),
244             //~^ ERROR cannot borrow `v[..].x` as immutable because it is also borrowed as mutable
245             _ => panic!("other case")
246         }
247         drop(x);
248     }
249     // Field from upvar
250     {
251         let mut x = 0;
252         || {
253             let y = &mut x;
254             &mut x; //~ ERROR cannot borrow `x` as mutable more than once at a time
255             *y = 1;
256         };
257     }
258     // Field from upvar nested
259     {
260         let mut x = 0;
261            || {
262                || { //~ ERROR captured variable cannot escape `FnMut` closure body
263                    let y = &mut x;
264                    &mut x; //~ ERROR cannot borrow `x` as mutable more than once at a time
265                    *y = 1;
266                    drop(y);
267                 }
268            };
269     }
270     {
271         fn foo(x: Vec<i32>) {
272             let c = || {
273                 drop(x);
274                 drop(x); //~ ERROR use of moved value: `x`
275             };
276             c();
277         }
278     }
279 }