diff options
| author | Esteban Küber <esteban@kuber.com.ar> | 2020-07-01 14:02:57 -0700 |
|---|---|---|
| committer | Esteban Küber <esteban@kuber.com.ar> | 2020-07-22 12:25:55 -0700 |
| commit | 53d96b5159ee4eb937728bbc33c28c3b98ebebd6 (patch) | |
| tree | 316f97dce47e66f8a38021faffe36a8fd026e778 | |
| parent | 3712dfc677bb5dff909cdc29fd2da11772ddba9e (diff) | |
| download | rust-53d96b5159ee4eb937728bbc33c28c3b98ebebd6.tar.gz rust-53d96b5159ee4eb937728bbc33c28c3b98ebebd6.zip | |
Handle fully-qualified paths and add test cases
8 files changed, 404 insertions, 98 deletions
diff --git a/src/librustc_infer/infer/error_reporting/nice_region_error/static_impl_trait.rs b/src/librustc_infer/infer/error_reporting/nice_region_error/static_impl_trait.rs index 18466b00da9..9581ee611fc 100644 --- a/src/librustc_infer/infer/error_reporting/nice_region_error/static_impl_trait.rs +++ b/src/librustc_infer/infer/error_reporting/nice_region_error/static_impl_trait.rs @@ -12,6 +12,7 @@ use rustc_hir::{ TyKind, }; use rustc_middle::ty::{self, AssocItemContainer, RegionKind, Ty, TypeFoldable, TypeVisitor}; +use rustc_span::symbol::Ident; use rustc_span::{MultiSpan, Span}; impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { @@ -115,33 +116,6 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { err.span_label(param.param_ty_span, &format!("this data with {}...", lifetime)); debug!("try_report_static_impl_trait: param_info={:?}", param); - let fn_returns = tcx.return_type_impl_or_dyn_traits(anon_reg_sup.def_id); - - let mut postfix = String::new(); - if let SubregionOrigin::Subtype(box TypeTrace { cause, .. }) = &sup_origin { - if let ObligationCauseCode::UnifyReceiver(ctxt) = &cause.code { - if self.find_impl_on_dyn_trait(&mut err, param.param_ty, &ctxt) - && fn_returns.is_empty() - { - err.code(rustc_errors::error_code!(E0767)); - err.set_primary_message(&format!( - "{} has {} but calling `{}` introduces an implicit `'static` lifetime \ - requirement", - param_name, lifetime, ctxt.assoc_item.ident, - )); - postfix = format!( - " because of an implicit lifetime on the {}", - match ctxt.assoc_item.container { - AssocItemContainer::TraitContainer(id) => - format!("`impl` of `{}`", tcx.def_path_str(id)), - AssocItemContainer::ImplContainer(_) => "inherent `impl`".to_string(), - }, - ); - } - // } - } - } - // We try to make the output have fewer overlapping spans if possible. if (sp == sup_origin.span() || !return_sp.overlaps(sup_origin.span())) && sup_origin.span() != return_sp @@ -168,35 +142,68 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { // | ---- ^ err.span_label( sup_origin.span(), - &format!( - "...is captured here, requiring it to live as long as `'static`{}", - postfix - ), + "...is captured here, requiring it to live as long as `'static`", ); } else { err.span_label(sup_origin.span(), "...is captured here..."); if return_sp < sup_origin.span() { err.span_note( return_sp, - &format!("...and is required to live as long as `'static` here{}", postfix), + "...and is required to live as long as `'static` here", ); } else { err.span_label( return_sp, - &format!("...and is required to live as long as `'static` here{}", postfix), + "...and is required to live as long as `'static` here", ); } } } else { err.span_label( return_sp, - &format!( - "...is captured and required to live as long as `'static` here{}", - postfix - ), + "...is captured and required to live as long as `'static` here", ); } + let fn_returns = tcx.return_type_impl_or_dyn_traits(anon_reg_sup.def_id); + + let mut override_error_code = None; + if let SubregionOrigin::Subtype(box TypeTrace { cause, .. }) = &sup_origin { + if let ObligationCauseCode::UnifyReceiver(ctxt) = &cause.code { + // Handle case of `impl Foo for dyn Bar { fn qux(&self) {} }` introducing a + // `'static` lifetime when called as a method on a binding: `bar.qux()`. + if self.find_impl_on_dyn_trait(&mut err, param.param_ty, &ctxt) { + override_error_code = Some(ctxt.assoc_item.ident); + } + } + } + if let SubregionOrigin::Subtype(box TypeTrace { cause, .. }) = &sub_origin { + if let ObligationCauseCode::ItemObligation(item_def_id) = cause.code { + // Same case of `impl Foo for dyn Bar { fn qux(&self) {} }` introducing a `'static` + // lifetime as above, but called using a fully-qualified path to the method: + // `Foo::qux(bar)`. + let mut v = TraitObjectVisitor(vec![]); + v.visit_ty(param.param_ty); + if let Some((ident, self_ty)) = + self.get_impl_ident_and_self_ty_from_trait(item_def_id, &v.0[..]) + { + if self.suggest_constrain_dyn_trait_in_impl(&mut err, &v.0[..], ident, self_ty) + { + override_error_code = Some(ident); + } + } + } + } + if let (Some(ident), true) = (override_error_code, fn_returns.is_empty()) { + // Provide a more targetted error code and description. + err.code(rustc_errors::error_code!(E0767)); + err.set_primary_message(&format!( + "{} has {} but calling `{}` introduces an implicit `'static` lifetime \ + requirement", + param_name, lifetime, ident, + )); + } + debug!("try_report_static_impl_trait: fn_return={:?}", fn_returns); // FIXME: account for the need of parens in `&(dyn Trait + '_)` let consider = "consider changing the"; @@ -318,40 +325,19 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { Some(ErrorReported) } - /// When we call a method coming from an `impl Foo for dyn Bar`, `dyn Bar` introduces a default - /// `'static` obligation. Suggest relaxing that implicit bound. - fn find_impl_on_dyn_trait( + fn get_impl_ident_and_self_ty_from_trait( &self, - err: &mut DiagnosticBuilder<'_>, - ty: Ty<'_>, - ctxt: &UnifyReceiverContext<'tcx>, - ) -> bool { + def_id: DefId, + trait_objects: &[DefId], + ) -> Option<(Ident, &'tcx hir::Ty<'tcx>)> { let tcx = self.tcx(); - let mut suggested = false; - - // Find the method being called. - let instance = match ty::Instance::resolve( - tcx, - ctxt.param_env, - ctxt.assoc_item.def_id, - self.infcx.resolve_vars_if_possible(&ctxt.substs), - ) { - Ok(Some(instance)) => instance, - _ => return false, - }; - - let mut v = TraitObjectVisitor(vec![]); - v.visit_ty(ty); - - // Get the `Ident` of the method being called and the corresponding `impl` (to point at - // `Bar` in `impl Foo for dyn Bar {}` and the definition of the method being called). - let (ident, self_ty) = match tcx.hir().get_if_local(instance.def_id()) { + match tcx.hir().get_if_local(def_id) { Some(Node::ImplItem(ImplItem { ident, hir_id, .. })) => { match tcx.hir().find(tcx.hir().get_parent_item(*hir_id)) { Some(Node::Item(Item { kind: ItemKind::Impl { self_ty, .. }, .. })) => { - (ident, self_ty) + Some((*ident, self_ty)) } - _ => return false, + _ => None, } } Some(Node::TraitItem(TraitItem { ident, hir_id, .. })) => { @@ -372,7 +358,7 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { Some(Node::Item(Item { kind: ItemKind::Impl { self_ty, .. }, .. - })) if v.0.iter().all(|did| { + })) if trait_objects.iter().all(|did| { // FIXME: we should check `self_ty` against the receiver // type in the `UnifyReceiver` context, but for now, use // this imperfect proxy. This will fail if there are @@ -391,20 +377,64 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { }) .next() { - Some(self_ty) => (ident, self_ty), - _ => return false, + Some(self_ty) => Some((*ident, self_ty)), + _ => None, } } - _ => return false, + _ => None, } } + _ => None, + } + } + + /// When we call a method coming from an `impl Foo for dyn Bar`, `dyn Bar` introduces a default + /// `'static` obligation. Suggest relaxing that implicit bound. + fn find_impl_on_dyn_trait( + &self, + err: &mut DiagnosticBuilder<'_>, + ty: Ty<'_>, + ctxt: &UnifyReceiverContext<'tcx>, + ) -> bool { + let tcx = self.tcx(); + + // Find the method being called. + let instance = match ty::Instance::resolve( + tcx, + ctxt.param_env, + ctxt.assoc_item.def_id, + self.infcx.resolve_vars_if_possible(&ctxt.substs), + ) { + Ok(Some(instance)) => instance, _ => return false, }; + let mut v = TraitObjectVisitor(vec![]); + v.visit_ty(ty); + + // Get the `Ident` of the method being called and the corresponding `impl` (to point at + // `Bar` in `impl Foo for dyn Bar {}` and the definition of the method being called). + let (ident, self_ty) = + match self.get_impl_ident_and_self_ty_from_trait(instance.def_id(), &v.0[..]) { + Some((ident, self_ty)) => (ident, self_ty), + None => return false, + }; + // Find the trait object types in the argument, so we point at *only* the trait object. - for found_did in &v.0 { + self.suggest_constrain_dyn_trait_in_impl(err, &v.0[..], ident, self_ty) + } + + fn suggest_constrain_dyn_trait_in_impl( + &self, + err: &mut DiagnosticBuilder<'_>, + found_dids: &[DefId], + ident: Ident, + self_ty: &hir::Ty<'_>, + ) -> bool { + let mut suggested = false; + for found_did in found_dids { let mut hir_v = HirTraitObjectVisitor(vec![], *found_did); - hir_v.visit_ty(self_ty); + hir_v.visit_ty(&self_ty); for span in &hir_v.0 { let mut multi_span: MultiSpan = vec![*span].into(); multi_span.push_span_label( @@ -415,17 +445,7 @@ impl<'a, 'tcx> NiceRegionError<'a, 'tcx> { ident.span, "calling this method introduces the `impl`'s 'static` requirement".to_string(), ); - err.span_note( - multi_span, - &format!( - "{} has a `'static` requirement", - match ctxt.assoc_item.container { - AssocItemContainer::TraitContainer(id) => - format!("`impl` of `{}`", tcx.def_path_str(id)), - AssocItemContainer::ImplContainer(_) => "inherent `impl`".to_string(), - }, - ), - ); + err.span_note(multi_span, "the used `impl` has a `'static` requirement"); err.span_suggestion_verbose( span.shrink_to_hi(), "consider relaxing the implicit `'static` requirement", diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.nll.stderr b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.nll.stderr new file mode 100644 index 00000000000..6921926590a --- /dev/null +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.nll.stderr @@ -0,0 +1,37 @@ +error[E0597]: `val` does not live long enough + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:22:9 + | +LL | fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> { + | -- lifetime `'a` defined here ------------------- opaque type requires that `val` is borrowed for `'a` +LL | val.use_self() + | ^^^ borrowed value does not live long enough +LL | } + | - `val` dropped here while still borrowed + | +help: you can add a bound to the opaque type to make it last less than `'static` and match `'a` + | +LL | fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> + 'a { + | ^^^^ + +error[E0515]: cannot return value referencing function parameter `val` + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:44:9 + | +LL | val.use_self() + | ---^^^^^^^^^^^ + | | + | returns a value referencing data owned by the current function + | `val` is borrowed here + +error[E0515]: cannot return value referencing function parameter `val` + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:110:9 + | +LL | val.use_self() + | ---^^^^^^^^^^^ + | | + | returns a value referencing data owned by the current function + | `val` is borrowed here + +error: aborting due to 3 previous errors + +Some errors have detailed explanations: E0515, E0597. +For more information about an error, try `rustc --explain E0515`. diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs new file mode 100644 index 00000000000..ae6ffa8d93e --- /dev/null +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs @@ -0,0 +1,114 @@ + +// FIXME: the following cases need to suggest more things to make users reach a working end state. + +mod bav { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait { + type Assoc: Bar; + } + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Bar {} + + impl MyTrait for Box<dyn ObjectTrait<Assoc = i32>> { + fn use_self(&self) -> &() { panic!() } + } + impl Bar for i32 {} + + fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> { + val.use_self() //~ ERROR E0597 + } +} + +mod bap { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait { + type Assoc: Bar; + } + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Bar {} + + impl MyTrait for Box<dyn ObjectTrait<Assoc = i32>> { + fn use_self(&self) -> &() { panic!() } + } + impl Bar for i32 {} + + fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> + 'a { + val.use_self() //~ ERROR E0515 + } +} + +// This case in particular requires the user to write all of the bounds we have in `mod bax`. +mod bay { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait { + type Assoc: Bar; + } + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Bar {} + + impl MyTrait for Box<dyn ObjectTrait<Assoc = i32>> { + fn use_self(&self) -> &() { panic!() } + } + impl Bar for i32 {} + + fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32> + 'a>) -> &'a () { + val.use_self() //~ ERROR E0767 + } +} + +mod bax { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait { + type Assoc: Bar; + } + trait MyTrait<'a> { + fn use_self(&'a self) -> &'a () { panic!() } + } + trait Bar {} + + impl<'a> MyTrait<'a> for Box<dyn ObjectTrait<Assoc = i32> + 'a> { + fn use_self(&'a self) -> &'a () { panic!() } + } + impl Bar for i32 {} + + fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32> + 'a>) -> &'a () { + val.use_self() + } +} + +mod baw { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait { + type Assoc: Bar; + } + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Bar {} + + impl<'a> MyTrait for Box<dyn ObjectTrait<Assoc = Box<dyn Bar>>> { + fn use_self(&self) -> &() { panic!() } + } + + fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = Box<dyn Bar>>>) -> impl OtherTrait<'a> + 'a{ + val.use_self() //~ ERROR E0515 + } +} + +fn main() {} diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.stderr b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.stderr new file mode 100644 index 00000000000..2fab02fd1be --- /dev/null +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.stderr @@ -0,0 +1,57 @@ +error[E0597]: `val` does not live long enough + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:22:9 + | +LL | fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> { + | -- lifetime `'a` defined here ------------------- opaque type requires that `val` is borrowed for `'a` +LL | val.use_self() + | ^^^ borrowed value does not live long enough +LL | } + | - `val` dropped here while still borrowed + | +help: you can add a bound to the opaque type to make it last less than `'static` and match `'a` + | +LL | fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32>>) -> impl OtherTrait<'a> + 'a { + | ^^^^ + +error[E0515]: cannot return value referencing function parameter `val` + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:44:9 + | +LL | val.use_self() + | ---^^^^^^^^^^^ + | | + | returns a value referencing data owned by the current function + | `val` is borrowed here + +error[E0515]: cannot return value referencing function parameter `val` + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:110:9 + | +LL | val.use_self() + | ---^^^^^^^^^^^ + | | + | returns a value referencing data owned by the current function + | `val` is borrowed here + +error[E0767]: `val` has lifetime `'a` but calling `use_self` introduces an implicit `'static` lifetime requirement + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:67:13 + | +LL | fn use_it<'a>(val: Box<dyn ObjectTrait<Assoc = i32> + 'a>) -> &'a () { + | -------------------------------------- this data with lifetime `'a`... +LL | val.use_self() + | ^^^^^^^^ ...is captured and required to live as long as `'static` here + | +note: the used `impl` has a `'static` requirement + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound-needing-more-suggestions.rs:61:30 + | +LL | impl MyTrait for Box<dyn ObjectTrait<Assoc = i32>> { + | ^^^^^^^^^^^^^^^^^^^^^^^^ this has an implicit `'static` lifetime requirement +LL | fn use_self(&self) -> &() { panic!() } + | -------- calling this method introduces the `impl`'s 'static` requirement +help: consider relaxing the implicit `'static` requirement + | +LL | impl MyTrait for Box<dyn ObjectTrait<Assoc = i32> + '_> { + | ^^^^ + +error: aborting due to 4 previous errors + +Some errors have detailed explanations: E0515, E0597. +For more information about an error, try `rustc --explain E0515`. diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.fixed b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.fixed index 45e6cfdb821..c568738d94b 100644 --- a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.fixed +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.fixed @@ -78,14 +78,35 @@ mod ban { trait MyTrait { fn use_self(&self) -> &() { panic!() } } - trait Irrelevant {} + trait Irrelevant { + fn use_self(&self) -> &() { panic!() } + } impl MyTrait for dyn ObjectTrait + '_ {} - impl Irrelevant for dyn ObjectTrait {} fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { val.use_self() //~ ERROR E0759 } } +mod bal { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait {} + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Irrelevant { + fn use_self(&self) -> &() { panic!() } + } + + impl MyTrait for dyn ObjectTrait + '_ {} + impl Irrelevant for dyn ObjectTrait {} + + fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { + MyTrait::use_self(val) //~ ERROR E0759 + } +} + fn main() {} diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.nll.stderr b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.nll.stderr index fb6e62e76da..697467dc3a6 100644 --- a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.nll.stderr +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.nll.stderr @@ -19,7 +19,7 @@ LL | val.use_self() = help: consider replacing `'a` with `'static` error[E0521]: borrowed data escapes outside of function - --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:87:9 + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:88:9 | LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> { | --- `val` is a reference that is only valid in the function body @@ -28,5 +28,15 @@ LL | val.use_self() | = help: consider replacing `'a` with `'static` -error: aborting due to 3 previous errors +error[E0521]: borrowed data escapes outside of function + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:108:9 + | +LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { + | --- `val` is a reference that is only valid in the function body +LL | MyTrait::use_self(val) + | ^^^^^^^^^^^^^^^^^^^^^^ `val` escapes the function body here + | + = help: consider replacing `'a` with `'static` + +error: aborting due to 4 previous errors diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.rs b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.rs index 7de11f4f8fc..8dd1e5d78de 100644 --- a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.rs +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.rs @@ -78,14 +78,35 @@ mod ban { trait MyTrait { fn use_self(&self) -> &() { panic!() } } - trait Irrelevant {} + trait Irrelevant { + fn use_self(&self) -> &() { panic!() } + } impl MyTrait for dyn ObjectTrait {} - impl Irrelevant for dyn ObjectTrait {} fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> { val.use_self() //~ ERROR E0759 } } +mod bal { + trait OtherTrait<'a> {} + impl<'a> OtherTrait<'a> for &'a () {} + + trait ObjectTrait {} + trait MyTrait { + fn use_self(&self) -> &() { panic!() } + } + trait Irrelevant { + fn use_self(&self) -> &() { panic!() } + } + + impl MyTrait for dyn ObjectTrait {} + impl Irrelevant for dyn ObjectTrait {} + + fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { + MyTrait::use_self(val) //~ ERROR E0759 + } +} + fn main() {} diff --git a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.stderr b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.stderr index 1375ac8db8d..7e814fc6646 100644 --- a/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.stderr +++ b/src/test/ui/suggestions/impl-on-dyn-trait-with-implicit-static-bound.stderr @@ -6,7 +6,7 @@ LL | fn use_it<'a, T>(val: &'a dyn ObjectTrait<T>) -> impl OtherTrait<'a> + LL | val.use_self::<T>() | ^^^^^^^^ ...is captured and required to live as long as `'static` here | -note: `impl` of `foo::MyTrait` has a `'static` requirement +note: the used `impl` has a `'static` requirement --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:14:32 | LL | impl<T> MyTrait<T> for dyn ObjectTrait<T> { @@ -26,7 +26,7 @@ LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { LL | val.use_self() | ^^^^^^^^ ...is captured and required to live as long as `'static` here because of an implicit lifetime bound on the inherent `impl` | -note: inherent `impl` has a `'static` requirement +note: the used `impl` has a `'static` requirement --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:64:14 | LL | impl dyn ObjectTrait { @@ -39,15 +39,15 @@ LL | impl dyn ObjectTrait + '_ { | ^^^^ error[E0759]: `val` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement - --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:87:13 + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:88:13 | LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> { | ------------------- this data with lifetime `'a`... LL | val.use_self() | ^^^^^^^^ ...is captured and required to live as long as `'static` here | -note: `impl` of `ban::MyTrait` has a `'static` requirement - --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:83:26 +note: the used `impl` has a `'static` requirement + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:85:26 | LL | fn use_self(&self) -> &() { panic!() } | -------- calling this method introduces the `impl`'s 'static` requirement @@ -63,15 +63,41 @@ help: to declare that the `impl Trait` captures data from argument `val`, you ca LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { | ^^^^ +error[E0759]: `val` has lifetime `'a` but it needs to satisfy a `'static` lifetime requirement + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:108:27 + | +LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> impl OtherTrait<'a> + 'a { + | ------------------- this data with lifetime `'a`... +LL | MyTrait::use_self(val) + | ^^^ ...is captured here... + | +note: ...and is required to live as long as `'static` here + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:108:9 + | +LL | MyTrait::use_self(val) + | ^^^^^^^^^^^^^^^^^ +note: the used `impl` has a `'static` requirement + --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:104:26 + | +LL | fn use_self(&self) -> &() { panic!() } + | -------- calling this method introduces the `impl`'s 'static` requirement +... +LL | impl MyTrait for dyn ObjectTrait {} + | ^^^^^^^^^^^ this has an implicit `'static` lifetime requirement +help: consider relaxing the implicit `'static` requirement + | +LL | impl MyTrait for dyn ObjectTrait + '_ {} + | ^^^^ + error[E0767]: `val` has lifetime `'a` but calling `use_self` introduces an implicit `'static` lifetime requirement --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:37:13 | LL | fn use_it<'a>(val: &'a dyn ObjectTrait) -> &'a () { | ------------------- this data with lifetime `'a`... LL | val.use_self() - | ^^^^^^^^ ...is captured and required to live as long as `'static` here because of an implicit lifetime on the `impl` of `bar::MyTrait` + | ^^^^^^^^ ...is captured and required to live as long as `'static` here | -note: `impl` of `bar::MyTrait` has a `'static` requirement +note: the used `impl` has a `'static` requirement --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:31:26 | LL | impl MyTrait for dyn ObjectTrait { @@ -89,9 +115,9 @@ error[E0767]: `val` has lifetime `'a` but calling `use_self` introduces an impli LL | fn use_it<'a>(val: &'a Box<dyn ObjectTrait + 'a>) -> &'a () { | ----------------------------- this data with lifetime `'a`... LL | val.use_self() - | ^^^^^^^^ ...is captured and required to live as long as `'static` here because of an implicit lifetime on the `impl` of `baz::MyTrait` + | ^^^^^^^^ ...is captured and required to live as long as `'static` here | -note: `impl` of `baz::MyTrait` has a `'static` requirement +note: the used `impl` has a `'static` requirement --> $DIR/impl-on-dyn-trait-with-implicit-static-bound.rs:48:30 | LL | impl MyTrait for Box<dyn ObjectTrait> { @@ -103,6 +129,6 @@ help: consider relaxing the implicit `'static` requirement LL | impl MyTrait for Box<dyn ObjectTrait + '_> { | ^^^^ -error: aborting due to 5 previous errors +error: aborting due to 6 previous errors For more information about this error, try `rustc --explain E0759`. |
