Auto merge of #55069 - matthewjasper:explain-free-region-liveness, r=nikomatsakis

[NLL] Use new region infer errors when explaining borrows

Use the new free region infer errors for explaining borrows

This gives at least some explanation for why a borrow is expected to
last for a certain free region. Also:

* Reports E0373: "closure may outlive the current function" with NLL.
* Special cases the case of returning a reference to (or value referencing) a local variable or temporary (E0515).
* Special case assigning a reference to a local variable in a closure to a captured variable. (E0521)

Closes #51026 - `regions-nested-fns-2.rs` isn't changed to that diagnostic, since that would not be the correct error here.
Closes #51169
cc #53882 - The error is (IMO) better now, but it could be better when we trace lifetimes in these error messages.

r? @nikomatsakis cc @pnkfelix
This commit is contained in:
bors 2018-10-21 12:04:25 +00:00
commit 31b97f789f
138 changed files with 1939 additions and 1837 deletions

View file

@ -1,18 +1,11 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-11681.rs:22:20
error[E0515]: cannot return value referencing temporary value
--> $DIR/issue-11681.rs:23:10
|
LL | let testValue = &Test; //~ ERROR borrowed value does not live long enough
| ^^^^ creates a temporary which is freed while still in use
| ---- temporary value created here
LL | return testValue;
LL | }
| - temporary value is freed at the end of this statement
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 21:15...
--> $DIR/issue-11681.rs:21:15
|
LL | fn createTest<'a>() -> &'a Test {
| ^^
| ^^^^^^^^^ returns a value referencing data owned by the current function
error: aborting due to previous error
For more information about this error, try `rustc --explain E0716`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,18 +1,11 @@
error[E0597]: `*b` does not live long enough
--> $DIR/issue-12470.rs:38:18
error[E0515]: cannot return value referencing local data `*b`
--> $DIR/issue-12470.rs:39:5
|
LL | let bb: &B = &*b; //~ ERROR does not live long enough
| ^^^ borrowed value does not live long enough
| --- `*b` is borrowed here
LL | make_a(bb)
LL | }
| - `*b` dropped here while still borrowed
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 36:16...
--> $DIR/issue-12470.rs:36:16
|
LL | fn make_make_a<'a>() -> A<'a> {
| ^^
| ^^^^^^^^^^ returns a value referencing data owned by the current function
error: aborting due to previous error
For more information about this error, try `rustc --explain E0597`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,18 +1,14 @@
error[E0597]: `rawLines` does not live long enough
error[E0515]: cannot return value referencing local variable `rawLines`
--> $DIR/issue-13497-2.rs:13:5
|
LL | rawLines //~ ERROR `rawLines` does not live long enough
| ^^^^^^^^ borrowed value does not live long enough
LL | .iter().map(|l| l.trim()).collect()
LL | }
| - `rawLines` dropped here while still borrowed
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 11:24...
--> $DIR/issue-13497-2.rs:11:24
|
LL | fn read_lines_borrowed<'a>() -> Vec<&'a str> {
| ^^
LL | rawLines //~ ERROR `rawLines` does not live long enough
| ^-------
| |
| _____`rawLines` is borrowed here
| |
LL | | .iter().map(|l| l.trim()).collect()
| |___________________________________________^ returns a value referencing data owned by the current function
error: aborting due to previous error
For more information about this error, try `rustc --explain E0597`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,16 +1,15 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-17545.rs:17:10
|
LL | &id(()), //~ ERROR borrowed value does not live long enough
| ^^^^^^ creates a temporary which is freed while still in use
LL | ));
| - temporary value is freed at the end of this statement
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 15:12...
--> $DIR/issue-17545.rs:15:12
|
LL | pub fn foo<'a, F: Fn(&'a ())>(bar: F) {
| ^^
LL | pub fn foo<'a, F: Fn(&'a ())>(bar: F) {
| -- lifetime `'a` defined here
LL | / bar.call((
LL | | &id(()), //~ ERROR borrowed value does not live long enough
| | ^^^^^^ 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

View file

@ -1,13 +1,12 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-17718-constants-not-static.rs:15:31
error[E0515]: cannot return reference to temporary value
--> $DIR/issue-17718-constants-not-static.rs:15:30
|
LL | fn foo() -> &'static usize { &id(FOO) }
| ^^^^^^^ - temporary value is freed at the end of this statement
| |
| creates a temporary which is freed while still in use
|
= note: borrowed value must be valid for the static lifetime...
| ^-------
| ||
| |temporary value created here
| 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 E0716`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -54,12 +54,13 @@ error[E0597]: `p` does not live long enough
--> $DIR/issue-18118.rs:18:9
|
LL | &p //~ ERROR `p` does not live long enough
| ^^ borrowed value does not live long enough
| ^^
| |
| borrowed value does not live long enough
| using this value as a constant requires that `p` is borrowed for `'static`
LL | //~^ ERROR let bindings in constants are unstable
LL | };
| - `p` dropped here while still borrowed
|
= note: borrowed value must be valid for the static lifetime...
error: aborting due to 6 previous errors

View file

@ -1,19 +1,21 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-27592.rs:26:27
error[E0515]: cannot return value referencing temporary value
--> $DIR/issue-27592.rs:26:14
|
LL | write(|| format_args!("{}", String::from("Hello world")));
| ^^^^ - temporary value is freed at the end of this statement
| |
| creates a temporary which is freed while still in use
| ^^^^^^^^^^^^^^^^^^^---------------------------^
| | |
| | temporary value created here
| returns a value referencing data owned by the current function
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-27592.rs:26:33
error[E0515]: cannot return value referencing temporary value
--> $DIR/issue-27592.rs:26:14
|
LL | write(|| format_args!("{}", String::from("Hello world")));
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement
| |
| creates a temporary which is freed while still in use
| ^^^^^^^^^^^^^----^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| | |
| | temporary value created here
| returns a value referencing data owned by the current function
error: aborting due to 2 previous errors
For more information about this error, try `rustc --explain E0716`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,20 +1,12 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-30438-a.rs:22:17
error[E0515]: cannot return reference to temporary value
--> $DIR/issue-30438-a.rs:22:16
|
LL | return &Test { s: &self.s};
| ^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement
| |
| creates a temporary which is freed while still in use
|
note: borrowed value must be valid for the anonymous lifetime #1 defined on the method body at 21:5...
--> $DIR/issue-30438-a.rs:21:5
|
LL | / fn index(&self, _: usize) -> &Self::Output {
LL | | return &Test { s: &self.s};
LL | | //~^ ERROR: borrowed value does not live long enough
LL | | }
| |_____^
| ^------------------
| ||
| |temporary value created here
| 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 E0716`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,21 +1,12 @@
error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-30438-b.rs:23:10
error[E0515]: cannot return reference to temporary value
--> $DIR/issue-30438-b.rs:23:9
|
LL | &Test { s: &self.s}
| ^^^^^^^^^^^^^^^^^^ creates a temporary which is freed while still in use
LL | //~^ ERROR: borrowed value does not live long enough
LL | }
| - temporary value is freed at the end of this statement
|
note: borrowed value must be valid for the anonymous lifetime #1 defined on the method body at 22:5...
--> $DIR/issue-30438-b.rs:22:5
|
LL | / fn index(&self, _: usize) -> &Self::Output {
LL | | &Test { s: &self.s}
LL | | //~^ ERROR: borrowed value does not live long enough
LL | | }
| |_____^
| ^------------------
| ||
| |temporary value created here
| 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 E0716`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -1,21 +1,9 @@
error[E0597]: `x` does not live long enough
error[E0515]: cannot return reference to local variable `x`
--> $DIR/issue-30438-c.rs:19:5
|
LL | fn silly<'y, 'z>(_s: &'y Test<'z>) -> &'y <Test<'z> as Trait>::Out where 'z: 'static {
| -- -- also has lifetime `'y`
| |
| has lifetime `'y`
LL | let x = Test { s: "this cannot last" };
LL | &x
| ^^ `x` would have to be valid for `'y`...
LL | //~^ ERROR: `x` does not live long enough
LL | }
| - ...but `x` will be dropped here, when the function `silly` returns
|
= help: use data from the highlighted arguments which match the `'y` lifetime of the return type
= note: functions cannot return a borrow to data owned within the function's scope, functions can only return borrows to data passed as arguments
= note: to learn more, visit <https://doc.rust-lang.org/book/second-edition/ch04-02-references-and-borrowing.html#dangling-references>
| ^^ 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 E0597`.
For more information about this error, try `rustc --explain E0515`.

View file

@ -15,24 +15,25 @@ LL | id(Box::new(|| *v))
| cannot move out of `*v` which is behind a `&` reference
| cannot move
error[E0597]: `v` does not live long enough
--> $DIR/issue-4335.rs:16:21
error[E0373]: closure may outlive the current function, but it borrows `v`, which is owned by the current function
--> $DIR/issue-4335.rs:16:17
|
LL | id(Box::new(|| *v))
| -- ^ borrowed value does not live long enough
| ^^ - `v` is borrowed here
| |
| value captured here
...
LL | }
| - `v` dropped here while still borrowed
| may outlive borrowed value `v`
|
note: borrowed value must be valid for the lifetime 'r as defined on the function body at 15:6...
--> $DIR/issue-4335.rs:15:6
note: closure is returned here
--> $DIR/issue-4335.rs:16:5
|
LL | fn f<'r, T>(v: &'r T) -> Box<FnMut() -> T + 'r> {
| ^^
LL | id(Box::new(|| *v))
| ^^^^^^^^^^^^^^^^^^^
help: to force the closure to take ownership of `v` (and any other referenced variables), use the `move` keyword
|
LL | id(Box::new(move || *v))
| ^^^^^^^
error: aborting due to 3 previous errors
Some errors occurred: E0507, E0597.
For more information about an error, try `rustc --explain E0507`.
Some errors occurred: E0373, E0507.
For more information about an error, try `rustc --explain E0373`.

View file

@ -2,11 +2,11 @@ error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-44373.rs:15:42
|
LL | let _val: &'static [&'static u32] = &[&FOO]; //~ ERROR borrowed value does not live long enough
| ^^^^^^ creates a temporary which is freed while still in use
| ----------------------- ^^^^^^ creates a temporary which is freed while still in use
| |
| type annotation requires that borrow lasts for `'static`
LL | }
| - temporary value is freed at the end of this statement
|
= note: borrowed value must be valid for the static lifetime...
error: aborting due to previous error

View file

@ -1,17 +1,14 @@
warning[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:63:5
|
LL | fn scribbled<'a>(s: Scribble<'a>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *s.0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^
| ^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 62:14...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:62:14
|
LL | fn scribbled<'a>(s: Scribble<'a>) -> &'a mut u32 {
| ^^
= warning: This error has been downgraded to a warning for backwards compatibility with previous releases.
It represents potential unsoundness in your code.
This warning will become a hard error in the future.
@ -19,17 +16,14 @@ LL | fn scribbled<'a>(s: Scribble<'a>) -> &'a mut u32 {
warning[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:73:5
|
LL | fn boxed_scribbled<'a>(s: Box<Scribble<'a>>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *(*s).0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^^^^
| ^^^^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 72:20...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:72:20
|
LL | fn boxed_scribbled<'a>(s: Box<Scribble<'a>>) -> &'a mut u32 {
| ^^
= warning: This error has been downgraded to a warning for backwards compatibility with previous releases.
It represents potential unsoundness in your code.
This warning will become a hard error in the future.
@ -37,17 +31,14 @@ LL | fn boxed_scribbled<'a>(s: Box<Scribble<'a>>) -> &'a mut u32 {
warning[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:83:5
|
LL | fn boxed_boxed_scribbled<'a>(s: Box<Box<Scribble<'a>>>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *(**s).0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^^^^^
| ^^^^^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 82:26...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:82:26
|
LL | fn boxed_boxed_scribbled<'a>(s: Box<Box<Scribble<'a>>>) -> &'a mut u32 {
| ^^
= warning: This error has been downgraded to a warning for backwards compatibility with previous releases.
It represents potential unsoundness in your code.
This warning will become a hard error in the future.

View file

@ -1,47 +1,35 @@
error[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:63:5
|
LL | fn scribbled<'a>(s: Scribble<'a>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *s.0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^
| ^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 62:14...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:62:14
|
LL | fn scribbled<'a>(s: Scribble<'a>) -> &'a mut u32 {
| ^^
error[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:73:5
|
LL | fn boxed_scribbled<'a>(s: Box<Scribble<'a>>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *(*s).0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^^^^
| ^^^^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 72:20...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:72:20
|
LL | fn boxed_scribbled<'a>(s: Box<Scribble<'a>>) -> &'a mut u32 {
| ^^
error[E0713]: borrow may still be in use when destructor runs
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:83:5
|
LL | fn boxed_boxed_scribbled<'a>(s: Box<Box<Scribble<'a>>>) -> &'a mut u32 {
| -- lifetime `'a` defined here
LL | &mut *(**s).0 //[nll]~ ERROR borrow may still be in use when destructor runs [E0713]
| ^^^^^^^^^^^^^
| ^^^^^^^^^^^^^ returning this value requires that `*s.0` is borrowed for `'a`
...
LL | }
| - here, drop of `s` needs exclusive access to `*s.0`, because the type `Scribble<'_>` implements the `Drop` trait
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 82:26...
--> $DIR/issue-45696-scribble-on-boxed-borrow.rs:82:26
|
LL | fn boxed_boxed_scribbled<'a>(s: Box<Box<Scribble<'a>>>) -> &'a mut u32 {
| ^^
error: aborting due to 3 previous errors

View file

@ -2,12 +2,13 @@ error[E0597]: `a` does not live long enough
--> $DIR/issue-46036.rs:19:24
|
LL | let foo = Foo { x: &a }; //~ ERROR E0597
| ^^ borrowed value does not live long enough
| ^^
| |
| borrowed value does not live long enough
| requires that `a` is borrowed for `'static`
LL | loop { }
LL | }
| - `a` dropped here while still borrowed
|
= note: borrowed value must be valid for the static lifetime...
error: aborting due to previous error

View file

@ -14,7 +14,7 @@ fn foo() -> &'static u32 {
let x = 0;
&x
//~^ ERROR `x` does not live long enough (Ast) [E0597]
//~| ERROR `x` does not live long enough (Mir) [E0597]
//~| ERROR cannot return reference to local variable `x` (Mir) [E0515]
}
fn main() { }

View file

@ -9,17 +9,13 @@ LL | }
|
= note: borrowed value must be valid for the static lifetime...
error[E0597]: `x` does not live long enough (Mir)
error[E0515]: cannot return reference to local variable `x` (Mir)
--> $DIR/issue-46471.rs:15:5
|
LL | &x
| ^^ borrowed value does not live long enough
...
LL | }
| - `x` dropped here while still borrowed
|
= note: borrowed value must be valid for the static lifetime...
| ^^ returns a reference to data owned by the current function
error: aborting due to 2 previous errors
For more information about this error, try `rustc --explain E0597`.
Some errors occurred: E0515, E0597.
For more information about an error, try `rustc --explain E0515`.

View file

@ -13,7 +13,7 @@
fn bar<'a>() -> &'a mut u32 {
&mut 4
//~^ ERROR borrowed value does not live long enough (Ast) [E0597]
//~| ERROR temporary value dropped while borrowed (Mir) [E0716]
//~| ERROR cannot return reference to temporary value (Mir) [E0515]
}
fn main() { }

View file

@ -13,22 +13,16 @@ note: borrowed value must be valid for the lifetime 'a as defined on the functio
LL | fn bar<'a>() -> &'a mut u32 {
| ^^
error[E0716]: temporary value dropped while borrowed (Mir)
--> $DIR/issue-46472.rs:14:10
error[E0515]: cannot return reference to temporary value (Mir)
--> $DIR/issue-46472.rs:14:5
|
LL | &mut 4
| ^ creates a temporary which is freed while still in use
...
LL | }
| - temporary value is freed at the end of this statement
|
note: borrowed value must be valid for the lifetime 'a as defined on the function body at 13:8...
--> $DIR/issue-46472.rs:13:8
|
LL | fn bar<'a>() -> &'a mut u32 {
| ^^
| ^^^^^-
| | |
| | temporary value created here
| returns a reference to data owned by the current function
error: aborting due to 2 previous errors
Some errors occurred: E0597, E0716.
For more information about an error, try `rustc --explain E0597`.
Some errors occurred: E0515, E0597.
For more information about an error, try `rustc --explain E0515`.

View file

@ -2,11 +2,10 @@ error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-47184.rs:14:44
|
LL | let _vec: Vec<&'static String> = vec![&String::new()];
| ^^^^^^^^^^^^^ - temporary value is freed at the end of this statement
| |
| creates a temporary which is freed while still in use
|
= note: borrowed value must be valid for the static lifetime...
| -------------------- ^^^^^^^^^^^^^ - temporary value is freed at the end of this statement
| | |
| | creates a temporary which is freed while still in use
| type annotation requires that borrow lasts for `'static`
error: aborting due to previous error

View file

@ -2,11 +2,12 @@ error[E0716]: temporary value dropped while borrowed
--> $DIR/issue-52049.rs:16:10
|
LL | foo(&unpromotable(5u32));
| ^^^^^^^^^^^^^^^^^^ creates a temporary which is freed while still in use
| -----^^^^^^^^^^^^^^^^^^-
| | |
| | creates a temporary which is freed while still in use
| argument requires that borrow lasts for `'static`
LL | }
| - temporary value is freed at the end of this statement
|
= note: borrowed value must be valid for the static lifetime...
error: aborting due to previous error