@@ -16,7 +16,7 @@ use rustc_hir::def::Res;
16
16
use rustc_hir:: definitions:: DefPathData ;
17
17
use rustc_session:: errors:: report_lit_error;
18
18
use rustc_span:: source_map:: { respan, DesugaringKind , Span , Spanned } ;
19
- use rustc_span:: symbol:: { sym, Ident } ;
19
+ use rustc_span:: symbol:: { kw , sym, Ident } ;
20
20
use rustc_span:: DUMMY_SP ;
21
21
use thin_vec:: thin_vec;
22
22
@@ -592,14 +592,38 @@ impl<'hir> LoweringContext<'_, 'hir> {
592
592
) -> hir:: ExprKind < ' hir > {
593
593
let output = ret_ty. unwrap_or_else ( || hir:: FnRetTy :: DefaultReturn ( self . lower_span ( span) ) ) ;
594
594
595
- // Resume argument type: `ResumeTy`
596
- let unstable_span =
597
- self . mark_span_with_reason ( DesugaringKind :: Async , span, self . allow_gen_future . clone ( ) ) ;
598
- let resume_ty = hir:: QPath :: LangItem ( hir:: LangItem :: ResumeTy , unstable_span, None ) ;
595
+ // Resume argument type, which should be `&mut Context<'_>`.
596
+ // NOTE: Using the `'static` lifetime here is technically cheating.
597
+ // The `Future::poll` argument really is `&'a mut Context<'b>`, but we cannot
598
+ // express the fact that we are not storing it across yield-points yet,
599
+ // and we would thus run into lifetime errors.
600
+ // See <https://github.com/rust-lang/rust/issues/68923>.
601
+ // Our lowering makes sure we are not mis-using the `_task_context` input type
602
+ // in the sense that we are indeed not using it across yield points. We
603
+ // get a fresh `&mut Context` for each resume / call of `Future::poll`.
604
+ // This "cheating" was previously done with a `ResumeTy` that contained a raw
605
+ // pointer, and a `get_context` accessor that pulled the `Context` lifetimes
606
+ // out of thin air.
607
+ let context_lifetime_ident = Ident :: with_dummy_span ( kw:: StaticLifetime ) ;
608
+ let context_lifetime = self . arena . alloc ( hir:: Lifetime {
609
+ hir_id : self . next_id ( ) ,
610
+ ident : context_lifetime_ident,
611
+ res : hir:: LifetimeName :: Static ,
612
+ } ) ;
613
+ let context_path =
614
+ hir:: QPath :: LangItem ( hir:: LangItem :: Context , self . lower_span ( span) , None ) ;
615
+ let context_ty = hir:: MutTy {
616
+ ty : self . arena . alloc ( hir:: Ty {
617
+ hir_id : self . next_id ( ) ,
618
+ kind : hir:: TyKind :: Path ( context_path) ,
619
+ span : self . lower_span ( span) ,
620
+ } ) ,
621
+ mutbl : hir:: Mutability :: Mut ,
622
+ } ;
599
623
let input_ty = hir:: Ty {
600
624
hir_id : self . next_id ( ) ,
601
- kind : hir:: TyKind :: Path ( resume_ty ) ,
602
- span : unstable_span ,
625
+ kind : hir:: TyKind :: Rptr ( context_lifetime , context_ty ) ,
626
+ span : self . lower_span ( span ) ,
603
627
} ;
604
628
605
629
// The closure/generator `FnDecl` takes a single (resume) argument of type `input_ty`.
@@ -710,7 +734,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
710
734
/// mut __awaitee => loop {
711
735
/// match unsafe { ::std::future::Future::poll(
712
736
/// <::std::pin::Pin>::new_unchecked(&mut __awaitee),
713
- /// ::std::future::get_context( task_context) ,
737
+ /// task_context,
714
738
/// ) } {
715
739
/// ::std::task::Poll::Ready(result) => break result,
716
740
/// ::std::task::Poll::Pending => {}
@@ -751,7 +775,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
751
775
// unsafe {
752
776
// ::std::future::Future::poll(
753
777
// ::std::pin::Pin::new_unchecked(&mut __awaitee),
754
- // ::std::future::get_context( task_context) ,
778
+ // task_context,
755
779
// )
756
780
// }
757
781
let poll_expr = {
@@ -769,16 +793,10 @@ impl<'hir> LoweringContext<'_, 'hir> {
769
793
arena_vec ! [ self ; ref_mut_awaitee] ,
770
794
Some ( expr_hir_id) ,
771
795
) ;
772
- let get_context = self . expr_call_lang_item_fn_mut (
773
- gen_future_span,
774
- hir:: LangItem :: GetContext ,
775
- arena_vec ! [ self ; task_context] ,
776
- Some ( expr_hir_id) ,
777
- ) ;
778
796
let call = self . expr_call_lang_item_fn (
779
797
span,
780
798
hir:: LangItem :: FuturePoll ,
781
- arena_vec ! [ self ; new_unchecked, get_context ] ,
799
+ arena_vec ! [ self ; new_unchecked, task_context ] ,
782
800
Some ( expr_hir_id) ,
783
801
) ;
784
802
self . arena . alloc ( self . expr_unsafe ( call) )
0 commit comments