@@ -145,8 +145,6 @@ fn fn_sig_for_fn_abi<'tcx>(
145145 )
146146 }
147147 ty:: Coroutine ( did, args) => {
148- // FIXME(async_closures): This isn't right for `CoroutineKindShim`.
149-
150148 let coroutine_kind = tcx. coroutine_kind ( did) . unwrap ( ) ;
151149 let sig = args. as_coroutine ( ) . sig ( ) ;
152150
@@ -157,6 +155,40 @@ fn fn_sig_for_fn_abi<'tcx>(
157155 var : ty:: BoundVar :: from_usize ( bound_vars. len ( ) - 1 ) ,
158156 kind : ty:: BoundRegionKind :: BrEnv ,
159157 } ;
158+
159+ let mut ty = ty;
160+ // When this `Closure` comes from a `CoroutineKindShim`,
161+ // make sure we respect the `target_kind` in that shim.
162+ // FIXME(async_closures): This shouldn't be needed, and we should be populating
163+ // a separate def-id for these bodies.
164+ if let InstanceDef :: CoroutineKindShim { target_kind, .. } = instance. def {
165+ // Grab the parent coroutine-closure. It has the same args for the purposes
166+ // of substitution, so this will be okay to do.
167+ let ty:: CoroutineClosure ( _, coroutine_closure_args) = * tcx
168+ . instantiate_and_normalize_erasing_regions (
169+ args,
170+ param_env,
171+ tcx. type_of ( tcx. parent ( did) ) ,
172+ )
173+ . kind ( )
174+ else {
175+ bug ! ( "CoroutineKindShim comes from calling a coroutine-closure" ) ;
176+ } ;
177+ let coroutine_closure_args = coroutine_closure_args. as_coroutine_closure ( ) ;
178+ ty = tcx. instantiate_bound_regions_with_erased (
179+ coroutine_closure_args. coroutine_closure_sig ( ) . map_bound ( |sig| {
180+ sig. to_coroutine_given_kind_and_upvars (
181+ tcx,
182+ coroutine_closure_args. parent_args ( ) ,
183+ did,
184+ target_kind,
185+ tcx. lifetimes . re_erased ,
186+ coroutine_closure_args. tupled_upvars_ty ( ) ,
187+ coroutine_closure_args. coroutine_captures_by_ref_ty ( ) ,
188+ )
189+ } ) ,
190+ ) ;
191+ }
160192 let env_ty = Ty :: new_mut_ref ( tcx, ty:: Region :: new_bound ( tcx, ty:: INNERMOST , br) , ty) ;
161193
162194 let pin_did = tcx. require_lang_item ( LangItem :: Pin , None ) ;
0 commit comments