From 9f730e92f24ebd21b94112e46a0e44bdf7730e27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Fri, 3 May 2024 21:42:34 +0000 Subject: [PATCH 1/6] Suggest setting lifetime in borrowck error involving types with elided lifetimes ``` error: lifetime may not live long enough --> $DIR/ex3-both-anon-regions-both-are-structs-2.rs:7:5 | LL | fn foo(mut x: Ref, y: Ref) { | ----- - has type `Ref<'_, '1>` | | | has type `Ref<'_, '2>` LL | x.b = y.b; | ^^^^^^^^^ assignment requires that `'1` must outlive `'2` | help: consider introducing a named lifetime parameter | LL | fn foo<'a>(mut x: Ref<'a, 'a>, y: Ref<'a, 'a>) { | ++++ ++++++++ ++++++++ ``` As can be seen above, it currently doesn't try to compare the `ty::Ty` lifetimes that diverged vs the `hir::Ty` to correctly suggest the following ``` help: consider introducing a named lifetime parameter | LL | fn foo<'a>(mut x: Ref<'_, 'a>, y: Ref<'_, 'a>) { | ++++ ++++++++ ++++++++ ``` but I believe this to still be an improvement over the status quo. CC #40990. --- compiler/rustc_infer/src/errors/mod.rs | 105 +++++++++++++----- ...ne-existing-name-if-else-using-impl.stderr | 5 + ...e-existing-name-return-type-is-anon.stderr | 5 + ...turn-one-existing-name-self-is-anon.stderr | 5 + .../ex2b-push-no-existing-names.stderr | 5 + ...oth-anon-regions-both-are-structs-2.stderr | 5 + ...oth-anon-regions-both-are-structs-3.stderr | 5 + ...-both-anon-regions-both-are-structs.stderr | 5 + ...3-both-anon-regions-one-is-struct-2.stderr | 5 + ...3-both-anon-regions-one-is-struct-3.stderr | 5 + ...3-both-anon-regions-one-is-struct-4.stderr | 5 + ...ex3-both-anon-regions-one-is-struct.stderr | 5 + ...f_types_pin_lifetime_mismatch-async.stderr | 5 + ...ry_self_types_pin_lifetime_mismatch.stderr | 5 + 14 files changed, 140 insertions(+), 30 deletions(-) diff --git a/compiler/rustc_infer/src/errors/mod.rs b/compiler/rustc_infer/src/errors/mod.rs index 2acaeac24398d..039472398964b 100644 --- a/compiler/rustc_infer/src/errors/mod.rs +++ b/compiler/rustc_infer/src/errors/mod.rs @@ -4,6 +4,7 @@ use rustc_errors::{ MultiSpan, SubdiagMessageOp, Subdiagnostic, }; use rustc_hir as hir; +use rustc_hir::intravisit::{walk_ty, Visitor}; use rustc_hir::FnRetTy; use rustc_macros::{Diagnostic, Subdiagnostic}; use rustc_middle::ty::print::TraitRefPrintOnlyTraitPath; @@ -355,18 +356,6 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { _f: &F, ) { let mut mk_suggestion = || { - let ( - hir::Ty { kind: hir::TyKind::Ref(lifetime_sub, _), .. }, - hir::Ty { kind: hir::TyKind::Ref(lifetime_sup, _), .. }, - ) = (self.ty_sub, self.ty_sup) - else { - return false; - }; - - if !lifetime_sub.is_anonymous() || !lifetime_sup.is_anonymous() { - return false; - }; - let Some(anon_reg) = self.tcx.is_suitable_region(self.sub) else { return false; }; @@ -393,21 +382,77 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { let suggestion_param_name = suggestion_param_name.map(|n| n.to_string()).unwrap_or_else(|| "'a".to_owned()); - debug!(?lifetime_sup.ident.span); - debug!(?lifetime_sub.ident.span); - let make_suggestion = |ident: Ident| { - let sugg = if ident.name == kw::Empty { - format!("{suggestion_param_name}, ") - } else if ident.name == kw::UnderscoreLifetime && ident.span.is_empty() { - format!("{suggestion_param_name} ") - } else { - suggestion_param_name.clone() - }; - (ident.span, sugg) - }; - let mut suggestions = - vec![make_suggestion(lifetime_sub.ident), make_suggestion(lifetime_sup.ident)]; + struct ImplicitLifetimeFinder { + suggestions: Vec<(Span, String)>, + suggestion_param_name: String, + } + impl<'v> Visitor<'v> for ImplicitLifetimeFinder { + fn visit_ty(&mut self, ty: &'v hir::Ty<'v>) { + let make_suggestion = |ident: Ident| { + if ident.name == kw::Empty && ident.span.is_empty() { + format!("{}, ", self.suggestion_param_name) + } else if ident.name == kw::UnderscoreLifetime && ident.span.is_empty() { + format!("{} ", self.suggestion_param_name) + } else { + self.suggestion_param_name.clone() + } + }; + match ty.kind { + hir::TyKind::Path(hir::QPath::Resolved(_, path)) => { + for segment in path.segments { + if let Some(args) = segment.args { + if args.args.iter().all(|arg| { + matches!( + arg, + hir::GenericArg::Lifetime(lifetime) + if lifetime.ident.name == kw::Empty + ) + }) { + self.suggestions.push(( + segment.ident.span.shrink_to_hi(), + format!( + "<{}>", + args.args + .iter() + .map(|_| self.suggestion_param_name.clone()) + .collect::>() + .join(", ") + ), + )); + } else { + for arg in args.args { + if let hir::GenericArg::Lifetime(lifetime) = arg + && lifetime.is_anonymous() + { + self.suggestions.push(( + lifetime.ident.span, + make_suggestion(lifetime.ident), + )); + } + } + } + } + } + } + hir::TyKind::Ref(lifetime, ..) if lifetime.is_anonymous() => { + self.suggestions + .push((lifetime.ident.span, make_suggestion(lifetime.ident))); + } + _ => {} + } + walk_ty(self, ty); + } + } + let mut visitor = ImplicitLifetimeFinder { + suggestions: vec![], + suggestion_param_name: suggestion_param_name.clone(), + }; + visitor.visit_ty(self.ty_sub); + visitor.visit_ty(self.ty_sup); + if visitor.suggestions.is_empty() { + return false; + } if introduce_new { let new_param_suggestion = if let Some(first) = generics.params.iter().find(|p| !p.name.ident().span.is_empty()) @@ -417,15 +462,15 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { (generics.span, format!("<{suggestion_param_name}>")) }; - suggestions.push(new_param_suggestion); + visitor.suggestions.push(new_param_suggestion); } - - diag.multipart_suggestion( + diag.multipart_suggestion_verbose( fluent::infer_lifetime_param_suggestion, - suggestions, + visitor.suggestions, Applicability::MaybeIncorrect, ); diag.arg("is_impl", is_impl); + true }; if mk_suggestion() && self.add_note { diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr index 5827b2fe695a6..6bc82910b06a5 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr @@ -8,6 +8,11 @@ LL | fn foo<'a>(x: &i32, y: &'a i32) -> &'a i32 { LL | LL | if x > y { x } else { y } | ^ associated function was supposed to return data with lifetime `'a` but it is returning data with lifetime `'1` + | +help: consider introducing a named lifetime parameter and update trait if needed + | +LL | fn foo<'a>(x: &'a i32, y: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index da454b8fd8637..cdcdc0c07e3ab 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -8,6 +8,11 @@ LL | fn foo<'a>(&self, x: &'a i32) -> &i32 { LL | LL | x | ^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` + | +help: consider introducing a named lifetime parameter and update trait if needed + | +LL | fn foo<'a>(&'a self, x: &'a i32) -> &i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr index a1dfff883a004..f106d45b9acdd 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr @@ -8,6 +8,11 @@ LL | fn foo<'a>(&self, x: &'a Foo) -> &'a Foo { LL | LL | if true { x } else { self } | ^^^^ method was supposed to return data with lifetime `'a` but it is returning data with lifetime `'1` + | +help: consider introducing a named lifetime parameter and update trait if needed + | +LL | fn foo<'a>(&'a self, x: &'a Foo) -> &'a Foo { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex2b-push-no-existing-names.stderr b/tests/ui/lifetimes/lifetime-errors/ex2b-push-no-existing-names.stderr index df1d03d517032..6f7127d4c4c4e 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex2b-push-no-existing-names.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex2b-push-no-existing-names.stderr @@ -7,6 +7,11 @@ LL | fn foo(x: &mut Vec>, y: Ref) { | has type `&mut Vec>` LL | x.push(y); | ^^^^^^^^^ argument requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(x: &mut Vec>, y: Ref<'a, i32>) { + | ++++ +++ +++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-2.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-2.stderr index 4f1cb1e797221..f8ad923cce8a5 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-2.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-2.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut x: Ref, y: Ref) { | has type `Ref<'_, '2>` LL | x.b = y.b; | ^^^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut x: Ref<'a, 'a>, y: Ref<'a, 'a>) { + | ++++ ++++++++ ++++++++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr index 3a1947973b551..a1149779d2c6d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs-3.stderr @@ -8,6 +8,11 @@ LL | fn foo(mut x: Ref) { | has type `Ref<'2, '_>` LL | x.a = x.b; | ^^^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut x: Ref<'a, 'a>) { + | ++++ ++++++++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs.stderr index c778f77366abc..017bfa7146317 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-both-are-structs.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut x: Vec, y: Ref) { | has type `Vec>` LL | x.push(y); | ^^^^^^^^^ argument requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut x: Vec>, y: Ref<'a>) { + | ++++ ++++ ++++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-2.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-2.stderr index bbd62902d9f44..0980de92d350e 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-2.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-2.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut x: Ref, y: &u32) { | has type `Ref<'_, '1>` LL | y = x.b; | ^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut x: Ref<'a, 'a>, y: &'a u32) { + | ++++ ++++++++ ++ error[E0384]: cannot assign to immutable argument `y` --> $DIR/ex3-both-anon-regions-one-is-struct-2.rs:4:5 diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-3.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-3.stderr index 60ca416845515..d9c7530b64c57 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-3.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-3.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut y: Ref, x: &u32) { | has type `Ref<'_, '2>` LL | y.b = x; | ^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut y: Ref<'a, 'a>, x: &'a u32) { + | ++++ ++++++++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-4.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-4.stderr index 98e490c3827b5..d07b821444ccc 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-4.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct-4.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut y: Ref, x: &u32) { | has type `Ref<'_, '2>` LL | y.b = x; | ^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut y: Ref<'a, 'a>, x: &'a u32) { + | ++++ ++++++++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct.stderr index ea1cc1f18a4dc..ef28ddeacc5e2 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-one-is-struct.stderr @@ -7,6 +7,11 @@ LL | fn foo(mut x: Ref, y: &u32) { | has type `Ref<'_, '2>` LL | x.b = y; | ^^^^^^^ assignment requires that `'1` must outlive `'2` + | +help: consider introducing a named lifetime parameter + | +LL | fn foo<'a>(mut x: Ref<'a, 'a>, y: &'a u32) { + | ++++ ++++++++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr index 0b4c0a7fecec4..bb643ab827222 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr @@ -34,6 +34,11 @@ LL | async fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg } | | | | | let's call the lifetime of this reference `'1` | lifetime `'a` defined here + | +help: consider introducing a named lifetime parameter and update trait if needed + | +LL | async fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &() { arg } + | ++ error: aborting due to 3 previous errors diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index 209dae9c1b3e8..bbb2ef4641e72 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -33,6 +33,11 @@ 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` | | | lifetime `'a` defined here + | +help: consider introducing a named lifetime parameter and update trait if needed + | +LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &() { arg } + | ++ error: aborting due to 3 previous errors From 120049fab4e293c19fa1c5a09d68f89bcd940b36 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Sun, 5 May 2024 03:42:47 +0000 Subject: [PATCH 2/6] Always constrain the return type in lifetime suggestion ``` error: lifetime may not live long enough --> f205.rs:8:16 | 7 | fn resolve_symbolic_reference(&self, reference: Option) -> Option { | - --------- has type `Option>` | | | let's call the lifetime of this reference `'2` 8 | return reference; | ^^^^^^^^^ method was supposed to return data with lifetime `'2` but it is returning data with lifetime `'1` | help: consider introducing a named lifetime parameter | 7 | fn resolve_symbolic_reference<'a>(&'a self, reference: Option>) -> Option> { | ++++ ++ ++++ ++++ ``` The correct suggestion would be ``` help: consider introducing a named lifetime parameter | 7 | fn resolve_symbolic_reference<'a>(&self, reference: Option>) -> Option> { | ++++ ++++ ++++ ``` but we are not doing the analysis to detect that yet. If we constrain `&'a self`, then the return type with a borrow will implicitly take its lifetime from `'a`, it is better to make it explicit in the suggestion, in case that `&self` *doesn't* need to be `'a`, but the return does. --- compiler/rustc_infer/src/errors/mod.rs | 5 ++++ tests/ui/lifetimes/issue-17728.stderr | 4 +-- ...e-existing-name-return-type-is-anon.stderr | 4 +-- ...th-anon-regions-return-type-is-anon.stderr | 4 +-- .../ex3-both-anon-regions-self-is-anon.stderr | 4 +-- ...ry_self_types_pin_lifetime_mismatch.stderr | 12 ++++---- tests/ui/self/elision/lt-ref-self.stderr | 24 ++++++++-------- tests/ui/self/elision/ref-mut-self.stderr | 24 ++++++++-------- tests/ui/self/elision/ref-mut-struct.stderr | 20 ++++++------- tests/ui/self/elision/ref-self.stderr | 28 +++++++++---------- tests/ui/self/elision/ref-struct.stderr | 20 ++++++------- 11 files changed, 77 insertions(+), 72 deletions(-) diff --git a/compiler/rustc_infer/src/errors/mod.rs b/compiler/rustc_infer/src/errors/mod.rs index 039472398964b..4db79af10a559 100644 --- a/compiler/rustc_infer/src/errors/mod.rs +++ b/compiler/rustc_infer/src/errors/mod.rs @@ -450,6 +450,11 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { }; visitor.visit_ty(self.ty_sub); visitor.visit_ty(self.ty_sup); + if let Some(fn_decl) = node.fn_decl() + && let hir::FnRetTy::Return(ty) = fn_decl.output + { + visitor.visit_ty(ty); + } if visitor.suggestions.is_empty() { return false; } diff --git a/tests/ui/lifetimes/issue-17728.stderr b/tests/ui/lifetimes/issue-17728.stderr index 23547f722a116..da4ce2dd2911d 100644 --- a/tests/ui/lifetimes/issue-17728.stderr +++ b/tests/ui/lifetimes/issue-17728.stderr @@ -29,8 +29,8 @@ LL | Some(entry) => Ok(entry), | help: consider introducing a named lifetime parameter | -LL | fn attemptTraverse<'a>(&'a self, room: &'a Room, directionStr: &str) -> Result<&Room, &str> { - | ++++ ++ ++ +LL | fn attemptTraverse<'a>(&'a self, room: &'a Room, directionStr: &str) -> Result<&'a Room, &'a str> { + | ++++ ++ ++ ++ ++ error: aborting due to 2 previous errors diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index cdcdc0c07e3ab..5cfa571722402 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -11,8 +11,8 @@ LL | x | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a i32) -> &i32 { - | ++ +LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + | ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr index e934ce7c040ef..fd15d516999cf 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr @@ -10,8 +10,8 @@ LL | x | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a i32) -> &i32 { - | ++ ++ +LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + | ++ ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr index dde271d100c58..0a312cf93c8de 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr @@ -10,8 +10,8 @@ LL | if true { x } else { self } | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a Foo) -> &Foo { - | ++ ++ +LL | fn foo<'a>(&'a self, x: &'a Foo) -> &'a Foo { + | ++ ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index bbb2ef4641e72..3e2bbd37f33fd 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -9,8 +9,8 @@ LL | fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { f } | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn a<'a>(self: Pin<&'a Foo>, f: &'a Foo) -> &Foo { f } - | ++++ ++ ++ +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 @@ -23,8 +23,8 @@ LL | fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { (self, | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { (self, f) } - | ++++ ++ ++ +LL | fn c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'a Foo) { (self, f) } + | ++++ ++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:15:58 @@ -36,8 +36,8 @@ LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg } | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &() { arg } - | ++ +LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &'a () { arg } + | ++ ++ error: aborting due to 3 previous errors diff --git a/tests/ui/self/elision/lt-ref-self.stderr b/tests/ui/self/elision/lt-ref-self.stderr index 216737a2c7330..5eaaa7698b6e4 100644 --- a/tests/ui/self/elision/lt-ref-self.stderr +++ b/tests/ui/self/elision/lt-ref-self.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_self<'a>(&'a self, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn ref_self<'a>(&'a self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:18:9 @@ -25,8 +25,8 @@ 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) -> &u32 { - | ++++ ++ ++ +LL | fn ref_Self<'a>(self: &'a Self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:23:9 @@ -40,8 +40,8 @@ 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) -> &u32 { - | ++++ ++ ++ +LL | fn box_ref_Self<'a>(self: Box<&'a Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:28:9 @@ -55,8 +55,8 @@ 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) -> &u32 { - | ++++ ++ ++ +LL | fn pin_ref_Self<'a>(self: Pin<&'a Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:33:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:38:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_pin_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/ref-mut-self.stderr b/tests/ui/self/elision/ref-mut-self.stderr index 12b64a3f6dcb5..8fea05e493dcd 100644 --- a/tests/ui/self/elision/ref-mut-self.stderr +++ b/tests/ui/self/elision/ref-mut-self.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_self<'a>(&'a mut self, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Self<'a>(self: &'a mut Self, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Self<'a>(self: Box<&'a mut Self>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Self<'a>(self: Pin<&'a mut Self>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:38:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/ref-mut-struct.stderr b/tests/ui/self/elision/ref-mut-struct.stderr index cde16ce8ba414..26dcfcb6dd0b1 100644 --- a/tests/ui/self/elision/ref-mut-struct.stderr +++ b/tests/ui/self/elision/ref-mut-struct.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Struct<'a>(self: &'a mut Struct, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Struct<'a>(self: Box<&'a mut Struct>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Struct<'a>(self: Pin<&'a mut Struct>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-struct.rs:31:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: aborting due to 5 previous errors diff --git a/tests/ui/self/elision/ref-self.stderr b/tests/ui/self/elision/ref-self.stderr index 35693257c9919..8654032b0476b 100644 --- a/tests/ui/self/elision/ref-self.stderr +++ b/tests/ui/self/elision/ref-self.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_self<'a>(&'a self, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -25,8 +25,8 @@ 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) -> &u32 { - | ++++ ++ ++ +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 @@ -40,8 +40,8 @@ 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) -> &u32 { - | ++++ ++ ++ +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 @@ -55,8 +55,8 @@ 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) -> &u32 { - | ++++ ++ ++ +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 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:48:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:53:9 @@ -100,8 +100,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn wrap_ref_Self_Self<'a>(self: Wrap<&'a Self, Self>, f: &'a u8) -> &u8 { - | ++++ ++ ++ +LL | fn wrap_ref_Self_Self<'a>(self: Wrap<&'a Self, Self>, f: &'a u8) -> &'a u8 { + | ++++ ++ ++ ++ error: aborting due to 7 previous errors diff --git a/tests/ui/self/elision/ref-struct.stderr b/tests/ui/self/elision/ref-struct.stderr index a3d3cebeba9c5..653ecc612d572 100644 --- a/tests/ui/self/elision/ref-struct.stderr +++ b/tests/ui/self/elision/ref-struct.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Struct<'a>(self: &'a Struct, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Struct<'a>(self: Box<&'a Struct>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Struct<'a>(self: Pin<&'a Struct>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +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 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-struct.rs:31:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &u32 { - | ++++ ++ ++ +LL | fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ ++ error: aborting due to 5 previous errors From d1d585d039ace2ea72db8772166773a80a661905 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Tue, 7 May 2024 19:35:25 +0000 Subject: [PATCH 3/6] 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 { | ++++ ++ ++ ++ ``` --- compiler/rustc_infer/src/errors/mod.rs | 42 ++++++++++++- ...ne-existing-name-return-type-is-anon.fixed | 17 ++++++ ...n-one-existing-name-return-type-is-anon.rs | 6 +- ...e-existing-name-return-type-is-anon.stderr | 2 +- ...oth-anon-regions-return-type-is-anon.fixed | 14 +++++ ...3-both-anon-regions-return-type-is-anon.rs | 4 +- ...th-anon-regions-return-type-is-anon.stderr | 2 +- ...itrary_self_types_pin_lifetime_mismatch.rs | 3 + ...ry_self_types_pin_lifetime_mismatch.stderr | 4 +- tests/ui/self/elision/lt-ref-self-async.fixed | 45 ++++++++++++++ tests/ui/self/elision/lt-ref-self-async.rs | 4 +- .../ui/self/elision/lt-ref-self-async.stderr | 12 ++-- tests/ui/self/elision/lt-ref-self.fixed | 44 ++++++++++++++ tests/ui/self/elision/lt-ref-self.rs | 3 +- tests/ui/self/elision/lt-ref-self.stderr | 24 ++++---- tests/ui/self/elision/ref-mut-self.fixed | 44 ++++++++++++++ tests/ui/self/elision/ref-mut-self.rs | 3 +- tests/ui/self/elision/ref-mut-self.stderr | 12 ++-- tests/ui/self/elision/ref-mut-struct.fixed | 37 ++++++++++++ tests/ui/self/elision/ref-mut-struct.rs | 3 +- tests/ui/self/elision/ref-mut-struct.stderr | 10 ++-- tests/ui/self/elision/ref-self.fixed | 59 +++++++++++++++++++ tests/ui/self/elision/ref-self.rs | 5 +- tests/ui/self/elision/ref-self.stderr | 14 ++--- tests/ui/self/elision/ref-struct.fixed | 37 ++++++++++++ tests/ui/self/elision/ref-struct.rs | 3 +- tests/ui/self/elision/ref-struct.stderr | 10 ++-- 27 files changed, 404 insertions(+), 59 deletions(-) create mode 100644 tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed create mode 100644 tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed create mode 100644 tests/ui/self/elision/lt-ref-self-async.fixed create mode 100644 tests/ui/self/elision/lt-ref-self.fixed create mode 100644 tests/ui/self/elision/ref-mut-self.fixed create mode 100644 tests/ui/self/elision/ref-mut-struct.fixed create mode 100644 tests/ui/self/elision/ref-self.fixed create mode 100644 tests/ui/self/elision/ref-struct.fixed diff --git a/compiler/rustc_infer/src/errors/mod.rs b/compiler/rustc_infer/src/errors/mod.rs index 4db79af10a559..f60ecb3f453ae 100644 --- a/compiler/rustc_infer/src/errors/mod.rs +++ b/compiler/rustc_infer/src/errors/mod.rs @@ -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 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { 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 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { .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)>, diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed new file mode 100644 index 0000000000000..b5513818f63e8 --- /dev/null +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed @@ -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() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs index 49993aca3cadd..52646ff89eb24 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs @@ -1,5 +1,7 @@ +//@ run-rustfix +#![allow(dead_code)] struct Foo { - field: i32 + field: i32, } impl Foo { @@ -12,4 +14,4 @@ impl Foo { } -fn main() { } +fn main() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index 5cfa571722402..e2f42cbfb286d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -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` diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed new file mode 100644 index 0000000000000..d9f454f346cef --- /dev/null +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed @@ -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() { } diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs index 3ffd7be4e73fe..bf66a551a80ee 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs @@ -1,5 +1,7 @@ +//@ run-rustfix +#![allow(dead_code)] struct Foo { - field: i32 + field: i32, } impl Foo { diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr index fd15d516999cf..778634e95be56 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr @@ -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` diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs index f1a3fb0185db7..3b2c8c7bc791f 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs @@ -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 } diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index 3e2bbd37f33fd..773f9362ec53f 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -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` diff --git a/tests/ui/self/elision/lt-ref-self-async.fixed b/tests/ui/self/elision/lt-ref-self-async.fixed new file mode 100644 index 0000000000000..6d875ef0cec17 --- /dev/null +++ b/tests/ui/self/elision/lt-ref-self-async.fixed @@ -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>, f: &'b u32) -> &u32 { + f + //~^ ERROR lifetime may not live long enough + } + + async fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &u32 { + f + //~^ ERROR lifetime may not live long enough + } +} + +fn main() { } diff --git a/tests/ui/self/elision/lt-ref-self-async.rs b/tests/ui/self/elision/lt-ref-self-async.rs index 8eb4a48a9c932..a70e22ab77ad0 100644 --- a/tests/ui/self/elision/lt-ref-self-async.rs +++ b/tests/ui/self/elision/lt-ref-self-async.rs @@ -1,6 +1,6 @@ //@ edition:2018 - -#![allow(non_snake_case)] +//@ run-rustfix +#![allow(non_snake_case, dead_code)] use std::pin::Pin; diff --git a/tests/ui/self/elision/lt-ref-self-async.stderr b/tests/ui/self/elision/lt-ref-self-async.stderr index 29d60ed663523..c8b49de7671ef 100644 --- a/tests/ui/self/elision/lt-ref-self-async.stderr +++ b/tests/ui/self/elision/lt-ref-self-async.stderr @@ -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>, f: &'a u32) -> &u32 { +LL | async fn box_box_ref_Self<'b>(self: Box>, 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>, f: &'a u32) -> &u32 { +LL | async fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &u32 { | ++++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/lt-ref-self.fixed b/tests/ui/self/elision/lt-ref-self.fixed new file mode 100644 index 0000000000000..c9faa86c441b4 --- /dev/null +++ b/tests/ui/self/elision/lt-ref-self.fixed @@ -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>, f: &'b u32) -> &'b u32 { + f + //~^ ERROR lifetime may not live long enough + } + + fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { + f + //~^ ERROR lifetime may not live long enough + } +} + +fn main() { } diff --git a/tests/ui/self/elision/lt-ref-self.rs b/tests/ui/self/elision/lt-ref-self.rs index d37ed5acbcb2e..fbd0665b22d23 100644 --- a/tests/ui/self/elision/lt-ref-self.rs +++ b/tests/ui/self/elision/lt-ref-self.rs @@ -1,4 +1,5 @@ -#![allow(non_snake_case)] +//@ run-rustfix +#![allow(non_snake_case, dead_code)] use std::pin::Pin; diff --git a/tests/ui/self/elision/lt-ref-self.stderr b/tests/ui/self/elision/lt-ref-self.stderr index 5eaaa7698b6e4..53b662bcb693c 100644 --- a/tests/ui/self/elision/lt-ref-self.stderr +++ b/tests/ui/self/elision/lt-ref-self.stderr @@ -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>, 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>, f: &'a u32) -> &'a u32 { +LL | fn box_box_ref_Self<'b>(self: Box>, 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>, 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>, f: &'a u32) -> &'a u32 { +LL | fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { | ++++ ++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/ref-mut-self.fixed b/tests/ui/self/elision/ref-mut-self.fixed new file mode 100644 index 0000000000000..90e50221a19bc --- /dev/null +++ b/tests/ui/self/elision/ref-mut-self.fixed @@ -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>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } + + fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } +} + +fn main() { } diff --git a/tests/ui/self/elision/ref-mut-self.rs b/tests/ui/self/elision/ref-mut-self.rs index bb82e6be74897..a09fcdfcbb2fd 100644 --- a/tests/ui/self/elision/ref-mut-self.rs +++ b/tests/ui/self/elision/ref-mut-self.rs @@ -1,4 +1,5 @@ -#![allow(non_snake_case)] +//@ run-rustfix +#![allow(non_snake_case, dead_code)] use std::pin::Pin; diff --git a/tests/ui/self/elision/ref-mut-self.stderr b/tests/ui/self/elision/ref-mut-self.stderr index 8fea05e493dcd..a09034e5f71d7 100644 --- a/tests/ui/self/elision/ref-mut-self.stderr +++ b/tests/ui/self/elision/ref-mut-self.stderr @@ -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>, 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>, 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>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` diff --git a/tests/ui/self/elision/ref-mut-struct.fixed b/tests/ui/self/elision/ref-mut-struct.fixed new file mode 100644 index 0000000000000..275fafbad53a5 --- /dev/null +++ b/tests/ui/self/elision/ref-mut-struct.fixed @@ -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>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } + + fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } +} + +fn main() { } diff --git a/tests/ui/self/elision/ref-mut-struct.rs b/tests/ui/self/elision/ref-mut-struct.rs index ca8bd8da1335a..6bfdca62bca73 100644 --- a/tests/ui/self/elision/ref-mut-struct.rs +++ b/tests/ui/self/elision/ref-mut-struct.rs @@ -1,4 +1,5 @@ -#![allow(non_snake_case)] +//@ run-rustfix +#![allow(non_snake_case, dead_code)] use std::pin::Pin; diff --git a/tests/ui/self/elision/ref-mut-struct.stderr b/tests/ui/self/elision/ref-mut-struct.stderr index 26dcfcb6dd0b1..19b09272504e3 100644 --- a/tests/ui/self/elision/ref-mut-struct.stderr +++ b/tests/ui/self/elision/ref-mut-struct.stderr @@ -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>, 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>, 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>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` diff --git a/tests/ui/self/elision/ref-self.fixed b/tests/ui/self/elision/ref-self.fixed new file mode 100644 index 0000000000000..41b11c2d77a3d --- /dev/null +++ b/tests/ui/self/elision/ref-self.fixed @@ -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, PhantomData

); + +impl Deref for Wrap { + 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>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } + + fn box_pin_ref_Self<'a>(self: Box>, 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() { } diff --git a/tests/ui/self/elision/ref-self.rs b/tests/ui/self/elision/ref-self.rs index dd07fe1b00be3..9b204e2a43ba4 100644 --- a/tests/ui/self/elision/ref-self.rs +++ b/tests/ui/self/elision/ref-self.rs @@ -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, PhantomData

); diff --git a/tests/ui/self/elision/ref-self.stderr b/tests/ui/self/elision/ref-self.stderr index 8654032b0476b..b17667827bb78 100644 --- a/tests/ui/self/elision/ref-self.stderr +++ b/tests/ui/self/elision/ref-self.stderr @@ -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>, 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>, 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>, 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>, 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` diff --git a/tests/ui/self/elision/ref-struct.fixed b/tests/ui/self/elision/ref-struct.fixed new file mode 100644 index 0000000000000..1c26c84c08848 --- /dev/null +++ b/tests/ui/self/elision/ref-struct.fixed @@ -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>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } + + fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + f + //~^ ERROR lifetime may not live long enough + } +} + +fn main() { } diff --git a/tests/ui/self/elision/ref-struct.rs b/tests/ui/self/elision/ref-struct.rs index 13a42cd1aed92..78b894765aa41 100644 --- a/tests/ui/self/elision/ref-struct.rs +++ b/tests/ui/self/elision/ref-struct.rs @@ -1,4 +1,5 @@ -#![allow(non_snake_case)] +//@ run-rustfix +#![allow(non_snake_case, dead_code)] use std::pin::Pin; diff --git a/tests/ui/self/elision/ref-struct.stderr b/tests/ui/self/elision/ref-struct.stderr index 653ecc612d572..157e0d407932a 100644 --- a/tests/ui/self/elision/ref-struct.stderr +++ b/tests/ui/self/elision/ref-struct.stderr @@ -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>, 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>, 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>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` From ee5a157b4a9d51788d7306af63b3e3ef063ec49d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Tue, 7 May 2024 19:45:51 +0000 Subject: [PATCH 4/6] Run `rustfmt` on modified tests --- ...ne-existing-name-return-type-is-anon.fixed | 11 +++--- ...n-one-existing-name-return-type-is-anon.rs | 11 +++--- ...e-existing-name-return-type-is-anon.stderr | 19 +++++----- ...oth-anon-regions-return-type-is-anon.fixed | 12 +++---- ...3-both-anon-regions-return-type-is-anon.rs | 12 +++---- ...th-anon-regions-return-type-is-anon.stderr | 18 +++++----- ...itrary_self_types_pin_lifetime_mismatch.rs | 15 ++++---- ...ry_self_types_pin_lifetime_mismatch.stderr | 36 ++++++++++--------- tests/ui/self/elision/lt-ref-self-async.fixed | 6 ++-- tests/ui/self/elision/lt-ref-self-async.rs | 6 ++-- .../ui/self/elision/lt-ref-self-async.stderr | 12 +++---- tests/ui/self/elision/lt-ref-self.fixed | 6 ++-- tests/ui/self/elision/lt-ref-self.rs | 6 ++-- tests/ui/self/elision/lt-ref-self.stderr | 12 +++---- tests/ui/self/elision/ref-mut-self.fixed | 4 +-- tests/ui/self/elision/ref-mut-self.rs | 4 +-- tests/ui/self/elision/ref-mut-struct.fixed | 4 +-- tests/ui/self/elision/ref-mut-struct.rs | 4 +-- tests/ui/self/elision/ref-self.fixed | 6 ++-- tests/ui/self/elision/ref-self.rs | 6 ++-- tests/ui/self/elision/ref-self.stderr | 14 ++++---- tests/ui/self/elision/ref-struct.fixed | 4 +-- tests/ui/self/elision/ref-struct.rs | 4 +-- 23 files changed, 122 insertions(+), 110 deletions(-) diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed index b5513818f63e8..3408463ce4990 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed @@ -5,13 +5,10 @@ struct Foo { } impl Foo { - fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - - x - //~^ ERROR lifetime may not live long enough - - } - + fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + x + //~^ ERROR lifetime may not live long enough + } } fn main() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs index 52646ff89eb24..c8dd958b37c6a 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.rs @@ -5,13 +5,10 @@ struct Foo { } impl Foo { - fn foo<'a>(&self, x: &'a i32) -> &i32 { - - x - //~^ ERROR lifetime may not live long enough - - } - + fn foo<'a>(&self, x: &'a i32) -> &i32 { + x + //~^ ERROR lifetime may not live long enough + } } fn main() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index e2f42cbfb286d..ca6ee1c25cdd4 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -1,18 +1,17 @@ error: lifetime may not live long enough - --> $DIR/ex1-return-one-existing-name-return-type-is-anon.rs:10:5 + --> $DIR/ex1-return-one-existing-name-return-type-is-anon.rs:9:9 | -LL | fn foo<'a>(&self, x: &'a i32) -> &i32 { - | -- - let's call the lifetime of this reference `'1` - | | - | lifetime `'a` defined here -LL | -LL | x - | ^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` +LL | fn foo<'a>(&self, x: &'a i32) -> &i32 { + | -- - let's call the lifetime of this reference `'1` + | | + | lifetime `'a` defined here +LL | x + | ^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - | ++ ++ +LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + | ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed index d9f454f346cef..3408463ce4990 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed @@ -1,14 +1,14 @@ //@ run-rustfix #![allow(dead_code)] struct Foo { - field: i32, + field: i32, } impl Foo { - fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - x - //~^ ERROR lifetime may not live long enough - } + fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + x + //~^ ERROR lifetime may not live long enough + } } -fn main() { } +fn main() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs index bf66a551a80ee..0225d8c79616c 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.rs @@ -1,14 +1,14 @@ //@ run-rustfix #![allow(dead_code)] struct Foo { - field: i32, + field: i32, } impl Foo { - fn foo<'a>(&self, x: &i32) -> &i32 { - x - //~^ ERROR lifetime may not live long enough - } + fn foo<'a>(&self, x: &i32) -> &i32 { + x + //~^ ERROR lifetime may not live long enough + } } -fn main() { } +fn main() {} diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr index 778634e95be56..a81b5cfad5a5b 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr @@ -1,17 +1,17 @@ error: lifetime may not live long enough - --> $DIR/ex3-both-anon-regions-return-type-is-anon.rs:9:5 + --> $DIR/ex3-both-anon-regions-return-type-is-anon.rs:9:9 | -LL | fn foo<'a>(&self, x: &i32) -> &i32 { - | - - let's call the lifetime of this reference `'1` - | | - | let's call the lifetime of this reference `'2` -LL | x - | ^ method was supposed to return data with lifetime `'2` but it is returning data with lifetime `'1` +LL | fn foo<'a>(&self, x: &i32) -> &i32 { + | - - let's call the lifetime of this reference `'1` + | | + | let's call the lifetime of this reference `'2` +LL | x + | ^ 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 foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - | ++ ++ ++ +LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + | ++ ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs index 3b2c8c7bc791f..784afa8b40f89 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.rs @@ -3,20 +3,23 @@ use std::pin::Pin; struct Foo; impl Foo { - fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { f } - //~^ lifetime may not live long enough + fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { + f //~ ERROR 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 + fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { + (self, f) //~ ERROR lifetime may not live long enough + } } type Alias = Pin; impl Foo { - fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg } - //~^ lifetime may not live long enough + fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { + arg //~ ERROR lifetime may not live long enough + } } fn main() {} diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index 773f9362ec53f..549b03b061bc9 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -1,42 +1,46 @@ error: lifetime may not live long enough - --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:6:46 + --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:7:9 | -LL | fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { f } - | - - ^ method was supposed to return data with lifetime `'2` but it is returning data with lifetime `'1` - | | | - | | let's call the lifetime of this reference `'1` +LL | fn a(self: Pin<&Foo>, f: &Foo) -> &Foo { + | - - 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 a<'a>(self: Pin<&'a Foo>, f: &'a Foo) -> &'a Foo { f } +LL | fn a<'a>(self: Pin<&'a Foo>, f: &'a Foo) -> &'a Foo { | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:12:69 + --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:14:9 | -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` - | | | - | | let's call the lifetime of this reference `'1` +LL | fn c(self: Pin<&Self>, f: &Foo, g: &Foo) -> (Pin<&Foo>, &Foo) { + | - - let's call the lifetime of this reference `'1` + | | | let's call the lifetime of this reference `'2` +LL | (self, 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 c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'a Foo) { (self, f) } +LL | fn c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'a Foo) { | ++++ ++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:18:58 + --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:21:9 | -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` +LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { + | -- ---- has type `Pin<&'1 Foo>` | | | lifetime `'a` defined here +LL | arg + | ^^^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &'a () { arg } +LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &'a () { | ++ ++ error: aborting due to 3 previous errors diff --git a/tests/ui/self/elision/lt-ref-self-async.fixed b/tests/ui/self/elision/lt-ref-self-async.fixed index 6d875ef0cec17..aa1d62012da03 100644 --- a/tests/ui/self/elision/lt-ref-self-async.fixed +++ b/tests/ui/self/elision/lt-ref-self-async.fixed @@ -4,7 +4,9 @@ use std::pin::Pin; -struct Struct<'a> { data: &'a u32 } +struct Struct<'a> { + data: &'a u32, +} impl<'a> Struct<'a> { // Test using `&self` sugar: @@ -42,4 +44,4 @@ impl<'a> Struct<'a> { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/lt-ref-self-async.rs b/tests/ui/self/elision/lt-ref-self-async.rs index a70e22ab77ad0..38de0fd39f086 100644 --- a/tests/ui/self/elision/lt-ref-self-async.rs +++ b/tests/ui/self/elision/lt-ref-self-async.rs @@ -4,7 +4,9 @@ use std::pin::Pin; -struct Struct<'a> { data: &'a u32 } +struct Struct<'a> { + data: &'a u32, +} impl<'a> Struct<'a> { // Test using `&self` sugar: @@ -42,4 +44,4 @@ impl<'a> Struct<'a> { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/lt-ref-self-async.stderr b/tests/ui/self/elision/lt-ref-self-async.stderr index c8b49de7671ef..b84044f754887 100644 --- a/tests/ui/self/elision/lt-ref-self-async.stderr +++ b/tests/ui/self/elision/lt-ref-self-async.stderr @@ -1,5 +1,5 @@ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:13:9 + --> $DIR/lt-ref-self-async.rs:15:9 | LL | async fn ref_self(&self, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -14,7 +14,7 @@ LL | async fn ref_self<'b>(&'b self, f: &'b u32) -> &u32 { | ++++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:20:9 + --> $DIR/lt-ref-self-async.rs:22:9 | LL | async fn ref_Self(self: &Self, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -29,7 +29,7 @@ LL | async fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &u32 { | ++++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:25:9 + --> $DIR/lt-ref-self-async.rs:27:9 | LL | async fn box_ref_Self(self: Box<&Self>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -44,7 +44,7 @@ LL | async fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &u32 { | ++++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:30:9 + --> $DIR/lt-ref-self-async.rs:32:9 | LL | async fn pin_ref_Self(self: Pin<&Self>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -59,7 +59,7 @@ LL | async fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &u32 { | ++++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:35:9 + --> $DIR/lt-ref-self-async.rs:37:9 | LL | async fn box_box_ref_Self(self: Box>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -74,7 +74,7 @@ LL | async fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> | ++++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self-async.rs:40:9 + --> $DIR/lt-ref-self-async.rs:42:9 | LL | async fn box_pin_Self(self: Box>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` diff --git a/tests/ui/self/elision/lt-ref-self.fixed b/tests/ui/self/elision/lt-ref-self.fixed index c9faa86c441b4..ff0c057fe427e 100644 --- a/tests/ui/self/elision/lt-ref-self.fixed +++ b/tests/ui/self/elision/lt-ref-self.fixed @@ -3,7 +3,9 @@ use std::pin::Pin; -struct Struct<'a> { data: &'a u32 } +struct Struct<'a> { + data: &'a u32, +} impl<'a> Struct<'a> { // Test using `&self` sugar: @@ -41,4 +43,4 @@ impl<'a> Struct<'a> { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/lt-ref-self.rs b/tests/ui/self/elision/lt-ref-self.rs index fbd0665b22d23..4cd97c5b729bd 100644 --- a/tests/ui/self/elision/lt-ref-self.rs +++ b/tests/ui/self/elision/lt-ref-self.rs @@ -3,7 +3,9 @@ use std::pin::Pin; -struct Struct<'a> { data: &'a u32 } +struct Struct<'a> { + data: &'a u32, +} impl<'a> Struct<'a> { // Test using `&self` sugar: @@ -41,4 +43,4 @@ impl<'a> Struct<'a> { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/lt-ref-self.stderr b/tests/ui/self/elision/lt-ref-self.stderr index 53b662bcb693c..237175ac7635e 100644 --- a/tests/ui/self/elision/lt-ref-self.stderr +++ b/tests/ui/self/elision/lt-ref-self.stderr @@ -1,5 +1,5 @@ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:12:9 + --> $DIR/lt-ref-self.rs:14: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<'b>(&'b self, f: &'b u32) -> &'b u32 { | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:19:9 + --> $DIR/lt-ref-self.rs:21: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<'b>(self: &'b Self, f: &'b u32) -> &'b u32 { | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:24:9 + --> $DIR/lt-ref-self.rs:26: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<'b>(self: Box<&'b Self>, f: &'b u32) -> &'b u32 { | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:29:9 + --> $DIR/lt-ref-self.rs:31: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<'b>(self: Pin<&'b Self>, f: &'b u32) -> &'b u32 { | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:34:9 + --> $DIR/lt-ref-self.rs:36:9 | LL | fn box_box_ref_Self(self: Box>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` @@ -74,7 +74,7 @@ LL | fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> &'b u3 | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/lt-ref-self.rs:39:9 + --> $DIR/lt-ref-self.rs:41:9 | LL | fn box_pin_Self(self: Box>, f: &u32) -> &u32 { | - - let's call the lifetime of this reference `'1` diff --git a/tests/ui/self/elision/ref-mut-self.fixed b/tests/ui/self/elision/ref-mut-self.fixed index 90e50221a19bc..7886d0979761a 100644 --- a/tests/ui/self/elision/ref-mut-self.fixed +++ b/tests/ui/self/elision/ref-mut-self.fixed @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&mut self` sugar: @@ -41,4 +41,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-mut-self.rs b/tests/ui/self/elision/ref-mut-self.rs index a09fcdfcbb2fd..87dab2a9ab421 100644 --- a/tests/ui/self/elision/ref-mut-self.rs +++ b/tests/ui/self/elision/ref-mut-self.rs @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&mut self` sugar: @@ -41,4 +41,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-mut-struct.fixed b/tests/ui/self/elision/ref-mut-struct.fixed index 275fafbad53a5..188d3bb517e04 100644 --- a/tests/ui/self/elision/ref-mut-struct.fixed +++ b/tests/ui/self/elision/ref-mut-struct.fixed @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&mut Struct` explicitly: @@ -34,4 +34,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-mut-struct.rs b/tests/ui/self/elision/ref-mut-struct.rs index 6bfdca62bca73..c227fa8bbfc6e 100644 --- a/tests/ui/self/elision/ref-mut-struct.rs +++ b/tests/ui/self/elision/ref-mut-struct.rs @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&mut Struct` explicitly: @@ -34,4 +34,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-self.fixed b/tests/ui/self/elision/ref-self.fixed index 41b11c2d77a3d..1369bb83e9708 100644 --- a/tests/ui/self/elision/ref-self.fixed +++ b/tests/ui/self/elision/ref-self.fixed @@ -12,7 +12,9 @@ struct Wrap(T, PhantomData

); impl Deref for Wrap { type Target = T; - fn deref(&self) -> &T { &self.0 } + fn deref(&self) -> &T { + &self.0 + } } impl Struct { @@ -56,4 +58,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-self.rs b/tests/ui/self/elision/ref-self.rs index 9b204e2a43ba4..4b4b8aa5b511d 100644 --- a/tests/ui/self/elision/ref-self.rs +++ b/tests/ui/self/elision/ref-self.rs @@ -12,7 +12,9 @@ struct Wrap(T, PhantomData

); impl Deref for Wrap { type Target = T; - fn deref(&self) -> &T { &self.0 } + fn deref(&self) -> &T { + &self.0 + } } impl Struct { @@ -56,4 +58,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-self.stderr b/tests/ui/self/elision/ref-self.stderr index b17667827bb78..a39a6a15385ea 100644 --- a/tests/ui/self/elision/ref-self.stderr +++ b/tests/ui/self/elision/ref-self.stderr @@ -1,5 +1,5 @@ error: lifetime may not live long enough - --> $DIR/ref-self.rs:22:9 + --> $DIR/ref-self.rs:24: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:29:9 + --> $DIR/ref-self.rs:31: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:34:9 + --> $DIR/ref-self.rs:36: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:39:9 + --> $DIR/ref-self.rs:41: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:44:9 + --> $DIR/ref-self.rs:46:9 | LL | fn box_box_ref_Self(self: Box>, 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>, f: &'a u32) -> &'a u3 | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/ref-self.rs:49:9 + --> $DIR/ref-self.rs:51:9 | LL | fn box_pin_ref_Self(self: Box>, 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>, f: &'a u32) -> &'a u3 | ++++ ++ ++ ++ error: lifetime may not live long enough - --> $DIR/ref-self.rs:54:9 + --> $DIR/ref-self.rs:56:9 | LL | fn wrap_ref_Self_Self(self: Wrap<&Self, Self>, f: &u8) -> &u8 { | - - let's call the lifetime of this reference `'1` diff --git a/tests/ui/self/elision/ref-struct.fixed b/tests/ui/self/elision/ref-struct.fixed index 1c26c84c08848..a9ecbc9c3aecd 100644 --- a/tests/ui/self/elision/ref-struct.fixed +++ b/tests/ui/self/elision/ref-struct.fixed @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&Struct` explicitly: @@ -34,4 +34,4 @@ impl Struct { } } -fn main() { } +fn main() {} diff --git a/tests/ui/self/elision/ref-struct.rs b/tests/ui/self/elision/ref-struct.rs index 78b894765aa41..733a175e7a1de 100644 --- a/tests/ui/self/elision/ref-struct.rs +++ b/tests/ui/self/elision/ref-struct.rs @@ -3,7 +3,7 @@ use std::pin::Pin; -struct Struct { } +struct Struct {} impl Struct { // Test using `&Struct` explicitly: @@ -34,4 +34,4 @@ impl Struct { } } -fn main() { } +fn main() {} From 1775e7b93d4142eb2e4c75c2d49a9c4d8541d7a6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Tue, 7 May 2024 19:54:16 +0000 Subject: [PATCH 5/6] Tweak suggested lifetimes to modify return type instead of `&self` receiver Do not suggest constraining the `&self` param, but rather the return type. If that is wrong (because it is not sufficient), a follow up error will tell the user to fix it. This way we lower the chances of *over* constraining, but still get the cake of "correctly" contrained in two steps. This is a correct suggestion: ``` error: lifetime may not live long enough --> $DIR/ex3-both-anon-regions-return-type-is-anon.rs:9:9 | LL | fn foo<'a>(&self, x: &i32) -> &i32 { | - - let's call the lifetime of this reference `'1` | | | let's call the lifetime of this reference `'2` LL | x | ^ 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 foo<'a>(&self, x: &'a i32) -> &'a i32 { | ++ ++ ``` While this is incomplete because it should suggestino `&'a self` ``` error: lifetime may not live long enough --> $DIR/ex3-both-anon-regions-self-is-anon.rs:7:19 | LL | fn foo<'a>(&self, x: &Foo) -> &Foo { | - - let's call the lifetime of this reference `'1` | | | let's call the lifetime of this reference `'2` LL | if true { x } else { self } | ^ 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 foo<'a>(&self, x: &'a Foo) -> &'a Foo { | ++ ++ ``` but the follow up error is ``` error: lifetime may not live long enough --> tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.rs:7:30 | 6 | fn foo<'a>(&self, x: &'a Foo) -> &'a Foo { | -- - let's call the lifetime of this reference `'1` | | | lifetime `'a` defined here 7 | if true { x } else { self } | ^^^^ method was supposed to return data with lifetime `'a` but it is returning data with lifetime `'1` | help: consider introducing a named lifetime parameter and update trait if needed | 6 | fn foo<'a>(&'a self, x: &'a Foo) -> &'a Foo { | ++ ``` --- compiler/rustc_infer/src/errors/mod.rs | 10 +++++-- tests/ui/lifetimes/issue-17728.stderr | 4 +-- ...ne-existing-name-return-type-is-anon.fixed | 2 +- ...e-existing-name-return-type-is-anon.stderr | 4 +-- ...oth-anon-regions-return-type-is-anon.fixed | 2 +- ...th-anon-regions-return-type-is-anon.stderr | 4 +-- .../ex3-both-anon-regions-self-is-anon.stderr | 4 +-- ...ry_self_types_pin_lifetime_mismatch.stderr | 12 ++++---- tests/ui/self/elision/lt-ref-self.fixed | 12 ++++---- tests/ui/self/elision/lt-ref-self.stderr | 24 ++++++++-------- tests/ui/self/elision/ref-mut-self.fixed | 12 ++++---- tests/ui/self/elision/ref-mut-self.stderr | 24 ++++++++-------- tests/ui/self/elision/ref-mut-struct.fixed | 10 +++---- tests/ui/self/elision/ref-mut-struct.stderr | 20 ++++++------- tests/ui/self/elision/ref-self.fixed | 14 +++++----- tests/ui/self/elision/ref-self.stderr | 28 +++++++++---------- tests/ui/self/elision/ref-struct.fixed | 10 +++---- tests/ui/self/elision/ref-struct.stderr | 20 ++++++------- 18 files changed, 111 insertions(+), 105 deletions(-) diff --git a/compiler/rustc_infer/src/errors/mod.rs b/compiler/rustc_infer/src/errors/mod.rs index f60ecb3f453ae..9998f089588aa 100644 --- a/compiler/rustc_infer/src/errors/mod.rs +++ b/compiler/rustc_infer/src/errors/mod.rs @@ -484,13 +484,19 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { suggestions: vec![], suggestion_param_name: suggestion_param_name.clone(), }; - visitor.visit_ty(self.ty_sub); - visitor.visit_ty(self.ty_sup); if let Some(fn_decl) = node.fn_decl() && let hir::FnRetTy::Return(ty) = fn_decl.output { visitor.visit_ty(ty); } + if visitor.suggestions.is_empty() { + // Do not suggest constraining the `&self` param, but rather the return type. + // If that is wrong (because it is not sufficient), a follow up error will tell the + // user to fix it. This way we lower the chances of *over* constraining, but still + // get the cake of "correctly" contrained in two steps. + visitor.visit_ty(self.ty_sup); + } + visitor.visit_ty(self.ty_sub); if visitor.suggestions.is_empty() { return false; } diff --git a/tests/ui/lifetimes/issue-17728.stderr b/tests/ui/lifetimes/issue-17728.stderr index da4ce2dd2911d..eb4381ea99eef 100644 --- a/tests/ui/lifetimes/issue-17728.stderr +++ b/tests/ui/lifetimes/issue-17728.stderr @@ -29,8 +29,8 @@ LL | Some(entry) => Ok(entry), | help: consider introducing a named lifetime parameter | -LL | fn attemptTraverse<'a>(&'a self, room: &'a Room, directionStr: &str) -> Result<&'a Room, &'a str> { - | ++++ ++ ++ ++ ++ +LL | fn attemptTraverse<'a>(&self, room: &'a Room, directionStr: &str) -> Result<&'a Room, &'a str> { + | ++++ ++ ++ ++ error: aborting due to 2 previous errors diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed index 3408463ce4990..40eee22fc321d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.fixed @@ -5,7 +5,7 @@ struct Foo { } impl Foo { - fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + fn foo<'a>(&self, x: &'a i32) -> &'a i32 { x //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index ca6ee1c25cdd4..345f099542d91 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -10,8 +10,8 @@ LL | x | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - | ++ ++ +LL | fn foo<'a>(&self, x: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed index 3408463ce4990..40eee22fc321d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.fixed @@ -5,7 +5,7 @@ struct Foo { } impl Foo { - fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { + fn foo<'a>(&self, x: &'a i32) -> &'a i32 { x //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr index a81b5cfad5a5b..dd45c8b1cb77a 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr @@ -10,8 +10,8 @@ LL | x | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a i32) -> &'a i32 { - | ++ ++ ++ +LL | fn foo<'a>(&self, x: &'a i32) -> &'a i32 { + | ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr index 0a312cf93c8de..997537f1ecd9f 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr @@ -10,8 +10,8 @@ LL | if true { x } else { self } | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn foo<'a>(&'a self, x: &'a Foo) -> &'a Foo { - | ++ ++ ++ +LL | fn foo<'a>(&self, x: &'a Foo) -> &'a Foo { + | ++ ++ error: aborting due to 1 previous error diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index 549b03b061bc9..98f493f3f91d0 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn a<'a>(self: Pin<&'a Foo>, f: &'a Foo) -> &'a Foo { - | ++++ ++ ++ ++ +LL | fn a<'a>(self: Pin<&Foo>, f: &'a Foo) -> &'a Foo { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:14:9 @@ -25,8 +25,8 @@ LL | (self, f) | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn c<'a>(self: Pin<&'a Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'a Foo) { - | ++++ ++ ++ ++ ++ +LL | fn c<'a>(self: Pin<&Self>, f: &'a Foo, g: &Foo) -> (Pin<&'a Foo>, &'a Foo) { + | ++++ ++ ++ ++ error: lifetime may not live long enough --> $DIR/arbitrary_self_types_pin_lifetime_mismatch.rs:21:9 @@ -40,8 +40,8 @@ LL | arg | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &'a () { - | ++ ++ +LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &'a () { + | ++ error: aborting due to 3 previous errors diff --git a/tests/ui/self/elision/lt-ref-self.fixed b/tests/ui/self/elision/lt-ref-self.fixed index ff0c057fe427e..1d90eacea50d8 100644 --- a/tests/ui/self/elision/lt-ref-self.fixed +++ b/tests/ui/self/elision/lt-ref-self.fixed @@ -10,34 +10,34 @@ struct Struct<'a> { impl<'a> Struct<'a> { // Test using `&self` sugar: - fn ref_self<'b>(&'b self, f: &'b u32) -> &'b u32 { + fn ref_self<'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 { + fn ref_Self<'b>(self: &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 { + fn box_ref_Self<'b>(self: Box<&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 { + fn pin_ref_Self<'b>(self: Pin<&Self>, f: &'b u32) -> &'b u32 { f //~^ ERROR lifetime may not live long enough } - fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { + fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { f //~^ ERROR lifetime may not live long enough } - fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { + fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { f //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/self/elision/lt-ref-self.stderr b/tests/ui/self/elision/lt-ref-self.stderr index 237175ac7635e..5c8e0a7a742a9 100644 --- a/tests/ui/self/elision/lt-ref-self.stderr +++ b/tests/ui/self/elision/lt-ref-self.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_self<'b>(&'b self, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn ref_self<'b>(&self, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:21:9 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Self<'b>(self: &'b Self, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn ref_Self<'b>(self: &Self, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:26:9 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Self<'b>(self: Box<&'b Self>, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn box_ref_Self<'b>(self: Box<&Self>, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:31:9 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Self<'b>(self: Pin<&'b Self>, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn pin_ref_Self<'b>(self: Pin<&Self>, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:36:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn box_box_ref_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/lt-ref-self.rs:41:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { - | ++++ ++ ++ ++ +LL | fn box_pin_Self<'b>(self: Box>, f: &'b u32) -> &'b u32 { + | ++++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/ref-mut-self.fixed b/tests/ui/self/elision/ref-mut-self.fixed index 7886d0979761a..42e8050f65e35 100644 --- a/tests/ui/self/elision/ref-mut-self.fixed +++ b/tests/ui/self/elision/ref-mut-self.fixed @@ -8,34 +8,34 @@ struct Struct {} impl Struct { // Test using `&mut self` sugar: - fn ref_self<'a>(&'a mut self, f: &'a u32) -> &'a u32 { + fn ref_self<'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 { + fn ref_Self<'a>(self: &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 { + fn box_ref_Self<'a>(self: Box<&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 { + fn pin_ref_Self<'a>(self: Pin<&mut Self>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/self/elision/ref-mut-self.stderr b/tests/ui/self/elision/ref-mut-self.stderr index a09034e5f71d7..620706fdbdbc7 100644 --- a/tests/ui/self/elision/ref-mut-self.stderr +++ b/tests/ui/self/elision/ref-mut-self.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_self<'a>(&'a mut self, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn ref_self<'a>(&mut self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:19:9 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Self<'a>(self: &'a mut Self, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn ref_Self<'a>(self: &mut Self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:24:9 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Self<'a>(self: Box<&'a mut Self>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_ref_Self<'a>(self: Box<&mut Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:29:9 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Self<'a>(self: Pin<&'a mut Self>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn pin_ref_Self<'a>(self: Pin<&mut Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:34:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-self.rs:39:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: aborting due to 6 previous errors diff --git a/tests/ui/self/elision/ref-mut-struct.fixed b/tests/ui/self/elision/ref-mut-struct.fixed index 188d3bb517e04..f7a84d4a45c7c 100644 --- a/tests/ui/self/elision/ref-mut-struct.fixed +++ b/tests/ui/self/elision/ref-mut-struct.fixed @@ -8,27 +8,27 @@ struct Struct {} impl Struct { // Test using `&mut Struct` explicitly: - fn ref_Struct<'a>(self: &'a mut Struct, f: &'a u32) -> &'a u32 { + fn ref_Struct<'a>(self: &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 { + fn box_ref_Struct<'a>(self: Box<&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 { + fn pin_ref_Struct<'a>(self: Pin<&mut Struct>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/self/elision/ref-mut-struct.stderr b/tests/ui/self/elision/ref-mut-struct.stderr index 19b09272504e3..cce07f827184e 100644 --- a/tests/ui/self/elision/ref-mut-struct.stderr +++ b/tests/ui/self/elision/ref-mut-struct.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Struct<'a>(self: &'a mut Struct, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn ref_Struct<'a>(self: &mut Struct, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-struct.rs:17:9 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Struct<'a>(self: Box<&'a mut Struct>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_ref_Struct<'a>(self: Box<&mut Struct>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-struct.rs:22:9 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Struct<'a>(self: Pin<&'a mut Struct>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn pin_ref_Struct<'a>(self: Pin<&mut Struct>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-struct.rs:27:9 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-mut-struct.rs:32:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_pin_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: aborting due to 5 previous errors diff --git a/tests/ui/self/elision/ref-self.fixed b/tests/ui/self/elision/ref-self.fixed index 1369bb83e9708..8bf5a0bb22322 100644 --- a/tests/ui/self/elision/ref-self.fixed +++ b/tests/ui/self/elision/ref-self.fixed @@ -20,39 +20,39 @@ impl Deref for Wrap { impl Struct { // Test using `&self` sugar: - fn ref_self<'a>(&'a self, f: &'a u32) -> &'a u32 { + fn ref_self<'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 { + fn ref_Self<'a>(self: &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 { + fn box_ref_Self<'a>(self: Box<&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 { + fn pin_ref_Self<'a>(self: Pin<&Self>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_pin_ref_Self<'a>(self: Box>, 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 { + fn wrap_ref_Self_Self<'a>(self: Wrap<&Self, Self>, f: &'a u8) -> &'a u8 { f //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/self/elision/ref-self.stderr b/tests/ui/self/elision/ref-self.stderr index a39a6a15385ea..c4ec8c55a003f 100644 --- a/tests/ui/self/elision/ref-self.stderr +++ b/tests/ui/self/elision/ref-self.stderr @@ -10,8 +10,8 @@ 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<'a>(&self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:31:9 @@ -25,8 +25,8 @@ 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<'a>(self: &Self, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:36:9 @@ -40,8 +40,8 @@ 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<'a>(self: Box<&Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:41:9 @@ -55,8 +55,8 @@ 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<'a>(self: Pin<&Self>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:46:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_box_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:51:9 @@ -85,8 +85,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_pin_ref_Self<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-self.rs:56:9 @@ -100,8 +100,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn wrap_ref_Self_Self<'a>(self: Wrap<&'a Self, Self>, f: &'a u8) -> &'a u8 { - | ++++ ++ ++ ++ +LL | fn wrap_ref_Self_Self<'a>(self: Wrap<&Self, Self>, f: &'a u8) -> &'a u8 { + | ++++ ++ ++ error: aborting due to 7 previous errors diff --git a/tests/ui/self/elision/ref-struct.fixed b/tests/ui/self/elision/ref-struct.fixed index a9ecbc9c3aecd..411f601319563 100644 --- a/tests/ui/self/elision/ref-struct.fixed +++ b/tests/ui/self/elision/ref-struct.fixed @@ -8,27 +8,27 @@ struct Struct {} impl Struct { // Test using `&Struct` explicitly: - fn ref_Struct<'a>(self: &'a Struct, f: &'a u32) -> &'a u32 { + fn ref_Struct<'a>(self: &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 { + fn box_ref_Struct<'a>(self: Box<&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 { + fn pin_ref_Struct<'a>(self: Pin<&Struct>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } - fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { f //~^ ERROR lifetime may not live long enough } diff --git a/tests/ui/self/elision/ref-struct.stderr b/tests/ui/self/elision/ref-struct.stderr index 157e0d407932a..860186c835321 100644 --- a/tests/ui/self/elision/ref-struct.stderr +++ b/tests/ui/self/elision/ref-struct.stderr @@ -10,8 +10,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn ref_Struct<'a>(self: &'a Struct, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn ref_Struct<'a>(self: &Struct, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-struct.rs:17:9 @@ -25,8 +25,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_ref_Struct<'a>(self: Box<&'a Struct>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_ref_Struct<'a>(self: Box<&Struct>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-struct.rs:22:9 @@ -40,8 +40,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn pin_ref_Struct<'a>(self: Pin<&'a Struct>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn pin_ref_Struct<'a>(self: Pin<&Struct>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-struct.rs:27:9 @@ -55,8 +55,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_box_ref_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: lifetime may not live long enough --> $DIR/ref-struct.rs:32:9 @@ -70,8 +70,8 @@ LL | f | help: consider introducing a named lifetime parameter and update trait if needed | -LL | fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { - | ++++ ++ ++ ++ +LL | fn box_pin_Struct<'a>(self: Box>, f: &'a u32) -> &'a u32 { + | ++++ ++ ++ error: aborting due to 5 previous errors From cf5702ee91dd9ba93c19aae9e663e613a577d02b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Esteban=20K=C3=BCber?= Date: Fri, 17 May 2024 21:23:47 +0000 Subject: [PATCH 6/6] Detect when a lifetime is being reused in suggestion --- compiler/rustc_infer/messages.ftl | 5 ++++- compiler/rustc_infer/src/errors/mod.rs | 1 + tests/ui/lifetimes/issue-90170-elision-mismatch.stderr | 2 +- .../ex1-return-one-existing-name-if-else-using-impl.stderr | 2 +- .../ex1-return-one-existing-name-return-type-is-anon.stderr | 2 +- .../ex1-return-one-existing-name-self-is-anon.stderr | 2 +- .../ex3-both-anon-regions-return-type-is-anon.stderr | 2 +- .../ex3-both-anon-regions-self-is-anon.stderr | 2 +- .../arbitrary_self_types_pin_lifetime_mismatch-async.stderr | 2 +- .../self/arbitrary_self_types_pin_lifetime_mismatch.stderr | 2 +- 10 files changed, 13 insertions(+), 9 deletions(-) diff --git a/compiler/rustc_infer/messages.ftl b/compiler/rustc_infer/messages.ftl index 64f52ea7ac196..8f1c4ad462a67 100644 --- a/compiler/rustc_infer/messages.ftl +++ b/compiler/rustc_infer/messages.ftl @@ -164,7 +164,10 @@ infer_label_bad = {$bad_kind -> infer_lf_bound_not_satisfied = lifetime bound not satisfied infer_lifetime_mismatch = lifetime mismatch -infer_lifetime_param_suggestion = consider introducing a named lifetime parameter{$is_impl -> +infer_lifetime_param_suggestion = consider {$is_reuse -> + [true] reusing + *[false] introducing +} a named lifetime parameter{$is_impl -> [true] {" "}and update trait if needed *[false] {""} } diff --git a/compiler/rustc_infer/src/errors/mod.rs b/compiler/rustc_infer/src/errors/mod.rs index 9998f089588aa..8bb0dc39143ce 100644 --- a/compiler/rustc_infer/src/errors/mod.rs +++ b/compiler/rustc_infer/src/errors/mod.rs @@ -517,6 +517,7 @@ impl Subdiagnostic for AddLifetimeParamsSuggestion<'_> { Applicability::MaybeIncorrect, ); diag.arg("is_impl", is_impl); + diag.arg("is_reuse", !introduce_new); true }; diff --git a/tests/ui/lifetimes/issue-90170-elision-mismatch.stderr b/tests/ui/lifetimes/issue-90170-elision-mismatch.stderr index 48fb3fb4a2293..82511d07b0efc 100644 --- a/tests/ui/lifetimes/issue-90170-elision-mismatch.stderr +++ b/tests/ui/lifetimes/issue-90170-elision-mismatch.stderr @@ -35,7 +35,7 @@ LL | pub fn foo3<'a>(_other: &'a [u8], x: &mut Vec<&u8>, y: &u8) { x.push(y); } | | let's call the lifetime of this reference `'1` | let's call the lifetime of this reference `'2` | -help: consider introducing a named lifetime parameter +help: consider reusing a named lifetime parameter | LL | pub fn foo3<'a>(_other: &'a [u8], x: &mut Vec<&'a u8>, y: &'a u8) { x.push(y); } | ++ ++ diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr index 6bc82910b06a5..2caab3df6b85b 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl.stderr @@ -9,7 +9,7 @@ LL | LL | if x > y { x } else { y } | ^ associated function was supposed to return data with lifetime `'a` but it is returning data with lifetime `'1` | -help: consider introducing a named lifetime parameter and update trait if needed +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn foo<'a>(x: &'a i32, y: &'a i32) -> &'a i32 { | ++ diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr index 345f099542d91..c743351a67025 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-return-type-is-anon.stderr @@ -8,7 +8,7 @@ LL | fn foo<'a>(&self, x: &'a i32) -> &i32 { LL | x | ^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` | -help: consider introducing a named lifetime parameter and update trait if needed +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn foo<'a>(&self, x: &'a i32) -> &'a i32 { | ++ diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr index f106d45b9acdd..4ed6c3bc92d7d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-self-is-anon.stderr @@ -9,7 +9,7 @@ LL | LL | if true { x } else { self } | ^^^^ method was supposed to return data with lifetime `'a` but it is returning data with lifetime `'1` | -help: consider introducing a named lifetime parameter and update trait if needed +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn foo<'a>(&'a self, x: &'a Foo) -> &'a Foo { | ++ diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr index dd45c8b1cb77a..673a87a4537c4 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-return-type-is-anon.stderr @@ -8,7 +8,7 @@ LL | fn foo<'a>(&self, x: &i32) -> &i32 { LL | x | ^ 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 +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn foo<'a>(&self, x: &'a i32) -> &'a i32 { | ++ ++ diff --git a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr index 997537f1ecd9f..64bd448a0747d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex3-both-anon-regions-self-is-anon.stderr @@ -8,7 +8,7 @@ LL | fn foo<'a>(&self, x: &Foo) -> &Foo { LL | if true { x } else { self } | ^ 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 +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn foo<'a>(&self, x: &'a Foo) -> &'a Foo { | ++ ++ diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr index bb643ab827222..b00260fa0efa4 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch-async.stderr @@ -35,7 +35,7 @@ LL | async fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { arg } | | let's call the lifetime of this reference `'1` | lifetime `'a` defined here | -help: consider introducing a named lifetime parameter and update trait if needed +help: consider reusing a named lifetime parameter and update trait if needed | LL | async fn bar<'a>(self: Alias<&'a Self>, arg: &'a ()) -> &() { arg } | ++ diff --git a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr index 98f493f3f91d0..57527dd31df35 100644 --- a/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr +++ b/tests/ui/self/arbitrary_self_types_pin_lifetime_mismatch.stderr @@ -38,7 +38,7 @@ LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &() { LL | arg | ^^^ method was supposed to return data with lifetime `'1` but it is returning data with lifetime `'a` | -help: consider introducing a named lifetime parameter and update trait if needed +help: consider reusing a named lifetime parameter and update trait if needed | LL | fn bar<'a>(self: Alias<&Self>, arg: &'a ()) -> &'a () { | ++