mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-01 06:51:58 +00:00
Revert "Replace usage of ResumeTy
in async lowering with Context
"
This commit is contained in:
parent
7ab803891d
commit
8441ca5d81
@ -16,7 +16,7 @@ use rustc_hir::def::Res;
|
|||||||
use rustc_hir::definitions::DefPathData;
|
use rustc_hir::definitions::DefPathData;
|
||||||
use rustc_session::errors::report_lit_error;
|
use rustc_session::errors::report_lit_error;
|
||||||
use rustc_span::source_map::{respan, DesugaringKind, Span, Spanned};
|
use rustc_span::source_map::{respan, DesugaringKind, Span, Spanned};
|
||||||
use rustc_span::symbol::{kw, sym, Ident};
|
use rustc_span::symbol::{sym, Ident};
|
||||||
use rustc_span::DUMMY_SP;
|
use rustc_span::DUMMY_SP;
|
||||||
use thin_vec::thin_vec;
|
use thin_vec::thin_vec;
|
||||||
|
|
||||||
@ -596,38 +596,14 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
) -> hir::ExprKind<'hir> {
|
) -> hir::ExprKind<'hir> {
|
||||||
let output = ret_ty.unwrap_or_else(|| hir::FnRetTy::DefaultReturn(self.lower_span(span)));
|
let output = ret_ty.unwrap_or_else(|| hir::FnRetTy::DefaultReturn(self.lower_span(span)));
|
||||||
|
|
||||||
// Resume argument type, which should be `&mut Context<'_>`.
|
// Resume argument type: `ResumeTy`
|
||||||
// NOTE: Using the `'static` lifetime here is technically cheating.
|
let unstable_span =
|
||||||
// The `Future::poll` argument really is `&'a mut Context<'b>`, but we cannot
|
self.mark_span_with_reason(DesugaringKind::Async, span, self.allow_gen_future.clone());
|
||||||
// express the fact that we are not storing it across yield-points yet,
|
let resume_ty = hir::QPath::LangItem(hir::LangItem::ResumeTy, unstable_span, None);
|
||||||
// and we would thus run into lifetime errors.
|
|
||||||
// See <https://github.com/rust-lang/rust/issues/68923>.
|
|
||||||
// Our lowering makes sure we are not mis-using the `_task_context` input type
|
|
||||||
// in the sense that we are indeed not using it across yield points. We
|
|
||||||
// get a fresh `&mut Context` for each resume / call of `Future::poll`.
|
|
||||||
// This "cheating" was previously done with a `ResumeTy` that contained a raw
|
|
||||||
// pointer, and a `get_context` accessor that pulled the `Context` lifetimes
|
|
||||||
// out of thin air.
|
|
||||||
let context_lifetime_ident = Ident::with_dummy_span(kw::StaticLifetime);
|
|
||||||
let context_lifetime = self.arena.alloc(hir::Lifetime {
|
|
||||||
hir_id: self.next_id(),
|
|
||||||
ident: context_lifetime_ident,
|
|
||||||
res: hir::LifetimeName::Static,
|
|
||||||
});
|
|
||||||
let context_path =
|
|
||||||
hir::QPath::LangItem(hir::LangItem::Context, self.lower_span(span), None);
|
|
||||||
let context_ty = hir::MutTy {
|
|
||||||
ty: self.arena.alloc(hir::Ty {
|
|
||||||
hir_id: self.next_id(),
|
|
||||||
kind: hir::TyKind::Path(context_path),
|
|
||||||
span: self.lower_span(span),
|
|
||||||
}),
|
|
||||||
mutbl: hir::Mutability::Mut,
|
|
||||||
};
|
|
||||||
let input_ty = hir::Ty {
|
let input_ty = hir::Ty {
|
||||||
hir_id: self.next_id(),
|
hir_id: self.next_id(),
|
||||||
kind: hir::TyKind::Rptr(context_lifetime, context_ty),
|
kind: hir::TyKind::Path(resume_ty),
|
||||||
span: self.lower_span(span),
|
span: unstable_span,
|
||||||
};
|
};
|
||||||
|
|
||||||
// The closure/generator `FnDecl` takes a single (resume) argument of type `input_ty`.
|
// The closure/generator `FnDecl` takes a single (resume) argument of type `input_ty`.
|
||||||
@ -686,9 +662,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
.map_or(false, |attrs| attrs.into_iter().any(|attr| attr.has_name(sym::track_caller)));
|
.map_or(false, |attrs| attrs.into_iter().any(|attr| attr.has_name(sym::track_caller)));
|
||||||
|
|
||||||
let hir_id = self.lower_node_id(closure_node_id);
|
let hir_id = self.lower_node_id(closure_node_id);
|
||||||
let unstable_span =
|
|
||||||
self.mark_span_with_reason(DesugaringKind::Async, span, self.allow_gen_future.clone());
|
|
||||||
if track_caller {
|
if track_caller {
|
||||||
|
let unstable_span = self.mark_span_with_reason(
|
||||||
|
DesugaringKind::Async,
|
||||||
|
span,
|
||||||
|
self.allow_gen_future.clone(),
|
||||||
|
);
|
||||||
self.lower_attrs(
|
self.lower_attrs(
|
||||||
hir_id,
|
hir_id,
|
||||||
&[Attribute {
|
&[Attribute {
|
||||||
@ -731,7 +710,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
/// mut __awaitee => loop {
|
/// mut __awaitee => loop {
|
||||||
/// match unsafe { ::std::future::Future::poll(
|
/// match unsafe { ::std::future::Future::poll(
|
||||||
/// <::std::pin::Pin>::new_unchecked(&mut __awaitee),
|
/// <::std::pin::Pin>::new_unchecked(&mut __awaitee),
|
||||||
/// task_context,
|
/// ::std::future::get_context(task_context),
|
||||||
/// ) } {
|
/// ) } {
|
||||||
/// ::std::task::Poll::Ready(result) => break result,
|
/// ::std::task::Poll::Ready(result) => break result,
|
||||||
/// ::std::task::Poll::Pending => {}
|
/// ::std::task::Poll::Pending => {}
|
||||||
@ -772,7 +751,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
// unsafe {
|
// unsafe {
|
||||||
// ::std::future::Future::poll(
|
// ::std::future::Future::poll(
|
||||||
// ::std::pin::Pin::new_unchecked(&mut __awaitee),
|
// ::std::pin::Pin::new_unchecked(&mut __awaitee),
|
||||||
// task_context,
|
// ::std::future::get_context(task_context),
|
||||||
// )
|
// )
|
||||||
// }
|
// }
|
||||||
let poll_expr = {
|
let poll_expr = {
|
||||||
@ -790,10 +769,16 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
arena_vec![self; ref_mut_awaitee],
|
arena_vec![self; ref_mut_awaitee],
|
||||||
Some(expr_hir_id),
|
Some(expr_hir_id),
|
||||||
);
|
);
|
||||||
|
let get_context = self.expr_call_lang_item_fn_mut(
|
||||||
|
gen_future_span,
|
||||||
|
hir::LangItem::GetContext,
|
||||||
|
arena_vec![self; task_context],
|
||||||
|
Some(expr_hir_id),
|
||||||
|
);
|
||||||
let call = self.expr_call_lang_item_fn(
|
let call = self.expr_call_lang_item_fn(
|
||||||
span,
|
span,
|
||||||
hir::LangItem::FuturePoll,
|
hir::LangItem::FuturePoll,
|
||||||
arena_vec![self; new_unchecked, task_context],
|
arena_vec![self; new_unchecked, get_context],
|
||||||
Some(expr_hir_id),
|
Some(expr_hir_id),
|
||||||
);
|
);
|
||||||
self.arena.alloc(self.expr_unsafe(call))
|
self.arena.alloc(self.expr_unsafe(call))
|
||||||
|
@ -286,9 +286,10 @@ language_item_table! {
|
|||||||
|
|
||||||
// FIXME(swatinem): the following lang items are used for async lowering and
|
// FIXME(swatinem): the following lang items are used for async lowering and
|
||||||
// should become obsolete eventually.
|
// should become obsolete eventually.
|
||||||
|
ResumeTy, sym::ResumeTy, resume_ty, Target::Struct, GenericRequirement::None;
|
||||||
IdentityFuture, sym::identity_future, identity_future_fn, Target::Fn, GenericRequirement::None;
|
IdentityFuture, sym::identity_future, identity_future_fn, Target::Fn, GenericRequirement::None;
|
||||||
|
GetContext, sym::get_context, get_context_fn, Target::Fn, GenericRequirement::None;
|
||||||
|
|
||||||
Context, sym::Context, context, Target::Struct, GenericRequirement::None;
|
|
||||||
FuturePoll, sym::poll, future_poll_fn, Target::Method(MethodKind::Trait { body: false }), GenericRequirement::None;
|
FuturePoll, sym::poll, future_poll_fn, Target::Method(MethodKind::Trait { body: false }), GenericRequirement::None;
|
||||||
|
|
||||||
FromFrom, sym::from, from_fn, Target::Method(MethodKind::Trait { body: false }), GenericRequirement::None;
|
FromFrom, sym::from, from_fn, Target::Method(MethodKind::Trait { body: false }), GenericRequirement::None;
|
||||||
|
@ -164,7 +164,6 @@ symbols! {
|
|||||||
Capture,
|
Capture,
|
||||||
Center,
|
Center,
|
||||||
Clone,
|
Clone,
|
||||||
Context,
|
|
||||||
Continue,
|
Continue,
|
||||||
Copy,
|
Copy,
|
||||||
Count,
|
Count,
|
||||||
@ -264,6 +263,7 @@ symbols! {
|
|||||||
Relaxed,
|
Relaxed,
|
||||||
Release,
|
Release,
|
||||||
Result,
|
Result,
|
||||||
|
ResumeTy,
|
||||||
Return,
|
Return,
|
||||||
Right,
|
Right,
|
||||||
Rust,
|
Rust,
|
||||||
@ -753,6 +753,7 @@ symbols! {
|
|||||||
generic_associated_types_extended,
|
generic_associated_types_extended,
|
||||||
generic_const_exprs,
|
generic_const_exprs,
|
||||||
generic_param_attrs,
|
generic_param_attrs,
|
||||||
|
get_context,
|
||||||
global_allocator,
|
global_allocator,
|
||||||
global_asm,
|
global_asm,
|
||||||
globs,
|
globs,
|
||||||
|
@ -44,7 +44,7 @@ pub use poll_fn::{poll_fn, PollFn};
|
|||||||
/// non-Send/Sync as well, and we don't want that.
|
/// non-Send/Sync as well, and we don't want that.
|
||||||
///
|
///
|
||||||
/// It also simplifies the HIR lowering of `.await`.
|
/// It also simplifies the HIR lowering of `.await`.
|
||||||
// FIXME(swatinem): This type can be removed when bumping the bootstrap compiler
|
#[cfg_attr(not(bootstrap), lang = "ResumeTy")]
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
#[unstable(feature = "gen_future", issue = "50547")]
|
#[unstable(feature = "gen_future", issue = "50547")]
|
||||||
#[derive(Debug, Copy, Clone)]
|
#[derive(Debug, Copy, Clone)]
|
||||||
@ -61,7 +61,6 @@ unsafe impl Sync for ResumeTy {}
|
|||||||
/// This function returns a `GenFuture` underneath, but hides it in `impl Trait` to give
|
/// This function returns a `GenFuture` underneath, but hides it in `impl Trait` to give
|
||||||
/// better error messages (`impl Future` rather than `GenFuture<[closure.....]>`).
|
/// better error messages (`impl Future` rather than `GenFuture<[closure.....]>`).
|
||||||
// This is `const` to avoid extra errors after we recover from `const async fn`
|
// This is `const` to avoid extra errors after we recover from `const async fn`
|
||||||
// FIXME(swatinem): This fn can be removed when bumping the bootstrap compiler
|
|
||||||
#[cfg_attr(bootstrap, lang = "from_generator")]
|
#[cfg_attr(bootstrap, lang = "from_generator")]
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
#[unstable(feature = "gen_future", issue = "50547")]
|
#[unstable(feature = "gen_future", issue = "50547")]
|
||||||
@ -103,8 +102,7 @@ where
|
|||||||
GenFuture(gen)
|
GenFuture(gen)
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME(swatinem): This fn can be removed when bumping the bootstrap compiler
|
#[lang = "get_context"]
|
||||||
#[cfg_attr(bootstrap, lang = "get_context")]
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
#[unstable(feature = "gen_future", issue = "50547")]
|
#[unstable(feature = "gen_future", issue = "50547")]
|
||||||
#[must_use]
|
#[must_use]
|
||||||
@ -115,10 +113,6 @@ pub unsafe fn get_context<'a, 'b>(cx: ResumeTy) -> &'a mut Context<'b> {
|
|||||||
unsafe { &mut *cx.0.as_ptr().cast() }
|
unsafe { &mut *cx.0.as_ptr().cast() }
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME(swatinem): This fn is currently needed to work around shortcomings
|
|
||||||
// in type and lifetime inference.
|
|
||||||
// See the comment at the bottom of `LoweringContext::make_async_expr` and
|
|
||||||
// <https://github.com/rust-lang/rust/issues/104826>.
|
|
||||||
#[cfg_attr(not(bootstrap), lang = "identity_future")]
|
#[cfg_attr(not(bootstrap), lang = "identity_future")]
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
#[unstable(feature = "gen_future", issue = "50547")]
|
#[unstable(feature = "gen_future", issue = "50547")]
|
||||||
|
@ -174,7 +174,6 @@ impl RawWakerVTable {
|
|||||||
/// Currently, `Context` only serves to provide access to a [`&Waker`](Waker)
|
/// Currently, `Context` only serves to provide access to a [`&Waker`](Waker)
|
||||||
/// which can be used to wake the current task.
|
/// which can be used to wake the current task.
|
||||||
#[stable(feature = "futures_api", since = "1.36.0")]
|
#[stable(feature = "futures_api", since = "1.36.0")]
|
||||||
#[cfg_attr(not(bootstrap), lang = "Context")]
|
|
||||||
pub struct Context<'a> {
|
pub struct Context<'a> {
|
||||||
waker: &'a Waker,
|
waker: &'a Waker,
|
||||||
// Ensure we future-proof against variance changes by forcing
|
// Ensure we future-proof against variance changes by forcing
|
||||||
|
@ -40,7 +40,7 @@ LL | async fn bar2<T>(_: T) -> ! {
|
|||||||
LL | | panic!()
|
LL | | panic!()
|
||||||
LL | | }
|
LL | | }
|
||||||
| |_^
|
| |_^
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `Option<bool>`, `impl Future<Output = !>`, `()`
|
= note: required because it captures the following types: `ResumeTy`, `Option<bool>`, `impl Future<Output = !>`, `()`
|
||||||
note: required because it's used within this `async fn` body
|
note: required because it's used within this `async fn` body
|
||||||
--> $DIR/async-await-let-else.rs:21:32
|
--> $DIR/async-await-let-else.rs:21:32
|
||||||
|
|
|
|
||||||
|
@ -57,7 +57,7 @@ note: required because it appears within the type `impl Future<Output = Arc<RefC
|
|||||||
|
|
|
|
||||||
LL | fn make_non_send_future2() -> impl Future<Output = Arc<RefCell<i32>>> {
|
LL | fn make_non_send_future2() -> impl Future<Output = Arc<RefCell<i32>>> {
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `impl Future<Output = Arc<RefCell<i32>>>`, `()`, `Ready<i32>`
|
= note: required because it captures the following types: `ResumeTy`, `impl Future<Output = Arc<RefCell<i32>>>`, `()`, `Ready<i32>`
|
||||||
note: required because it's used within this `async` block
|
note: required because it's used within this `async` block
|
||||||
--> $DIR/issue-68112.rs:60:20
|
--> $DIR/issue-68112.rs:60:20
|
||||||
|
|
|
|
||||||
|
@ -57,7 +57,7 @@ note: required because it appears within the type `impl Future<Output = Arc<RefC
|
|||||||
|
|
|
|
||||||
LL | fn make_non_send_future2() -> impl Future<Output = Arc<RefCell<i32>>> {
|
LL | fn make_non_send_future2() -> impl Future<Output = Arc<RefCell<i32>>> {
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `impl Future<Output = Arc<RefCell<i32>>>`, `()`, `i32`, `Ready<i32>`
|
= note: required because it captures the following types: `ResumeTy`, `impl Future<Output = Arc<RefCell<i32>>>`, `()`, `i32`, `Ready<i32>`
|
||||||
note: required because it's used within this `async` block
|
note: required because it's used within this `async` block
|
||||||
--> $DIR/issue-68112.rs:60:20
|
--> $DIR/issue-68112.rs:60:20
|
||||||
|
|
|
|
||||||
|
@ -14,9 +14,6 @@ LL | | });
|
|||||||
|
|
|
|
||||||
= note: `FnMut` closures only have access to their captured variables while they are executing...
|
= note: `FnMut` closures only have access to their captured variables while they are executing...
|
||||||
= note: ...therefore, they cannot allow references to captured variables to escape
|
= note: ...therefore, they cannot allow references to captured variables to escape
|
||||||
= note: requirement occurs because of a mutable reference to `Context<'_>`
|
|
||||||
= note: mutable references are invariant over their type parameter
|
|
||||||
= help: see <https://doc.rust-lang.org/nomicon/subtyping.html> for more information about variance
|
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@ LL | async fn baz<T>(_c: impl FnMut() -> T) where T: Future<Output=()> {
|
|||||||
| ___________________________________________________________________^
|
| ___________________________________________________________________^
|
||||||
LL | | }
|
LL | | }
|
||||||
| |_^
|
| |_^
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `impl Future<Output = ()>`, `()`
|
= note: required because it captures the following types: `ResumeTy`, `impl Future<Output = ()>`, `()`
|
||||||
note: required because it's used within this `async` block
|
note: required because it's used within this `async` block
|
||||||
--> $DIR/issue-70935-complex-spans.rs:16:5
|
--> $DIR/issue-70935-complex-spans.rs:16:5
|
||||||
|
|
|
|
||||||
|
@ -11,7 +11,7 @@ LL | async fn foo() {
|
|||||||
|
|
|
|
||||||
= help: within `impl Future<Output = ()>`, the trait `Send` is not implemented for `NotSend`
|
= help: within `impl Future<Output = ()>`, the trait `Send` is not implemented for `NotSend`
|
||||||
= note: required because it appears within the type `(NotSend,)`
|
= note: required because it appears within the type `(NotSend,)`
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `(NotSend,)`, `()`, `impl Future<Output = ()>`
|
= note: required because it captures the following types: `ResumeTy`, `(NotSend,)`, `()`, `impl Future<Output = ()>`
|
||||||
note: required because it's used within this `async fn` body
|
note: required because it's used within this `async fn` body
|
||||||
--> $DIR/partial-drop-partial-reinit.rs:31:16
|
--> $DIR/partial-drop-partial-reinit.rs:31:16
|
||||||
|
|
|
|
||||||
|
@ -11,7 +11,7 @@ LL | async fn foo() {
|
|||||||
|
|
|
|
||||||
= help: within `impl Future<Output = ()>`, the trait `Send` is not implemented for `NotSend`
|
= help: within `impl Future<Output = ()>`, the trait `Send` is not implemented for `NotSend`
|
||||||
= note: required because it appears within the type `(NotSend,)`
|
= note: required because it appears within the type `(NotSend,)`
|
||||||
= note: required because it captures the following types: `&mut Context<'_>`, `(NotSend,)`, `impl Future<Output = ()>`, `()`
|
= note: required because it captures the following types: `ResumeTy`, `(NotSend,)`, `impl Future<Output = ()>`, `()`
|
||||||
note: required because it's used within this `async fn` body
|
note: required because it's used within this `async fn` body
|
||||||
--> $DIR/partial-drop-partial-reinit.rs:31:16
|
--> $DIR/partial-drop-partial-reinit.rs:31:16
|
||||||
|
|
|
|
||||||
|
@ -22,11 +22,11 @@ fn good_generic_fn<T>() {
|
|||||||
// This should fail because `T` ends up in the upvars of the closure.
|
// This should fail because `T` ends up in the upvars of the closure.
|
||||||
fn bad_generic_fn<T: Copy>(t: T) {
|
fn bad_generic_fn<T: Copy>(t: T) {
|
||||||
assert_static(opaque(async move { t; }).next());
|
assert_static(opaque(async move { t; }).next());
|
||||||
//~^ ERROR the parameter type `T` may not live long enough
|
//~^ ERROR the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
assert_static(opaque(move || { t; }).next());
|
assert_static(opaque(move || { t; }).next());
|
||||||
//~^ ERROR the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
//~^ ERROR the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
assert_static(opaque(opaque(async move { t; }).next()).next());
|
assert_static(opaque(opaque(async move { t; }).next()).next());
|
||||||
//~^ ERROR the parameter type `T` may not live long enough
|
//~^ ERROR the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -1,13 +1,11 @@
|
|||||||
error[E0310]: the parameter type `T` may not live long enough
|
error[E0310]: the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
--> $DIR/closure-in-projection-issue-97405.rs:24:5
|
--> $DIR/closure-in-projection-issue-97405.rs:24:5
|
||||||
|
|
|
|
||||||
LL | assert_static(opaque(async move { t; }).next());
|
LL | assert_static(opaque(async move { t; }).next());
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ...so that the type `T` will meet its required lifetime bounds
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
|
||||||
help: consider adding an explicit lifetime bound...
|
= help: consider adding an explicit lifetime bound `<impl Iterator as Iterator>::Item: 'static`...
|
||||||
|
|
= note: ...so that the type `<impl Iterator as Iterator>::Item` will meet its required lifetime bounds
|
||||||
LL | fn bad_generic_fn<T: Copy + 'static>(t: T) {
|
|
||||||
| +++++++++
|
|
||||||
|
|
||||||
error[E0310]: the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
error[E0310]: the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
--> $DIR/closure-in-projection-issue-97405.rs:26:5
|
--> $DIR/closure-in-projection-issue-97405.rs:26:5
|
||||||
@ -18,16 +16,14 @@ LL | assert_static(opaque(move || { t; }).next());
|
|||||||
= help: consider adding an explicit lifetime bound `<impl Iterator as Iterator>::Item: 'static`...
|
= help: consider adding an explicit lifetime bound `<impl Iterator as Iterator>::Item: 'static`...
|
||||||
= note: ...so that the type `<impl Iterator as Iterator>::Item` will meet its required lifetime bounds
|
= note: ...so that the type `<impl Iterator as Iterator>::Item` will meet its required lifetime bounds
|
||||||
|
|
||||||
error[E0310]: the parameter type `T` may not live long enough
|
error[E0310]: the associated type `<impl Iterator as Iterator>::Item` may not live long enough
|
||||||
--> $DIR/closure-in-projection-issue-97405.rs:28:5
|
--> $DIR/closure-in-projection-issue-97405.rs:28:5
|
||||||
|
|
|
|
||||||
LL | assert_static(opaque(opaque(async move { t; }).next()).next());
|
LL | assert_static(opaque(opaque(async move { t; }).next()).next());
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ...so that the type `T` will meet its required lifetime bounds
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
|
||||||
help: consider adding an explicit lifetime bound...
|
= help: consider adding an explicit lifetime bound `<impl Iterator as Iterator>::Item: 'static`...
|
||||||
|
|
= note: ...so that the type `<impl Iterator as Iterator>::Item` will meet its required lifetime bounds
|
||||||
LL | fn bad_generic_fn<T: Copy + 'static>(t: T) {
|
|
||||||
| +++++++++
|
|
||||||
|
|
||||||
error: aborting due to 3 previous errors
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user