about summary refs log tree commit diff
path: root/src/test/ui/borrowck
diff options
context:
space:
mode:
authorCaio <c410.f3r@gmail.com>2021-01-16 15:54:05 -0300
committerCaio <c410.f3r@gmail.com>2021-01-16 19:46:54 -0300
commitad35979c50366d6b0fbcda99215f1c4e926e5dab (patch)
tree8bc4fd6168831ee45cf114456cc70d4cf49266d8 /src/test/ui/borrowck
parent63a83c5f55801b17b77adf690db397d17c706c48 (diff)
downloadrust-ad35979c50366d6b0fbcda99215f1c4e926e5dab.tar.gz
rust-ad35979c50366d6b0fbcda99215f1c4e926e5dab.zip
Move some tests to more reasonable directories - 2
Address comments

Update limits
Diffstat (limited to 'src/test/ui/borrowck')
-rw-r--r--src/test/ui/borrowck/issue-17263.rs25
-rw-r--r--src/test/ui/borrowck/issue-17545.rs10
-rw-r--r--src/test/ui/borrowck/issue-17545.stderr16
-rw-r--r--src/test/ui/borrowck/issue-20801.rs37
-rw-r--r--src/test/ui/borrowck/issue-20801.stderr39
-rw-r--r--src/test/ui/borrowck/issue-24267-flow-exit.rs19
-rw-r--r--src/test/ui/borrowck/issue-24267-flow-exit.stderr15
-rw-r--r--src/test/ui/borrowck/issue-25793.rs26
-rw-r--r--src/test/ui/borrowck/issue-25793.stderr18
-rw-r--r--src/test/ui/borrowck/issue-27282-move-match-input-into-guard.rs20
-rw-r--r--src/test/ui/borrowck/issue-27282-move-match-input-into-guard.stderr17
-rw-r--r--src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.rs40
-rw-r--r--src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.stderr14
-rw-r--r--src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.rs18
-rw-r--r--src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.stderr13
-rw-r--r--src/test/ui/borrowck/issue-45199.rs24
-rw-r--r--src/test/ui/borrowck/issue-45199.stderr35
-rw-r--r--src/test/ui/borrowck/issue-46471.rs7
-rw-r--r--src/test/ui/borrowck/issue-46471.stderr9
19 files changed, 402 insertions, 0 deletions
diff --git a/src/test/ui/borrowck/issue-17263.rs b/src/test/ui/borrowck/issue-17263.rs
new file mode 100644
index 00000000000..7e9ff685482
--- /dev/null
+++ b/src/test/ui/borrowck/issue-17263.rs
@@ -0,0 +1,25 @@
+// check-pass
+
+#![feature(box_syntax)]
+
+struct Foo { a: isize, b: isize }
+
+fn main() {
+    let mut x: Box<_> = box Foo { a: 1, b: 2 };
+    let (a, b) = (&mut x.a, &mut x.b);
+
+    let mut foo: Box<_> = box Foo { a: 1, b: 2 };
+    let (c, d) = (&mut foo.a, &foo.b);
+
+    // We explicitly use the references created above to illustrate that the
+    // borrow checker is accepting this code *not* because of artificially
+    // short lifetimes, but rather because it understands that all the
+    // references are of disjoint parts of memory.
+    use_imm(d);
+    use_mut(c);
+    use_mut(b);
+    use_mut(a);
+}
+
+fn use_mut<T>(_: &mut T) { }
+fn use_imm<T>(_: &T) { }
diff --git a/src/test/ui/borrowck/issue-17545.rs b/src/test/ui/borrowck/issue-17545.rs
new file mode 100644
index 00000000000..ced6fff315f
--- /dev/null
+++ b/src/test/ui/borrowck/issue-17545.rs
@@ -0,0 +1,10 @@
+#![feature(fn_traits)]
+
+fn id<T>(x: T) -> T { x }
+
+pub fn foo<'a, F: Fn(&'a ())>(bar: F) {
+    bar.call((
+        &id(()), //~ ERROR temporary value dropped while borrowed
+    ));
+}
+fn main() {}
diff --git a/src/test/ui/borrowck/issue-17545.stderr b/src/test/ui/borrowck/issue-17545.stderr
new file mode 100644
index 00000000000..79a1e09bd7c
--- /dev/null
+++ b/src/test/ui/borrowck/issue-17545.stderr
@@ -0,0 +1,16 @@
+error[E0716]: temporary value dropped while borrowed
+  --> $DIR/issue-17545.rs:7:10
+   |
+LL |   pub fn foo<'a, F: Fn(&'a ())>(bar: F) {
+   |              -- lifetime `'a` defined here
+LL | /     bar.call((
+LL | |         &id(()),
+   | |          ^^^^^^ creates a temporary which is freed while still in use
+LL | |     ));
+   | |      -- temporary value is freed at the end of this statement
+   | |______|
+   |        argument requires that borrow lasts for `'a`
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0716`.
diff --git a/src/test/ui/borrowck/issue-20801.rs b/src/test/ui/borrowck/issue-20801.rs
new file mode 100644
index 00000000000..c3f136f2876
--- /dev/null
+++ b/src/test/ui/borrowck/issue-20801.rs
@@ -0,0 +1,37 @@
+// We used to ICE when moving out of a `*mut T` or `*const T`.
+
+struct T(u8);
+
+static mut GLOBAL_MUT_T: T = T(0);
+
+static GLOBAL_T: T = T(0);
+
+fn imm_ref() -> &'static T {
+    unsafe { &GLOBAL_T }
+}
+
+fn mut_ref() -> &'static mut T {
+    unsafe { &mut GLOBAL_MUT_T }
+}
+
+fn mut_ptr() -> *mut T {
+    unsafe { core::ptr::null_mut() }
+}
+
+fn const_ptr() -> *const T {
+    unsafe { core::ptr::null() }
+}
+
+pub fn main() {
+    let a = unsafe { *mut_ref() };
+    //~^ ERROR cannot move out of a mutable reference
+
+    let b = unsafe { *imm_ref() };
+    //~^ ERROR cannot move out of a shared reference
+
+    let c = unsafe { *mut_ptr() };
+    //~^ ERROR cannot move out of a raw pointer
+
+    let d = unsafe { *const_ptr() };
+    //~^ ERROR cannot move out of a raw pointer
+}
diff --git a/src/test/ui/borrowck/issue-20801.stderr b/src/test/ui/borrowck/issue-20801.stderr
new file mode 100644
index 00000000000..d276231dc0c
--- /dev/null
+++ b/src/test/ui/borrowck/issue-20801.stderr
@@ -0,0 +1,39 @@
+error[E0507]: cannot move out of a mutable reference
+  --> $DIR/issue-20801.rs:26:22
+   |
+LL |     let a = unsafe { *mut_ref() };
+   |                      ^^^^^^^^^^
+   |                      |
+   |                      move occurs because value has type `T`, which does not implement the `Copy` trait
+   |                      help: consider borrowing here: `&*mut_ref()`
+
+error[E0507]: cannot move out of a shared reference
+  --> $DIR/issue-20801.rs:29:22
+   |
+LL |     let b = unsafe { *imm_ref() };
+   |                      ^^^^^^^^^^
+   |                      |
+   |                      move occurs because value has type `T`, which does not implement the `Copy` trait
+   |                      help: consider borrowing here: `&*imm_ref()`
+
+error[E0507]: cannot move out of a raw pointer
+  --> $DIR/issue-20801.rs:32:22
+   |
+LL |     let c = unsafe { *mut_ptr() };
+   |                      ^^^^^^^^^^
+   |                      |
+   |                      move occurs because value has type `T`, which does not implement the `Copy` trait
+   |                      help: consider borrowing here: `&*mut_ptr()`
+
+error[E0507]: cannot move out of a raw pointer
+  --> $DIR/issue-20801.rs:35:22
+   |
+LL |     let d = unsafe { *const_ptr() };
+   |                      ^^^^^^^^^^^^
+   |                      |
+   |                      move occurs because value has type `T`, which does not implement the `Copy` trait
+   |                      help: consider borrowing here: `&*const_ptr()`
+
+error: aborting due to 4 previous errors
+
+For more information about this error, try `rustc --explain E0507`.
diff --git a/src/test/ui/borrowck/issue-24267-flow-exit.rs b/src/test/ui/borrowck/issue-24267-flow-exit.rs
new file mode 100644
index 00000000000..d6809ee4143
--- /dev/null
+++ b/src/test/ui/borrowck/issue-24267-flow-exit.rs
@@ -0,0 +1,19 @@
+// Ensure that we reject code when a nonlocal exit (`break`,
+// `continue`) causes us to pop over a needed assignment.
+
+pub fn main() {
+    foo1();
+    foo2();
+}
+
+pub fn foo1() {
+    let x: i32;
+    loop { x = break; }
+    println!("{}", x); //~ ERROR borrow of possibly-uninitialized variable: `x`
+}
+
+pub fn foo2() {
+    let x: i32;
+    for _ in 0..10 { x = continue; }
+    println!("{}", x); //~ ERROR borrow of possibly-uninitialized variable: `x`
+}
diff --git a/src/test/ui/borrowck/issue-24267-flow-exit.stderr b/src/test/ui/borrowck/issue-24267-flow-exit.stderr
new file mode 100644
index 00000000000..4eb41ca24dd
--- /dev/null
+++ b/src/test/ui/borrowck/issue-24267-flow-exit.stderr
@@ -0,0 +1,15 @@
+error[E0381]: borrow of possibly-uninitialized variable: `x`
+  --> $DIR/issue-24267-flow-exit.rs:12:20
+   |
+LL |     println!("{}", x);
+   |                    ^ use of possibly-uninitialized `x`
+
+error[E0381]: borrow of possibly-uninitialized variable: `x`
+  --> $DIR/issue-24267-flow-exit.rs:18:20
+   |
+LL |     println!("{}", x);
+   |                    ^ use of possibly-uninitialized `x`
+
+error: aborting due to 2 previous errors
+
+For more information about this error, try `rustc --explain E0381`.
diff --git a/src/test/ui/borrowck/issue-25793.rs b/src/test/ui/borrowck/issue-25793.rs
new file mode 100644
index 00000000000..6c8dacc2248
--- /dev/null
+++ b/src/test/ui/borrowck/issue-25793.rs
@@ -0,0 +1,26 @@
+#![feature(rustc_attrs)]
+macro_rules! width(
+    ($this:expr) => {
+        $this.width.unwrap()
+        //~^ ERROR cannot use `self.width` because it was mutably borrowed
+    }
+);
+
+struct HasInfo {
+    width: Option<usize>
+}
+
+impl HasInfo {
+    fn get_size(&mut self, n: usize) -> usize {
+        n
+    }
+
+    fn get_other(&mut self) -> usize {
+        let r = &mut *self;
+        r.get_size(width!(self))
+    }
+    // Above is like `self.get_size(width!(self))`, but it
+    // deliberately avoids NLL's two phase borrow feature.
+}
+
+fn main() { }
diff --git a/src/test/ui/borrowck/issue-25793.stderr b/src/test/ui/borrowck/issue-25793.stderr
new file mode 100644
index 00000000000..9d66ba3aae1
--- /dev/null
+++ b/src/test/ui/borrowck/issue-25793.stderr
@@ -0,0 +1,18 @@
+error[E0503]: cannot use `self.width` because it was mutably borrowed
+  --> $DIR/issue-25793.rs:4:9
+   |
+LL |         $this.width.unwrap()
+   |         ^^^^^^^^^^^ use of borrowed `*self`
+...
+LL |         let r = &mut *self;
+   |                 ---------- borrow of `*self` occurs here
+LL |         r.get_size(width!(self))
+   |           -------- ------------ in this macro invocation
+   |           |
+   |           borrow later used by call
+   |
+   = note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0503`.
diff --git a/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.rs b/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.rs
new file mode 100644
index 00000000000..71f1f15654b
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.rs
@@ -0,0 +1,20 @@
+// Issue 27282: Example 2: This sidesteps the AST checks disallowing
+// mutable borrows in match guards by hiding the mutable borrow in a
+// guard behind a move (of the mutably borrowed match input) within a
+// closure.
+//
+// This example is not rejected by AST borrowck (and then reliably
+// reaches the panic code when executed, despite the compiler warning
+// about that match arm being unreachable.
+
+fn main() {
+    let b = &mut true;
+    match b {
+        &mut false => {},
+        _ if { (|| { let bar = b; *bar = false; })();
+                     false } => { },
+        &mut true => { println!("You might think we should get here"); },
+        //~^ ERROR use of moved value: `b` [E0382]
+        _ => panic!("surely we could never get here, since rustc warns it is unreachable."),
+    }
+}
diff --git a/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.stderr b/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.stderr
new file mode 100644
index 00000000000..51f9b464d76
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-move-match-input-into-guard.stderr
@@ -0,0 +1,17 @@
+error[E0382]: use of moved value: `b`
+  --> $DIR/issue-27282-move-match-input-into-guard.rs:16:14
+   |
+LL |     let b = &mut true;
+   |         - move occurs because `b` has type `&mut bool`, which does not implement the `Copy` trait
+...
+LL |         _ if { (|| { let bar = b; *bar = false; })();
+   |                 --             - variable moved due to use in closure
+   |                 |
+   |                 value moved into closure here
+LL |                      false } => { },
+LL |         &mut true => { println!("You might think we should get here"); },
+   |              ^^^^ value used here after move
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0382`.
diff --git a/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.rs b/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.rs
new file mode 100644
index 00000000000..9c3e7e9978e
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.rs
@@ -0,0 +1,40 @@
+// This is testing an attempt to corrupt the discriminant of the match
+// arm in a guard, followed by an attempt to continue matching on that
+// corrupted discriminant in the remaining match arms.
+//
+// Basically this is testing that our new NLL feature of emitting a
+// fake read on each match arm is catching cases like this.
+//
+// This case is interesting because it includes a guard that
+// diverges, and therefore a single final fake-read at the very end
+// after the final match arm would not suffice.
+//
+// It is also interesting because the access to the corrupted data
+// occurs in the pattern-match itself, and not in the guard
+// expression.
+
+struct ForceFnOnce;
+
+fn main() {
+    let mut x = &mut Some(&2);
+    let force_fn_once = ForceFnOnce;
+    match x {
+        &mut None => panic!("unreachable"),
+        &mut Some(&_)
+            if {
+                // ForceFnOnce needed to exploit #27282
+                (|| { *x = None; drop(force_fn_once); })();
+                //~^ ERROR cannot mutably borrow `x` in match guard [E0510]
+                false
+            } => {}
+
+        // this segfaults if we corrupted the discriminant, because
+        // the compiler gets to *assume* that it cannot be the `None`
+        // case, even though that was the effect of the guard.
+        &mut Some(&2)
+            if {
+                panic!()
+            } => {}
+        _ => panic!("unreachable"),
+    }
+}
diff --git a/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.stderr b/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.stderr
new file mode 100644
index 00000000000..f0a3151f4e1
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-mutate-before-diverging-arm-2.stderr
@@ -0,0 +1,14 @@
+error[E0510]: cannot mutably borrow `x` in match guard
+  --> $DIR/issue-27282-mutate-before-diverging-arm-2.rs:26:18
+   |
+LL |     match x {
+   |           - value is immutable in match guard
+...
+LL |                 (|| { *x = None; drop(force_fn_once); })();
+   |                  ^^    - borrow occurs due to use of `x` in closure
+   |                  |
+   |                  cannot mutably borrow
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0510`.
diff --git a/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.rs b/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.rs
new file mode 100644
index 00000000000..82d8b9e9ed9
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.rs
@@ -0,0 +1,18 @@
+// Issue 27282: This is a variation on issue-27282-move-ref-mut-into-guard.rs
+//
+// It reborrows instead of moving the `ref mut` pattern borrow. This
+// means that our conservative check for mutation in guards will
+// reject it. But I want to make sure that we continue to reject it
+// (under NLL) even when that conservaive check goes away.
+
+fn main() {
+    let mut b = &mut true;
+    match b {
+        &mut false => {},
+        ref mut r if { (|| { let bar = &mut *r; **bar = false; })();
+        //~^ ERROR cannot borrow `r` as mutable, as it is immutable for the pattern guard
+                             false } => { &mut *r; },
+        &mut true => { println!("You might think we should get here"); },
+        _ => panic!("surely we could never get here, since rustc warns it is unreachable."),
+    }
+}
diff --git a/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.stderr b/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.stderr
new file mode 100644
index 00000000000..f0264b56ea5
--- /dev/null
+++ b/src/test/ui/borrowck/issue-27282-reborrow-ref-mut-in-guard.stderr
@@ -0,0 +1,13 @@
+error[E0596]: cannot borrow `r` as mutable, as it is immutable for the pattern guard
+  --> $DIR/issue-27282-reborrow-ref-mut-in-guard.rs:12:25
+   |
+LL |         ref mut r if { (|| { let bar = &mut *r; **bar = false; })();
+   |                         ^^                   - mutable borrow occurs due to use of `r` in closure
+   |                         |
+   |                         cannot borrow as mutable
+   |
+   = note: variables bound in patterns are immutable until the end of the pattern guard
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0596`.
diff --git a/src/test/ui/borrowck/issue-45199.rs b/src/test/ui/borrowck/issue-45199.rs
new file mode 100644
index 00000000000..cbd45cbb619
--- /dev/null
+++ b/src/test/ui/borrowck/issue-45199.rs
@@ -0,0 +1,24 @@
+fn test_drop_replace() {
+    let b: Box<isize>;
+    //~^ HELP make this binding mutable
+    //~| SUGGESTION mut b
+    b = Box::new(1);    //~ NOTE first assignment
+    b = Box::new(2);    //~ ERROR cannot assign twice to immutable variable `b`
+                        //~| NOTE cannot assign twice to immutable
+}
+
+fn test_call() {
+    let b = Box::new(1);    //~ NOTE first assignment
+                            //~| HELP make this binding mutable
+                            //~| SUGGESTION mut b
+    b = Box::new(2);        //~ ERROR cannot assign twice to immutable variable `b`
+                            //~| NOTE cannot assign twice to immutable
+}
+
+fn test_args(b: Box<i32>) {  //~ HELP make this binding mutable
+                                //~| SUGGESTION mut b
+    b = Box::new(2);            //~ ERROR cannot assign to immutable argument `b`
+                                //~| NOTE cannot assign to immutable argument
+}
+
+fn main() {}
diff --git a/src/test/ui/borrowck/issue-45199.stderr b/src/test/ui/borrowck/issue-45199.stderr
new file mode 100644
index 00000000000..83b634051bb
--- /dev/null
+++ b/src/test/ui/borrowck/issue-45199.stderr
@@ -0,0 +1,35 @@
+error[E0384]: cannot assign twice to immutable variable `b`
+  --> $DIR/issue-45199.rs:6:5
+   |
+LL |     let b: Box<isize>;
+   |         - help: make this binding mutable: `mut b`
+...
+LL |     b = Box::new(1);
+   |     - first assignment to `b`
+LL |     b = Box::new(2);
+   |     ^ cannot assign twice to immutable variable
+
+error[E0384]: cannot assign twice to immutable variable `b`
+  --> $DIR/issue-45199.rs:14:5
+   |
+LL |     let b = Box::new(1);
+   |         -
+   |         |
+   |         first assignment to `b`
+   |         help: make this binding mutable: `mut b`
+...
+LL |     b = Box::new(2);
+   |     ^ cannot assign twice to immutable variable
+
+error[E0384]: cannot assign to immutable argument `b`
+  --> $DIR/issue-45199.rs:20:5
+   |
+LL | fn test_args(b: Box<i32>) {
+   |              - help: make this binding mutable: `mut b`
+LL |
+LL |     b = Box::new(2);
+   |     ^ cannot assign to immutable argument
+
+error: aborting due to 3 previous errors
+
+For more information about this error, try `rustc --explain E0384`.
diff --git a/src/test/ui/borrowck/issue-46471.rs b/src/test/ui/borrowck/issue-46471.rs
new file mode 100644
index 00000000000..8922005d2f8
--- /dev/null
+++ b/src/test/ui/borrowck/issue-46471.rs
@@ -0,0 +1,7 @@
+fn foo() -> &'static u32 {
+    let x = 0;
+    &x
+    //~^ ERROR cannot return reference to local variable `x` [E0515]
+}
+
+fn main() { }
diff --git a/src/test/ui/borrowck/issue-46471.stderr b/src/test/ui/borrowck/issue-46471.stderr
new file mode 100644
index 00000000000..935414c1f3f
--- /dev/null
+++ b/src/test/ui/borrowck/issue-46471.stderr
@@ -0,0 +1,9 @@
+error[E0515]: cannot return reference to local variable `x`
+  --> $DIR/issue-46471.rs:3:5
+   |
+LL |     &x
+   |     ^^ returns a reference to data owned by the current function
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0515`.