Account for owning item lifetimes in suggestion and annotate tests as run-rustfix

```
error: lifetime may not live long enough
  --> $DIR/lt-ref-self.rs:12:9
   |
LL |     fn ref_self(&self, f: &u32) -> &u32 {
   |                 -         - let's call the lifetime of this reference `'1`
   |                 |
   |                 let's call the lifetime of this reference `'2`
LL |         f
   |         ^ method was supposed to return data with lifetime `'2` but it is returning data with lifetime `'1`
   |
help: consider introducing a named lifetime parameter and update trait if needed
   |
LL |     fn ref_self<'b>(&'b self, f: &'b u32) -> &'b u32 {
   |                ++++  ++           ++          ++
```
This commit is contained in:
Esteban Küber 2024-05-07 19:35:25 +00:00
parent 120049fab4
commit d1d585d039
27 changed files with 404 additions and 59 deletions

View File

@ -1,4 +1,5 @@
use hir::GenericParamKind;
use rustc_data_structures::fx::FxHashSet;
use rustc_errors::{
codes::*, Applicability, Diag, DiagMessage, DiagStyledString, EmissionGuarantee, IntoDiagArg,
MultiSpan, SubdiagMessageOp, Subdiagnostic,
@ -362,13 +363,27 @@ fn add_to_diag_with<G: EmissionGuarantee, F: SubdiagMessageOp<G>>(
let node = self.tcx.hir_node_by_def_id(anon_reg.def_id);
let is_impl = matches!(&node, hir::Node::ImplItem(_));
let generics = match node {
let (generics, parent_generics) = match node {
hir::Node::Item(&hir::Item {
kind: hir::ItemKind::Fn(_, ref generics, ..),
..
})
| hir::Node::TraitItem(&hir::TraitItem { ref generics, .. })
| hir::Node::ImplItem(&hir::ImplItem { ref generics, .. }) => generics,
| hir::Node::ImplItem(&hir::ImplItem { ref generics, .. }) => (
generics,
match self.tcx.parent_hir_node(self.tcx.local_def_id_to_hir_id(anon_reg.def_id))
{
hir::Node::Item(hir::Item {
kind: hir::ItemKind::Trait(_, _, ref generics, ..),
..
})
| hir::Node::Item(hir::Item {
kind: hir::ItemKind::Impl(hir::Impl { ref generics, .. }),
..
}) => Some(generics),
_ => None,
},
),
_ => return false,
};
@ -379,8 +394,29 @@ fn add_to_diag_with<G: EmissionGuarantee, F: SubdiagMessageOp<G>>(
.map(|p| p.name.ident().name)
.find(|i| *i != kw::UnderscoreLifetime);
let introduce_new = suggestion_param_name.is_none();
let mut default = "'a".to_string();
if let Some(parent_generics) = parent_generics {
let used: FxHashSet<_> = parent_generics
.params
.iter()
.filter(|p| matches!(p.kind, GenericParamKind::Lifetime { .. }))
.map(|p| p.name.ident().name)
.filter(|i| *i != kw::UnderscoreLifetime)
.map(|l| l.to_string())
.collect();
if let Some(lt) =
('a'..='z').map(|it| format!("'{it}")).find(|it| !used.contains(it))
{
// We want a lifetime that *isn't* present in the `trait` or `impl` that assoc
// `fn` belongs to. We could suggest reusing one of their lifetimes, but it is
// likely to be an over-constraining lifetime requirement, so we always add a
// lifetime to the `fn`.
default = lt;
}
}
let suggestion_param_name =
suggestion_param_name.map(|n| n.to_string()).unwrap_or_else(|| "'a".to_owned());
suggestion_param_name.map(|n| n.to_string()).unwrap_or_else(|| default);
struct ImplicitLifetimeFinder {
suggestions: Vec<(Span, String)>,

View File

@ -0,0 +1,17 @@
//@ run-rustfix
#![allow(dead_code)]
struct Foo {
field: i32,
}
impl Foo {
fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 {
x
//~^ ERROR lifetime may not live long enough
}
}
fn main() {}

View File

@ -1,5 +1,7 @@
//@ run-rustfix
#![allow(dead_code)]
struct Foo {
field: i32
field: i32,
}
impl Foo {
@ -12,4 +14,4 @@ fn foo<'a>(&self, x: &'a i32) -> &i32 {
}
fn main() { }
fn main() {}

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ex1-return-one-existing-name-return-type-is-anon.rs:8:5
--> $DIR/ex1-return-one-existing-name-return-type-is-anon.rs:10:5
|
LL | fn foo<'a>(&self, x: &'a i32) -> &i32 {
| -- - let's call the lifetime of this reference `'1`

View File

@ -0,0 +1,14 @@
//@ run-rustfix
#![allow(dead_code)]
struct Foo {
field: i32,
}
impl Foo {
fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 {
x
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,5 +1,7 @@
//@ run-rustfix
#![allow(dead_code)]
struct Foo {
field: i32
field: i32,
}
impl Foo {

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ex3-both-anon-regions-return-type-is-anon.rs:7:5
--> $DIR/ex3-both-anon-regions-return-type-is-anon.rs:9:5
|
LL | fn foo<'a>(&self, x: &i32) -> &i32 {
| - - let's call the lifetime of this reference `'1`

View File

@ -6,6 +6,9 @@ impl Foo {
fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { f }
//~^ lifetime may not live long enough
// For this suggestion to be right, we'd need to also suggest `self: Pin<&'a Self>`, which we
// don't, but we provide a follow up suggestion to do so, so I condider that good at least for
// now.
fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { (self, f) }
//~^ lifetime may not live long enough
}

View File

@ -13,7 +13,7 @@ LL | fn a<'a>(self: Pin<&'a Foo>, f: &'a Foo) -> &'a Foo { f }
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:9:69
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:12:69
|
LL | fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { (self, f) }
| - - ^^^^^^^^^ method was supposed to return data with lifetime `'2` but it is returning data with lifetime `'1`
@ -27,7 +27,7 @@ LL | fn c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'
| ++++ ++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:15:58
--> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:18:58
|
LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg }
| -- ---- has type `Pin<&'1 Foo>` ^^^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a`

View File

@ -0,0 +1,45 @@
//@ edition:2018
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;
struct Struct<'a> { data: &'a u32 }
impl<'a> Struct<'a> {
// Test using `&self` sugar:
async fn ref_self<'b>(&'b self, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
// Test using `&Self` explicitly:
async fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
async fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
async fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
async fn box_box_ref_Self<'b>(self: Box<Box<&'b Self>>, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
async fn box_pin_Self<'b>(self: Box<Pin<&'b Self>>, f: &'b u32) -> &u32 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,6 +1,6 @@
//@ edition:2018
#![allow(non_snake_case)]
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;

View File

@ -10,7 +10,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn ref_self<'a>(&'a self, f: &'a u32) -> &u32 {
LL | async fn ref_self<'b>(&'b self, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: lifetime may not live long enough
@ -25,7 +25,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn ref_Self<'a>(self: &'a Self, f: &'a u32) -> &u32 {
LL | async fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: lifetime may not live long enough
@ -40,7 +40,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn box_ref_Self<'a>(self: Box<&'a Self>, f: &'a u32) -> &u32 {
LL | async fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: lifetime may not live long enough
@ -55,7 +55,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn pin_ref_Self<'a>(self: Pin<&'a Self>, f: &'a u32) -> &u32 {
LL | async fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: lifetime may not live long enough
@ -70,7 +70,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn box_box_ref_Self<'a>(self: Box<Box<&'a Self>>, f: &'a u32) -> &u32 {
LL | async fn box_box_ref_Self<'b>(self: Box<Box<&'b Self>>, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: lifetime may not live long enough
@ -85,7 +85,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | async fn box_pin_Self<'a>(self: Box<Pin<&'a Self>>, f: &'a u32) -> &u32 {
LL | async fn box_pin_Self<'b>(self: Box<Pin<&'b Self>>, f: &'b u32) -> &u32 {
| ++++ ++ ++
error: aborting due to 6 previous errors

View File

@ -0,0 +1,44 @@
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;
struct Struct<'a> { data: &'a u32 }
impl<'a> Struct<'a> {
// Test using `&self` sugar:
fn ref_self<'b>(&'b self, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
// Test using `&Self` explicitly:
fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_box_ref_Self<'b>(self: Box<Box<&'b Self>>, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_pin_Self<'b>(self: Box<Pin<&'b Self>>, f: &'b u32) -> &'b u32 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,4 +1,5 @@
#![allow(non_snake_case)]
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:11:9
--> $DIR/lt-ref-self.rs:12:9
|
LL | fn ref_self(&self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -10,11 +10,11 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn ref_self<'a>(&'a self, f: &'a u32) -> &'a u32 {
LL | fn ref_self<'b>(&'b self, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:18:9
--> $DIR/lt-ref-self.rs:19:9
|
LL | fn ref_Self(self: &Self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -25,11 +25,11 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn ref_Self<'a>(self: &'a Self, f: &'a u32) -> &'a u32 {
LL | fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:23:9
--> $DIR/lt-ref-self.rs:24:9
|
LL | fn box_ref_Self(self: Box<&Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -40,11 +40,11 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn box_ref_Self<'a>(self: Box<&'a Self>, f: &'a u32) -> &'a u32 {
LL | fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:28:9
--> $DIR/lt-ref-self.rs:29:9
|
LL | fn pin_ref_Self(self: Pin<&Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -55,11 +55,11 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn pin_ref_Self<'a>(self: Pin<&'a Self>, f: &'a u32) -> &'a u32 {
LL | fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:33:9
--> $DIR/lt-ref-self.rs:34:9
|
LL | fn box_box_ref_Self(self: Box<Box<&Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -70,11 +70,11 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn box_box_ref_Self<'a>(self: Box<Box<&'a Self>>, f: &'a u32) -> &'a u32 {
LL | fn box_box_ref_Self<'b>(self: Box<Box<&'b Self>>, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/lt-ref-self.rs:38:9
--> $DIR/lt-ref-self.rs:39:9
|
LL | fn box_pin_Self(self: Box<Pin<&Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -85,7 +85,7 @@ LL | f
|
help: consider introducing a named lifetime parameter and update trait if needed
|
LL | fn box_pin_Self<'a>(self: Box<Pin<&'a Self>>, f: &'a u32) -> &'a u32 {
LL | fn box_pin_Self<'b>(self: Box<Pin<&'b Self>>, f: &'b u32) -> &'b u32 {
| ++++ ++ ++ ++
error: aborting due to 6 previous errors

View File

@ -0,0 +1,44 @@
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;
struct Struct { }
impl Struct {
// Test using `&mut self` sugar:
fn ref_self<'a>(&'a mut self, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
// Test using `&mut Self` explicitly:
fn ref_Self<'a>(self: &'a mut Self, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_ref_Self<'a>(self: Box<&'a mut Self>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn pin_ref_Self<'a>(self: Pin<&'a mut Self>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_box_ref_Self<'a>(self: Box<Box<&'a mut Self>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_pin_ref_Self<'a>(self: Box<Pin<&'a mut Self>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,4 +1,5 @@
#![allow(non_snake_case)]
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:11:9
--> $DIR/ref-mut-self.rs:12:9
|
LL | fn ref_self(&mut self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -14,7 +14,7 @@ LL | fn ref_self<'a>(&'a mut self, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:18:9
--> $DIR/ref-mut-self.rs:19:9
|
LL | fn ref_Self(self: &mut Self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -29,7 +29,7 @@ LL | fn ref_Self<'a>(self: &'a mut Self, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:23:9
--> $DIR/ref-mut-self.rs:24:9
|
LL | fn box_ref_Self(self: Box<&mut Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -44,7 +44,7 @@ LL | fn box_ref_Self<'a>(self: Box<&'a mut Self>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:28:9
--> $DIR/ref-mut-self.rs:29:9
|
LL | fn pin_ref_Self(self: Pin<&mut Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -59,7 +59,7 @@ LL | fn pin_ref_Self<'a>(self: Pin<&'a mut Self>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:33:9
--> $DIR/ref-mut-self.rs:34:9
|
LL | fn box_box_ref_Self(self: Box<Box<&mut Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -74,7 +74,7 @@ LL | fn box_box_ref_Self<'a>(self: Box<Box<&'a mut Self>>, f: &'a u32) -> &'
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-self.rs:38:9
--> $DIR/ref-mut-self.rs:39:9
|
LL | fn box_pin_ref_Self(self: Box<Pin<&mut Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`

View File

@ -0,0 +1,37 @@
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;
struct Struct { }
impl Struct {
// Test using `&mut Struct` explicitly:
fn ref_Struct<'a>(self: &'a mut Struct, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_ref_Struct<'a>(self: Box<&'a mut Struct>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn pin_ref_Struct<'a>(self: Pin<&'a mut Struct>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_box_ref_Struct<'a>(self: Box<Box<&'a mut Struct>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_pin_ref_Struct<'a>(self: Box<Pin<&'a mut Struct>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,4 +1,5 @@
#![allow(non_snake_case)]
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ref-mut-struct.rs:11:9
--> $DIR/ref-mut-struct.rs:12:9
|
LL | fn ref_Struct(self: &mut Struct, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -14,7 +14,7 @@ LL | fn ref_Struct<'a>(self: &'a mut Struct, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-struct.rs:16:9
--> $DIR/ref-mut-struct.rs:17:9
|
LL | fn box_ref_Struct(self: Box<&mut Struct>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -29,7 +29,7 @@ LL | fn box_ref_Struct<'a>(self: Box<&'a mut Struct>, f: &'a u32) -> &'a u32
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-struct.rs:21:9
--> $DIR/ref-mut-struct.rs:22:9
|
LL | fn pin_ref_Struct(self: Pin<&mut Struct>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -44,7 +44,7 @@ LL | fn pin_ref_Struct<'a>(self: Pin<&'a mut Struct>, f: &'a u32) -> &'a u32
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-struct.rs:26:9
--> $DIR/ref-mut-struct.rs:27:9
|
LL | fn box_box_ref_Struct(self: Box<Box<&mut Struct>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -59,7 +59,7 @@ LL | fn box_box_ref_Struct<'a>(self: Box<Box<&'a mut Struct>>, f: &'a u32) -
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-mut-struct.rs:31:9
--> $DIR/ref-mut-struct.rs:32:9
|
LL | fn box_pin_ref_Struct(self: Box<Pin<&mut Struct>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`

View File

@ -0,0 +1,59 @@
//@ run-rustfix
#![feature(arbitrary_self_types)]
#![allow(non_snake_case, dead_code)]
use std::marker::PhantomData;
use std::ops::Deref;
use std::pin::Pin;
struct Struct {}
struct Wrap<T, P>(T, PhantomData<P>);
impl<T, P> Deref for Wrap<T, P> {
type Target = T;
fn deref(&self) -> &T { &self.0 }
}
impl Struct {
// Test using `&self` sugar:
fn ref_self<'a>(&'a self, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
// Test using `&Self` explicitly:
fn ref_Self<'a>(self: &'a Self, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_ref_Self<'a>(self: Box<&'a Self>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn pin_ref_Self<'a>(self: Pin<&'a Self>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_box_ref_Self<'a>(self: Box<Box<&'a Self>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_pin_ref_Self<'a>(self: Box<Pin<&'a Self>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn wrap_ref_Self_Self<'a>(self: Wrap<&'a Self, Self>, f: &'a u8) -> &'a u8 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,11 +1,12 @@
//@ run-rustfix
#![feature(arbitrary_self_types)]
#![allow(non_snake_case)]
#![allow(non_snake_case, dead_code)]
use std::marker::PhantomData;
use std::ops::Deref;
use std::pin::Pin;
struct Struct { }
struct Struct {}
struct Wrap<T, P>(T, PhantomData<P>);

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ref-self.rs:21:9
--> $DIR/ref-self.rs:22:9
|
LL | fn ref_self(&self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -14,7 +14,7 @@ LL | fn ref_self<'a>(&'a self, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:28:9
--> $DIR/ref-self.rs:29:9
|
LL | fn ref_Self(self: &Self, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -29,7 +29,7 @@ LL | fn ref_Self<'a>(self: &'a Self, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:33:9
--> $DIR/ref-self.rs:34:9
|
LL | fn box_ref_Self(self: Box<&Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -44,7 +44,7 @@ LL | fn box_ref_Self<'a>(self: Box<&'a Self>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:38:9
--> $DIR/ref-self.rs:39:9
|
LL | fn pin_ref_Self(self: Pin<&Self>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -59,7 +59,7 @@ LL | fn pin_ref_Self<'a>(self: Pin<&'a Self>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:43:9
--> $DIR/ref-self.rs:44:9
|
LL | fn box_box_ref_Self(self: Box<Box<&Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -74,7 +74,7 @@ LL | fn box_box_ref_Self<'a>(self: Box<Box<&'a Self>>, f: &'a u32) -> &'a u3
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:48:9
--> $DIR/ref-self.rs:49:9
|
LL | fn box_pin_ref_Self(self: Box<Pin<&Self>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -89,7 +89,7 @@ LL | fn box_pin_ref_Self<'a>(self: Box<Pin<&'a Self>>, f: &'a u32) -> &'a u3
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-self.rs:53:9
--> $DIR/ref-self.rs:54:9
|
LL | fn wrap_ref_Self_Self(self: Wrap<&Self, Self>, f: &u8) -> &u8 {
| - - let's call the lifetime of this reference `'1`

View File

@ -0,0 +1,37 @@
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;
struct Struct { }
impl Struct {
// Test using `&Struct` explicitly:
fn ref_Struct<'a>(self: &'a Struct, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_ref_Struct<'a>(self: Box<&'a Struct>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn pin_ref_Struct<'a>(self: Pin<&'a Struct>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_box_ref_Struct<'a>(self: Box<Box<&'a Struct>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
fn box_pin_Struct<'a>(self: Box<Pin<&'a Struct>>, f: &'a u32) -> &'a u32 {
f
//~^ ERROR lifetime may not live long enough
}
}
fn main() { }

View File

@ -1,4 +1,5 @@
#![allow(non_snake_case)]
//@ run-rustfix
#![allow(non_snake_case, dead_code)]
use std::pin::Pin;

View File

@ -1,5 +1,5 @@
error: lifetime may not live long enough
--> $DIR/ref-struct.rs:11:9
--> $DIR/ref-struct.rs:12:9
|
LL | fn ref_Struct(self: &Struct, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -14,7 +14,7 @@ LL | fn ref_Struct<'a>(self: &'a Struct, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-struct.rs:16:9
--> $DIR/ref-struct.rs:17:9
|
LL | fn box_ref_Struct(self: Box<&Struct>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -29,7 +29,7 @@ LL | fn box_ref_Struct<'a>(self: Box<&'a Struct>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-struct.rs:21:9
--> $DIR/ref-struct.rs:22:9
|
LL | fn pin_ref_Struct(self: Pin<&Struct>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -44,7 +44,7 @@ LL | fn pin_ref_Struct<'a>(self: Pin<&'a Struct>, f: &'a u32) -> &'a u32 {
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-struct.rs:26:9
--> $DIR/ref-struct.rs:27:9
|
LL | fn box_box_ref_Struct(self: Box<Box<&Struct>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`
@ -59,7 +59,7 @@ LL | fn box_box_ref_Struct<'a>(self: Box<Box<&'a Struct>>, f: &'a u32) -> &'
| ++++ ++ ++ ++
error: lifetime may not live long enough
--> $DIR/ref-struct.rs:31:9
--> $DIR/ref-struct.rs:32:9
|
LL | fn box_pin_Struct(self: Box<Pin<&Struct>>, f: &u32) -> &u32 {
| - - let's call the lifetime of this reference `'1`