add closure requirement tests, improve debugging output

The overall format is now easier to read. Also, There is now graphviz
output, as well as a `#[rustc_regions]` annotation that dumps internal
state.
This commit is contained in:
Niko Matsakis 2017-11-22 17:39:46 -05:00
parent ab1c1bc6bc
commit 05441abd2b
51 changed files with 1702 additions and 77 deletions

View file

@ -28,18 +28,18 @@ fn main() {
// START rustc.main.nll.0.mir
// | Live variables on entry to bb0: []
// bb0: {
// | Live variables at bb0[0]: []
// | Live variables on entry to bb0[0]: []
// StorageLive(_1);
// | Live variables at bb0[1]: []
// | Live variables on entry to bb0[1]: []
// _1 = const <std::boxed::Box<T>>::new(const 22usize) -> [return: bb2, unwind: bb1];
// }
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// | Live variables on entry to bb2: [_1 (drop)]
// bb2: {
// | Live variables at bb2[0]: [_1 (drop)]
// | Live variables on entry to bb2[0]: [_1 (drop)]
// StorageLive(_2);
// | Live variables at bb2[1]: [_1 (drop)]
// | Live variables on entry to bb2[1]: [_1 (drop)]
// _2 = const can_panic() -> [return: bb3, unwind: bb4];
// }
// END rustc.main.nll.0.mir

View file

@ -27,15 +27,15 @@ fn main() {
// START rustc.main.nll.0.mir
// | Live variables on entry to bb2: []
// bb2: {
// | Live variables at bb2[0]: []
// | Live variables on entry to bb2[0]: []
// _1 = const 55usize;
// | Live variables at bb2[1]: [_1]
// | Live variables on entry to bb2[1]: [_1]
// StorageLive(_3);
// | Live variables at bb2[2]: [_1]
// | Live variables on entry to bb2[2]: [_1]
// StorageLive(_4);
// | Live variables at bb2[3]: [_1]
// | Live variables on entry to bb2[3]: [_1]
// _4 = _1;
// | Live variables at bb2[4]: [_4]
// | Live variables on entry to bb2[4]: [_4]
// _3 = const use_x(move _4) -> [return: bb3, unwind: bb1];
// }
// END rustc.main.nll.0.mir

View file

@ -31,18 +31,18 @@ fn main() {
// START rustc.main.nll.0.mir
// | Live variables on entry to bb3: [_1]
// bb3: {
// | Live variables at bb3[0]: [_1]
// | Live variables on entry to bb3[0]: [_1]
// StorageLive(_4);
// | Live variables at bb3[1]: [_1]
// | Live variables on entry to bb3[1]: [_1]
// _4 = _1;
// | Live variables at bb3[2]: [_4]
// | Live variables on entry to bb3[2]: [_4]
// _3 = const make_live(move _4) -> [return: bb5, unwind: bb1];
// }
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// | Live variables on entry to bb4: []
// bb4: {
// | Live variables at bb4[0]: []
// | Live variables on entry to bb4[0]: []
// _5 = const make_dead() -> [return: bb6, unwind: bb1];
// }
// END rustc.main.nll.0.mir

View file

@ -26,9 +26,18 @@ fn main() {
// END RUST SOURCE
// START rustc.use_x.nll.0.mir
// | '_#0r: {bb0[0], bb0[1], '_#0r}
// | '_#1r: {bb0[0], bb0[1], '_#1r}
// | '_#2r: {bb0[0], bb0[1], '_#2r}
// | '_#3r: {bb0[0], bb0[1], '_#3r}
// | Free Region Mapping
// | '_#0r | Global | ['_#2r, '_#1r, '_#0r, '_#3r]
// | '_#1r | External | ['_#1r]
// | '_#2r | External | ['_#2r, '_#1r]
// | '_#3r | Local | ['_#3r]
// |
// | Inferred Region Values
// | '_#0r | {bb0[0], bb0[1], '_#0r}
// | '_#1r | {bb0[0], bb0[1], '_#1r}
// | '_#2r | {bb0[0], bb0[1], '_#2r}
// | '_#3r | {bb0[0], bb0[1], '_#3r}
// |
// ...
// fn use_x(_1: &'_#1r mut i32, _2: &'_#2r u32, _3: &'_#1r u32, _4: &'_#3r u32) -> bool {
// END rustc.use_x.nll.0.mir

View file

@ -28,11 +28,10 @@ fn main() {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#6r: {bb0[6], bb0[7], bb0[8], bb0[9], bb0[10], bb0[11], bb0[12], bb0[13], bb0[14]}
// | '_#6r | {bb0[6], bb0[7], bb0[8], bb0[9], bb0[10], bb0[11], bb0[12], bb0[13], bb0[14]}
// ...
// | '_#8r | {bb0[11], bb0[12], bb0[13], bb0[14]}
// ...
// | '_#8r: {bb0[11], bb0[12], bb0[13], bb0[14]}
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// let _2: &'_#6r mut i32;
// ...
// let _4: &'_#8r mut i32;

View file

@ -31,26 +31,26 @@ fn main() {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#1r: {bb2[0], bb2[1], bb3[0], bb3[1]}
// | '_#2r: {bb2[1], bb3[0], bb3[1]}
// | '_#1r | {bb2[0], bb2[1], bb3[0], bb3[1]}
// | '_#2r | {bb2[1], bb3[0], bb3[1]}
// ...
// let _2: &'_#2r usize;
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// bb2: {
// | Live variables at bb2[0]: [_1, _3]
// | Live variables on entry to bb2[0]: [_1, _3]
// _2 = &'_#1r _1[_3];
// | Live variables at bb2[1]: [_2]
// | Live variables on entry to bb2[1]: [_2]
// switchInt(const true) -> [0u8: bb4, otherwise: bb3];
// }
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// bb3: {
// | Live variables at bb3[0]: [_2]
// | Live variables on entry to bb3[0]: [_2]
// StorageLive(_7);
// | Live variables at bb3[1]: [_2]
// | Live variables on entry to bb3[1]: [_2]
// _7 = (*_2);
// | Live variables at bb3[2]: [_7]
// | Live variables on entry to bb3[2]: [_7]
// _6 = const use_x(move _7) -> [return: bb5, unwind: bb1];
// }
// END rustc.main.nll.0.mir

View file

@ -44,5 +44,5 @@ unsafe impl<#[may_dangle] T> Drop for Wrap<T> {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#5r: {bb2[3], bb2[4], bb2[5], bb3[0], bb3[1]}
// | '_#5r | {bb2[3], bb2[4], bb2[5], bb3[0], bb3[1]}
// END rustc.main.nll.0.mir

View file

@ -46,5 +46,5 @@ impl<T> Drop for Wrap<T> {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#5r: {bb2[3], bb2[4], bb2[5], bb3[0], bb3[1], bb3[2], bb4[0], bb5[0], bb5[1], bb5[2], bb6[0], bb7[0], bb7[1], bb8[0]}
// | '_#5r | {bb2[3], bb2[4], bb2[5], bb3[0], bb3[1], bb3[2], bb4[0], bb5[0], bb5[1], bb5[2], bb6[0], bb7[0], bb7[1], bb8[0]}
// END rustc.main.nll.0.mir

View file

@ -36,10 +36,10 @@ fn main() {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#1r: {bb2[0], bb2[1], bb3[0], bb3[1]}
// | '_#1r | {bb2[0], bb2[1], bb3[0], bb3[1]}
// ...
// | '_#3r: {bb8[1], bb8[2], bb8[3], bb8[4]}
// | '_#4r: {bb2[1], bb3[0], bb3[1], bb8[2], bb8[3], bb8[4]}
// | '_#3r | {bb8[1], bb8[2], bb8[3], bb8[4]}
// | '_#4r | {bb2[1], bb3[0], bb3[1], bb8[2], bb8[3], bb8[4]}
// ...
// let mut _2: &'_#4r usize;
// ...

View file

@ -32,9 +32,9 @@ fn main() {
// END RUST SOURCE
// START rustc.main.nll.0.mir
// | '_#1r: {bb2[0], bb2[1], bb2[2], bb2[3], bb2[4], bb2[5], bb2[6], bb3[0], bb3[1]}
// | '_#2r: {bb2[1], bb2[2], bb2[3], bb2[4], bb2[5], bb2[6], bb3[0], bb3[1]}
// | '_#3r: {bb2[5], bb2[6], bb3[0], bb3[1]}
// | '_#1r | {bb2[0], bb2[1], bb2[2], bb2[3], bb2[4], bb2[5], bb2[6], bb3[0], bb3[1]}
// | '_#2r | {bb2[1], bb2[2], bb2[3], bb2[4], bb2[5], bb2[6], bb3[0], bb3[1]}
// | '_#3r | {bb2[5], bb2[6], bb3[0], bb3[1]}
// END rustc.main.nll.0.mir
// START rustc.main.nll.0.mir
// let _2: &'_#2r usize;

View file

@ -0,0 +1,50 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// compile-flags:-Znll -Zborrowck=mir
// Test that a structure which tries to store a pointer to `y` into
// `p` (indirectly) fails to compile.
#![feature(rustc_attrs)]
struct SomeStruct<'a, 'b: 'a> {
p: &'a mut &'b i32,
y: &'b i32,
}
fn test() {
let x = 44;
let mut p = &x;
{
let y = 22;
let closure = SomeStruct {
p: &mut p,
y: &y,
};
closure.invoke();
}
//~^ ERROR borrowed value does not live long enough [E0597]
deref(p);
}
impl<'a, 'b> SomeStruct<'a, 'b> {
fn invoke(self) {
*self.p = self.y;
}
}
fn deref(_: &i32) { }
fn main() { }

View file

@ -0,0 +1,13 @@
error[E0597]: borrowed value does not live long enough
--> $DIR/capture-ref-in-struct.rs:36:6
|
28 | let y = 22;
| - temporary value created here
...
36 | }
| ^ temporary value dropped here while still borrowed
|
= note: consider using a `let` binding to increase its lifetime
error: aborting due to previous error

View file

@ -0,0 +1,48 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test closure that:
//
// - takes an argument `y`
// - stores `y` into another, longer-lived spot
//
// *but* the signature of the closure doesn't indicate that `y` lives
// long enough for that. The closure reports the error (and hence we
// see it before the closure's "external requirements" report).
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
#[rustc_regions]
fn test() {
let x = 44;
let mut p = &x;
{
let y = 22;
let mut closure = expect_sig(|p, y| *p = y);
//~^ ERROR free region `'_#4r` does not outlive free region `'_#3r`
//~| WARNING not reporting region error due to -Znll
closure(&mut p, &y);
}
deref(p);
}
fn expect_sig<F>(f: F) -> F
where F: FnMut(&mut &i32, &i32)
{
f
}
fn deref(_p: &i32) { }
fn main() { }

View file

@ -0,0 +1,40 @@
warning: not reporting region error due to -Znll
--> $DIR/escape-argument-callee.rs:31:50
|
31 | let mut closure = expect_sig(|p, y| *p = y);
| ^
error: free region `'_#4r` does not outlive free region `'_#3r`
--> $DIR/escape-argument-callee.rs:31:45
|
31 | let mut closure = expect_sig(|p, y| *p = y);
| ^^^^^^
note: External requirements
--> $DIR/escape-argument-callee.rs:31:38
|
31 | let mut closure = expect_sig(|p, y| *p = y);
| ^^^^^^^^^^^^^
|
= note: defining type: DefId(0/1:9 ~ escape_argument_callee[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's, 't0> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7666))) mut &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7667))) i32, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't0(7668))) i32))
]
= note: number of external vids: 1
note: No external requirements
--> $DIR/escape-argument-callee.rs:25:1
|
25 | / fn test() {
26 | | let x = 44;
27 | | let mut p = &x;
28 | |
... |
37 | | deref(p);
38 | | }
| |_^
|
= note: defining type: DefId(0/0:3 ~ escape_argument_callee[317d]::test[0]) with substs []
error: aborting due to previous error

View file

@ -0,0 +1,50 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test closure that:
//
// - takes an argument `y`
// - stores `y` into another, longer-lived spot
//
// but is invoked with a spot that doesn't live long
// enough to store `y`.
//
// The error is reported in the caller: invoking the closure links the
// lifetime of the borrow that is given as `y` and forces it to live
// too long.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
#[rustc_regions]
fn test() {
let x = 44;
let mut p = &x;
{
let y = 22;
let mut closure = expect_sig(|p, y| *p = y);
closure(&mut p, &y);
}
//~^ ERROR borrowed value does not live long enough [E0597]
deref(p);
}
fn expect_sig<F>(f: F) -> F
where F: for<'a, 'b> FnMut(&'a mut &'b i32, &'b i32)
{
f
}
fn deref(_p: &i32) { }
fn main() { }

View file

@ -0,0 +1,39 @@
note: External requirements
--> $DIR/escape-argument.rs:34:38
|
34 | let mut closure = expect_sig(|p, y| *p = y);
| ^^^^^^^^^^^^^
|
= note: defining type: DefId(0/1:9 ~ escape_argument[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(8634))) mut &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(8635))) i32, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(8635))) i32))
]
= note: number of external vids: 1
note: No external requirements
--> $DIR/escape-argument.rs:28:1
|
28 | / fn test() {
29 | | let x = 44;
30 | | let mut p = &x;
31 | |
... |
39 | | deref(p);
40 | | }
| |_^
|
= note: defining type: DefId(0/0:3 ~ escape_argument[317d]::test[0]) with substs []
error[E0597]: borrowed value does not live long enough
--> $DIR/escape-argument.rs:36:6
|
33 | let y = 22;
| - temporary value created here
...
36 | }
| ^ temporary value dropped here while still borrowed
|
= note: consider using a `let` binding to increase its lifetime
error: aborting due to previous error

View file

@ -0,0 +1,43 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// As in via-upvar, test closure that:
//
// - captures a variable `y`
// - stores reference to `y` into another, longer-lived spot
//
// except that the closure does so via a second closure.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
#[rustc_regions]
fn test() {
let x = 44;
let mut p = &x;
{
let y = 22;
let mut closure = || {
let mut closure1 = || p = &y;
closure1();
};
closure();
} //~ ERROR borrowed value does not live long enough
deref(p);
}
fn deref(_p: &i32) { }
fn main() { }

View file

@ -0,0 +1,61 @@
note: External requirements
--> $DIR/escape-upvar-nested.rs:31:32
|
31 | let mut closure1 = || p = &y;
| ^^^^^^^^^
|
= note: defining type: DefId(0/1:10 ~ escape_upvar_nested[317d]::test[0]::{{closure}}[0]::{{closure}}[0]) with closure substs [
i16,
extern "rust-call" fn(()),
&'_#1r mut &'_#2r i32,
&'_#3r i32
]
= note: number of external vids: 4
= note: where '_#3r: '_#2r
note: External requirements
--> $DIR/escape-upvar-nested.rs:30:27
|
30 | let mut closure = || {
| ___________________________^
31 | | let mut closure1 = || p = &y;
32 | | closure1();
33 | | };
| |_________^
|
= note: defining type: DefId(0/1:9 ~ escape_upvar_nested[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
extern "rust-call" fn(()),
&'_#1r mut &'_#2r i32,
&'_#3r i32
]
= note: number of external vids: 4
= note: where '_#3r: '_#2r
note: No external requirements
--> $DIR/escape-upvar-nested.rs:23:1
|
23 | / fn test() {
24 | | let x = 44;
25 | | let mut p = &x;
26 | |
... |
38 | | deref(p);
39 | | }
| |_^
|
= note: defining type: DefId(0/0:3 ~ escape_upvar_nested[317d]::test[0]) with substs []
error[E0597]: borrowed value does not live long enough
--> $DIR/escape-upvar-nested.rs:36:6
|
28 | let y = 22;
| - temporary value created here
...
36 | } //~ ERROR borrowed value does not live long enough
| ^ temporary value dropped here while still borrowed
|
= note: consider using a `let` binding to increase its lifetime
error: aborting due to previous error

View file

@ -0,0 +1,35 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test closure that:
// - captures a variable `y`
// - stores reference to `y` into another, longer-lived spot
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
#[rustc_regions]
fn test() {
let x = 44;
let mut p = &x;
{
let y = 22;
let mut closure = || p = &y;
closure();
} //~ ERROR borrowed value does not live long enough
deref(p);
}
fn deref(_p: &i32) { }
fn main() { }

View file

@ -0,0 +1,42 @@
note: External requirements
--> $DIR/escape-upvar-ref.rs:26:27
|
26 | let mut closure = || p = &y;
| ^^^^^^^^^
|
= note: defining type: DefId(0/1:9 ~ escape_upvar_ref[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
extern "rust-call" fn(()),
&'_#1r mut &'_#2r i32,
&'_#3r i32
]
= note: number of external vids: 4
= note: where '_#3r: '_#2r
note: No external requirements
--> $DIR/escape-upvar-ref.rs:20:1
|
20 | / fn test() {
21 | | let x = 44;
22 | | let mut p = &x;
23 | |
... |
30 | | deref(p);
31 | | }
| |_^
|
= note: defining type: DefId(0/0:3 ~ escape_upvar_ref[317d]::test[0]) with substs []
error[E0597]: borrowed value does not live long enough
--> $DIR/escape-upvar-ref.rs:28:6
|
25 | let y = 22;
| - temporary value created here
...
28 | } //~ ERROR borrowed value does not live long enough
| ^ temporary value dropped here while still borrowed
|
= note: consider using a `let` binding to increase its lifetime
error: aborting due to previous error

View file

@ -0,0 +1,63 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test where we fail to approximate due to demanding a postdom
// relationship between our upper bounds.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// Callee knows that:
//
// 'x: 'a
// 'x: 'b
// 'c: 'y
//
// we have to prove that `'x: 'y`. We currently can only approximate
// via a postdominator -- hence we fail to choose between `'a` and
// `'b` here and report the error in the closure.
fn establish_relationships<'a, 'b, 'c, F>(
_cell_a: Cell<&'a u32>,
_cell_b: Cell<&'b u32>,
_cell_c: Cell<&'c u32>,
_closure: F,
) where
F: for<'x, 'y> FnMut(
Cell<&'a &'x u32>, // shows that 'x: 'a
Cell<&'b &'x u32>, // shows that 'x: 'b
Cell<&'y &'c u32>, // shows that 'c: 'y
Cell<&'x u32>,
Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_cell_x: Cell<&'x u32>, _cell_y: Cell<&'y u32>, _y: &'y u32) {}
#[rustc_regions]
fn supply<'a, 'b, 'c>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>, cell_c: Cell<&'c u32>) {
establish_relationships(
cell_a,
cell_b,
cell_c,
|_outlives1, _outlives2, _outlives3, x, y| {
// Only works if 'x: 'y:
let p = x.get();
//~^ WARN not reporting region error due to -Znll
demand_y(x, y, p)
//~^ ERROR free region `'_#5r` does not outlive free region `'_#6r`
},
);
}
fn main() {}

View file

@ -0,0 +1,46 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-approximated-fail-no-postdom.rs:55:21
|
55 | let p = x.get();
| ^^^^^^^
error: free region `'_#5r` does not outlive free region `'_#6r`
--> $DIR/propagate-approximated-fail-no-postdom.rs:57:25
|
57 | demand_y(x, y, p)
| ^
note: External requirements
--> $DIR/propagate-approximated-fail-no-postdom.rs:53:9
|
53 | / |_outlives1, _outlives2, _outlives3, x, y| {
54 | | // Only works if 'x: 'y:
55 | | let p = x.get();
56 | | //~^ WARN not reporting region error due to -Znll
57 | | demand_y(x, y, p)
58 | | //~^ ERROR free region `'_#5r` does not outlive free region `'_#6r`
59 | | },
| |_________^
|
= note: defining type: DefId(0/1:20 ~ propagate_approximated_fail_no_postdom[317d]::supply[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's> extern "rust-call" fn((std::cell::Cell<&'_#1r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9523))) u32>, std::cell::Cell<&'_#2r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9523))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9524))) &'_#3r u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9523))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9524))) u32>))
]
= note: number of external vids: 4
note: No external requirements
--> $DIR/propagate-approximated-fail-no-postdom.rs:48:1
|
48 | / fn supply<'a, 'b, 'c>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>, cell_c: Cell<&'c u32>) {
49 | | establish_relationships(
50 | | cell_a,
51 | | cell_b,
... |
60 | | );
61 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_approximated_fail_no_postdom[317d]::supply[0]) with substs []
error: aborting due to previous error

View file

@ -0,0 +1,64 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Rather convoluted setup where we infer a relationship between two
// free regions in the closure signature (`'a` and `'b`) on the basis
// of a relationship between two bound regions (`'x` and `'y`).
//
// The idea is that, thanks to invoking `demand_y`, `'x: 'y` must
// hold, where `'x` and `'y` are bound regions. The closure can't
// prove that directly, and because `'x` and `'y` are bound it cannot
// ask the caller to prove it either. But it has bounds on `'x` and
// `'y` in terms of `'a` and `'b`, and it can propagate a relationship
// between `'a` and `'b` to the caller.
//
// Note: the use of `Cell` here is to introduce invariance. One less
// variable.
//
// FIXME: The `supply` function *ought* to generate an error, but it
// currently does not. This is I believe a shortcoming of the MIR type
// checker: the closure inference is expressing the correct
// requirement, as you can see from the `#[rustc_regions]` output.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// Callee knows that:
//
// 'x: 'a
// 'b: 'y
//
// so if we are going to ensure that `'x: 'y`, then `'a: 'b` must
// hold.
fn establish_relationships<'a, 'b, F>(_cell_a: &Cell<&'a u32>, _cell_b: &Cell<&'b u32>, _closure: F)
where
F: for<'x, 'y> FnMut(
&Cell<&'a &'x u32>, // shows that 'x: 'a
&Cell<&'y &'b u32>, // shows that 'b: 'y
&Cell<&'x u32>,
&Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_cell_x: &Cell<&'x u32>, _cell_y: &Cell<&'y u32>, _y: &'y u32) {}
#[rustc_regions]
fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
establish_relationships(&cell_a, &cell_b, |_outlives1, _outlives2, x, y| {
// Only works if 'x: 'y:
demand_y(x, y, x.get())
});
}
fn main() {}

View file

@ -0,0 +1,36 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-approximated-ref.rs:60:9
|
60 | demand_y(x, y, x.get())
| ^^^^^^^^^^^^^^^^^^^^^^^
note: External requirements
--> $DIR/propagate-approximated-ref.rs:58:47
|
58 | establish_relationships(&cell_a, &cell_b, |_outlives1, _outlives2, x, y| {
| _______________________________________________^
59 | | // Only works if 'x: 'y:
60 | | demand_y(x, y, x.get())
61 | | });
| |_____^
|
= note: defining type: DefId(0/1:18 ~ propagate_approximated_ref[317d]::supply[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's, 't0, 't1, 't2, 't3> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7696))) std::cell::Cell<&'_#1r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7697))) u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't0(7698))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't1(7699))) &'_#2r u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't2(9524))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7697))) u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't3(9525))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't1(7699))) u32>))
]
= note: number of external vids: 3
= note: where '_#1r: '_#2r
note: No external requirements
--> $DIR/propagate-approximated-ref.rs:57:1
|
57 | / fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
58 | | establish_relationships(&cell_a, &cell_b, |_outlives1, _outlives2, x, y| {
59 | | // Only works if 'x: 'y:
60 | | demand_y(x, y, x.get())
61 | | });
62 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_approximated_ref[317d]::supply[0]) with substs []

View file

@ -0,0 +1,47 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test a case where we fail to approximate one of the regions and
// hence report an error while checking the closure.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// Callee knows that:
//
// 'b: 'y
//
// but this doesn't really help us in proving that `'x: 'y`, so closure gets an error.
fn establish_relationships<'a, 'b, F>(_cell_a: &Cell<&'a u32>, _cell_b: &Cell<&'b u32>, _closure: F)
where
F: for<'x, 'y> FnMut(
&Cell<&'y &'b u32>, // shows that 'b: 'y
&Cell<&'x u32>,
&Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_cell_x: &Cell<&'x u32>, _cell_y: &Cell<&'y u32>, _y: &'y u32) {}
#[rustc_regions]
fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
// Only works if 'x: 'y:
demand_y(x, y, x.get())
//~^ WARN not reporting region error due to -Znll
//~| ERROR free region `'_#6r` does not outlive free region `'_#4r`
});
}
fn main() {}

View file

@ -0,0 +1,46 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-approximated-to-empty.rs:41:9
|
41 | demand_y(x, y, x.get())
| ^^^^^^^^^^^^^^^^^^^^^^^
error: free region `'_#6r` does not outlive free region `'_#4r`
--> $DIR/propagate-approximated-to-empty.rs:41:21
|
41 | demand_y(x, y, x.get())
| ^
note: External requirements
--> $DIR/propagate-approximated-to-empty.rs:39:47
|
39 | establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
| _______________________________________________^
40 | | // Only works if 'x: 'y:
41 | | demand_y(x, y, x.get())
42 | | //~^ WARN not reporting region error due to -Znll
43 | | //~| ERROR free region `'_#6r` does not outlive free region `'_#4r`
44 | | });
| |_____^
|
= note: defining type: DefId(0/1:18 ~ propagate_approximated_to_empty[317d]::supply[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's, 't0, 't1, 't2> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7695))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7696))) &'_#1r u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't0(7697))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't1(9522))) u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't2(9523))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7696))) u32>))
]
= note: number of external vids: 2
note: No external requirements
--> $DIR/propagate-approximated-to-empty.rs:38:1
|
38 | / fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
39 | | establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
40 | | // Only works if 'x: 'y:
41 | | demand_y(x, y, x.get())
... |
44 | | });
45 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_approximated_to_empty[317d]::supply[0]) with substs []
error: aborting due to previous error

View file

@ -0,0 +1,46 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test a case where we are forced to approximate one end-point with
// `'static`. Note that `'static` shows up in the stderr output as `'0`.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// Callee knows that:
//
// 'x: 'a
//
// so the only way we can ensure that `'x: 'y` is to show that
// `'a: 'static`.
fn establish_relationships<'a, 'b, F>(_cell_a: &Cell<&'a u32>, _cell_b: &Cell<&'b u32>, _closure: F)
where
F: for<'x, 'y> FnMut(
&Cell<&'a &'x u32>, // shows that 'x: 'a
&Cell<&'x u32>,
&Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_cell_x: &Cell<&'x u32>, _cell_y: &Cell<&'y u32>, _y: &'y u32) {}
#[rustc_regions]
fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
// Only works if 'x: 'y:
demand_y(x, y, x.get())
});
}
fn main() {}

View file

@ -0,0 +1,36 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-approximated-to-static.rs:42:9
|
42 | demand_y(x, y, x.get())
| ^^^^^^^^^^^^^^^^^^^^^^^
note: External requirements
--> $DIR/propagate-approximated-to-static.rs:40:47
|
40 | establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
| _______________________________________________^
41 | | // Only works if 'x: 'y:
42 | | demand_y(x, y, x.get())
43 | | });
| |_____^
|
= note: defining type: DefId(0/1:18 ~ propagate_approximated_to_static[317d]::supply[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's, 't0, 't1, 't2> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7695))) std::cell::Cell<&'_#1r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7696))) u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't0(7697))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(7696))) u32>, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't1(9522))) std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 't2(9523))) u32>))
]
= note: number of external vids: 2
= note: where '_#1r: '_#0r
note: No external requirements
--> $DIR/propagate-approximated-to-static.rs:39:1
|
39 | / fn supply<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
40 | | establish_relationships(&cell_a, &cell_b, |_outlives, x, y| {
41 | | // Only works if 'x: 'y:
42 | | demand_y(x, y, x.get())
43 | | });
44 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_approximated_to_static[317d]::supply[0]) with substs []

View file

@ -0,0 +1,52 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// A simpler variant of `outlives-from-argument` where cells are
// passed by value.
//
// This is simpler because there are no "extraneous" region
// relationships. In the 'main' variant, there are a number of
// anonymous regions as well.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// Callee knows that:
//
// 'x: 'a
// 'b: 'y
//
// so if we are going to ensure that `'x: 'y`, then `'a: 'b` must
// hold.
fn establish_relationships<'a, 'b, F>(_cell_a: Cell<&'a u32>, _cell_b: Cell<&'b u32>, _closure: F)
where
F: for<'x, 'y> FnMut(
Cell<&'a &'x u32>, // shows that 'x: 'a
Cell<&'y &'b u32>, // shows that 'b: 'y
Cell<&'x u32>,
Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_outlives1: Cell<&&'x u32>, _outlives2: Cell<&'y &u32>, _y: &'y u32) {}
#[rustc_regions]
fn test<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
establish_relationships(cell_a, cell_b, |outlives1, outlives2, x, y| {
// Only works if 'x: 'y:
demand_y(outlives1, outlives2, x.get())
});
}
fn main() {}

View file

@ -0,0 +1,36 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-approximated-val.rs:48:9
|
48 | demand_y(outlives1, outlives2, x.get())
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
note: External requirements
--> $DIR/propagate-approximated-val.rs:46:45
|
46 | establish_relationships(cell_a, cell_b, |outlives1, outlives2, x, y| {
| _____________________________________________^
47 | | // Only works if 'x: 'y:
48 | | demand_y(outlives1, outlives2, x.get())
49 | | });
| |_____^
|
= note: defining type: DefId(0/1:18 ~ propagate_approximated_val[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's> extern "rust-call" fn((std::cell::Cell<&'_#1r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9519))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9520))) &'_#2r u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9519))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9520))) u32>))
]
= note: number of external vids: 3
= note: where '_#1r: '_#2r
note: No external requirements
--> $DIR/propagate-approximated-val.rs:45:1
|
45 | / fn test<'a, 'b>(cell_a: Cell<&'a u32>, cell_b: Cell<&'b u32>) {
46 | | establish_relationships(cell_a, cell_b, |outlives1, outlives2, x, y| {
47 | | // Only works if 'x: 'y:
48 | | demand_y(outlives1, outlives2, x.get())
49 | | });
50 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_approximated_val[317d]::test[0]) with substs []

View file

@ -0,0 +1,59 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test where we might in theory be able to see that the relationship
// between two bound regions is true within closure and hence have no
// need to propagate; but in fact we do because identity of free
// regions is erased.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
use std::cell::Cell;
// In theory, callee knows that:
//
// 'x: 'a
// 'a: 'y
//
// and hence could satisfy that `'x: 'y` locally. However, in our
// checking, we ignore the precise free regions that come into the
// region and just assign each position a distinct universally bound
// region. Hence, we propagate a constraint to our caller that will
// wind up being solvable.
fn establish_relationships<'a, F>(
_cell_a: Cell<&'a u32>,
_closure: F,
) where
F: for<'x, 'y> FnMut(
Cell<&'a &'x u32>, // shows that 'x: 'a
Cell<&'y &'a u32>, // shows that 'a: 'y
Cell<&'x u32>,
Cell<&'y u32>,
),
{
}
fn demand_y<'x, 'y>(_cell_x: Cell<&'x u32>, _cell_y: Cell<&'y u32>, _y: &'y u32) {}
#[rustc_regions]
fn supply<'a>(cell_a: Cell<&'a u32>) {
establish_relationships(
cell_a,
|_outlives1, _outlives2, x, y| {
// Only works if 'x: 'y:
let p = x.get();
demand_y(x, y, p)
},
);
}
fn main() {}

View file

@ -0,0 +1,37 @@
warning: not reporting region error due to -Znll
--> $DIR/propagate-despite-same-free-region.rs:53:21
|
53 | let p = x.get();
| ^^^^^^^
note: External requirements
--> $DIR/propagate-despite-same-free-region.rs:51:9
|
51 | / |_outlives1, _outlives2, x, y| {
52 | | // Only works if 'x: 'y:
53 | | let p = x.get();
54 | | demand_y(x, y, p)
55 | | },
| |_________^
|
= note: defining type: DefId(0/1:16 ~ propagate_despite_same_free_region[317d]::supply[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's> extern "rust-call" fn((std::cell::Cell<&'_#1r &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9518))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9519))) &'_#2r u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(9518))) u32>, std::cell::Cell<&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(9519))) u32>))
]
= note: number of external vids: 3
= note: where '_#1r: '_#2r
note: No external requirements
--> $DIR/propagate-despite-same-free-region.rs:48:1
|
48 | / fn supply<'a>(cell_a: Cell<&'a u32>) {
49 | | establish_relationships(
50 | | cell_a,
51 | | |_outlives1, _outlives2, x, y| {
... |
56 | | );
57 | | }
| |_^
|
= note: defining type: DefId(0/0:6 ~ propagate_despite_same_free_region[317d]::supply[0]) with substs []

View file

@ -0,0 +1,26 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Basic test for free regions in the NLL code. This test ought to
// report an error due to a reborrowing constraint. Right now, we get
// a variety of errors from the older, AST-based machinery (notably
// borrowck), and then we get the NLL error at the end.
// compile-flags:-Znll -Zborrowck=mir
fn foo<'a>(x: &'a u32) -> &'static u32
where 'static: 'a
{
&*x
//~^ WARN not reporting region error due to -Znll
//~| ERROR free region `'a` does not outlive free region `'static`
}
fn main() { }

View file

@ -0,0 +1,14 @@
warning: not reporting region error due to -Znll
--> $DIR/region-ebr-does-not-outlive-static.rs:21:5
|
21 | &*x
| ^^^
error: free region `'a` does not outlive free region `'static`
--> $DIR/region-ebr-does-not-outlive-static.rs:21:5
|
21 | &*x
| ^^^
error: aborting due to previous error

View file

@ -0,0 +1,25 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Basic test for free regions in the NLL code. This test ought to
// report an error due to a reborrowing constraint. Right now, we get
// a variety of errors from the older, AST-based machinery (notably
// borrowck), and then we get the NLL error at the end.
// compile-flags:-Znll
fn foo(x: &u32) -> &'static u32 {
&*x
//~^ WARN not reporting region error due to -Znll
//~| ERROR `*x` does not live long enough
//~| ERROR free region `'_#1r` does not outlive free region `'static`
}
fn main() { }

View file

@ -0,0 +1,32 @@
warning: not reporting region error due to -Znll
--> $DIR/region-lbr-anon-does-not-outlive-static.rs:19:5
|
19 | &*x
| ^^^
error[E0597]: `*x` does not live long enough
--> $DIR/region-lbr-anon-does-not-outlive-static.rs:19:6
|
19 | &*x
| ^^ does not live long enough
|
= note: borrowed value must be valid for the static lifetime...
note: ...but borrowed value is only valid for the anonymous lifetime #1 defined on the function body at 18:1
--> $DIR/region-lbr-anon-does-not-outlive-static.rs:18:1
|
18 | / fn foo(x: &u32) -> &'static u32 {
19 | | &*x
20 | | //~^ WARN not reporting region error due to -Znll
21 | | //~| ERROR `*x` does not live long enough
22 | | //~| ERROR free region `'_#1r` does not outlive free region `'static`
23 | | }
| |_^
error: free region `'_#1r` does not outlive free region `'static`
--> $DIR/region-lbr-anon-does-not-outlive-static.rs:19:5
|
19 | &*x
| ^^^
error: aborting due to 2 previous errors

View file

@ -0,0 +1,24 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Basic test for free regions in the NLL code. This test ought to
// report an error due to a reborrowing constraint. Right now, we get
// a variety of errors from the older, AST-based machinery (notably
// borrowck), and then we get the NLL error at the end.
// compile-flags:-Znll -Zborrowck=mir
fn foo<'a>(x: &'a u32) -> &'static u32 {
&*x
//~^ WARN not reporting region error due to -Znll
//~| ERROR free region `'_#1r` does not outlive free region `'static`
}
fn main() { }

View file

@ -0,0 +1,14 @@
warning: not reporting region error due to -Znll
--> $DIR/region-lbr-named-does-not-outlive-static.rs:19:5
|
19 | &*x
| ^^^
error: free region `'_#1r` does not outlive free region `'static`
--> $DIR/region-lbr-named-does-not-outlive-static.rs:19:5
|
19 | &*x
| ^^^
error: aborting due to previous error

View file

@ -13,12 +13,12 @@
// a variety of errors from the older, AST-based machinery (notably
// borrowck), and then we get the NLL error at the end.
// compile-flags:-Znll
// compile-flags:-Znll -Zborrowck=mir
fn foo<'a, 'b>(x: &'a u32, y: &'b u32) -> &'b u32 {
&*x //~ ERROR free region `'a` does not outlive `'b`
//~^ ERROR `*x` does not live long enough
//~| WARN not reporting region error due to -Znll
&*x
//~^ WARN not reporting region error due to -Znll
//~| ERROR free region `'_#1r` does not outlive free region `'_#2r`
}
fn main() { }

View file

@ -0,0 +1,14 @@
warning: not reporting region error due to -Znll
--> $DIR/region-lbr1-does-not-outlive-ebr2.rs:19:5
|
19 | &*x
| ^^^
error: free region `'_#1r` does not outlive free region `'_#2r`
--> $DIR/region-lbr1-does-not-outlive-ebr2.rs:19:5
|
19 | &*x
| ^^^
error: aborting due to previous error

View file

@ -0,0 +1,23 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Basic test for free regions in the NLL code. This test does not
// report an error because of the (implied) bound that `'b: 'a`.
// compile-flags:-Znll
// must-compile-successfully
#![allow(warnings)]
fn foo<'a, 'b>(x: &'a &'b u32) -> &'a u32 {
&**x
}
fn main() { }

View file

@ -0,0 +1,34 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
// Test closure that takes two references and is supposed to return
// the first, but actually returns the second. This should fail within
// the closure.
// compile-flags:-Znll -Zborrowck=mir -Zverbose
#![feature(rustc_attrs)]
#[rustc_regions]
fn test() {
expect_sig(|a, b| b); // ought to return `a`
//~^ WARN not reporting region error due to -Znll
//~| ERROR free region `'_#3r` does not outlive free region `'_#2r`
}
fn expect_sig<F>(f: F) -> F
where F: for<'a> FnMut(&'a i32, &i32) -> &'a i32
{
f
}
fn deref(_p: &i32) { }
fn main() { }

View file

@ -0,0 +1,38 @@
warning: not reporting region error due to -Znll
--> $DIR/return-wrong-bound-region.rs:21:23
|
21 | expect_sig(|a, b| b); // ought to return `a`
| ^
error: free region `'_#3r` does not outlive free region `'_#2r`
--> $DIR/return-wrong-bound-region.rs:21:23
|
21 | expect_sig(|a, b| b); // ought to return `a`
| ^
note: External requirements
--> $DIR/return-wrong-bound-region.rs:21:16
|
21 | expect_sig(|a, b| b); // ought to return `a`
| ^^^^^^^^
|
= note: defining type: DefId(0/1:9 ~ return_wrong_bound_region[317d]::test[0]::{{closure}}[0]) with closure substs [
i16,
for<'r, 's> extern "rust-call" fn((&ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7661))) i32, &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 's(8630))) i32)) -> &ReLateBound(DebruijnIndex { depth: 1 }, BrNamed(crate0:DefIndex(0:0), 'r(7661))) i32
]
= note: number of external vids: 1
note: No external requirements
--> $DIR/return-wrong-bound-region.rs:20:1
|
20 | / fn test() {
21 | | expect_sig(|a, b| b); // ought to return `a`
22 | | //~^ WARN not reporting region error due to -Znll
23 | | //~| ERROR free region `'_#3r` does not outlive free region `'_#2r`
24 | | }
| |_^
|
= note: defining type: DefId(0/0:3 ~ return_wrong_bound_region[317d]::test[0]) with substs []
error: aborting due to previous error

View file

@ -0,0 +1,87 @@
note: External requirements
--> $DIR/via-upvar-nested.rs:24:28
|
24 | let closure1 = || p = &y;
| ^^^^^^^^^
|
= note: _0: ()
= note: _1: &mut [closure@$DIR/via-upvar-nested.rs:24:28: 24:37 p:&mut &i32, y:&i32]
note: External requirements
--> $DIR/via-upvar-nested.rs:23:27
|
23 | let mut closure = || {
| ___________________________^
24 | | let closure1 = || p = &y;
25 | | closure1();
26 | | };
| |_________^
|
= note: _0: ()
= note: _1: &mut [closure@$DIR/via-upvar-nested.rs:23:27: 26:10 p:&mut &i32, y:&i32]
= note: where '_#1r: '_#2r
error[E0596]: cannot borrow immutable item `closure1` as mutable (Mir)
--> $DIR/via-upvar-nested.rs:25:13
|
25 | closure1();
| ^^^^^^^^ cannot borrow as mutable
error[E0597]: `**y` does not live long enough (Ast)
--> $DIR/via-upvar-nested.rs:24:36
|
24 | let closure1 = || p = &y;
| -- ^ does not live long enough
| |
| capture occurs here
...
29 | }
| - borrowed value only lives until here
...
32 | }
| - borrowed value needs to live until here
error[E0596]: cannot borrow immutable local variable `closure1` as mutable (Ast)
--> $DIR/via-upvar-nested.rs:25:13
|
24 | let closure1 = || p = &y;
| -------- consider changing this to `mut closure1`
25 | closure1();
| ^^^^^^^^ cannot borrow mutably
note: No external requirements
--> $DIR/via-upvar-nested.rs:16:1
|
16 | / fn test() {
17 | | let x = 44;
18 | | let mut p = &x;
19 | |
... |
31 | | deref(p);
32 | | }
| |_^
error[E0597]: borrowed value does not live long enough (Mir)
--> $DIR/via-upvar-nested.rs:29:6
|
21 | let y = 22;
| - temporary value created here
...
29 | }
| ^ temporary value dropped here while still borrowed
|
= note: consider using a `let` binding to increase its lifetime
error[E0502]: cannot borrow `(*p)` as immutable because it is also borrowed as mutable (Mir)
--> $DIR/via-upvar-nested.rs:31:11
|
23 | let mut closure = || {
| -- mutable borrow occurs here
24 | let closure1 = || p = &y;
| - previous borrow occurs due to use of `(*p)` in closure
...
31 | deref(p);
| ^ immutable borrow occurs here
error: aborting due to 5 previous errors

View file

@ -1,31 +0,0 @@
warning: not reporting region error due to -Znll
--> $DIR/named-region-basic.rs:19:5
|
19 | &*x //~ ERROR free region `'a` does not outlive `'b`
| ^^^
error[E0597]: `*x` does not live long enough
--> $DIR/named-region-basic.rs:19:6
|
19 | &*x //~ ERROR free region `'a` does not outlive `'b`
| ^^ does not live long enough
|
= note: borrowed value must be valid for the static lifetime...
note: ...but borrowed value is only valid for the lifetime 'a as defined on the function body at 18:1
--> $DIR/named-region-basic.rs:18:1
|
18 | / fn foo<'a, 'b>(x: &'a u32, y: &'b u32) -> &'b u32 {
19 | | &*x //~ ERROR free region `'a` does not outlive `'b`
20 | | //~^ ERROR `*x` does not live long enough
21 | | //~| WARN not reporting region error due to -Znll
22 | | }
| |_^
error: free region `'a` does not outlive `'b`
--> $DIR/named-region-basic.rs:19:5
|
19 | &*x //~ ERROR free region `'a` does not outlive `'b`
| ^^^
error: aborting due to 2 previous errors