@@ -21,9 +21,8 @@ use rustc_const_eval::util;
2121use rustc_data_structures:: fx:: FxIndexSet ;
2222use rustc_data_structures:: steal:: Steal ;
2323use rustc_hir as hir;
24- use rustc_hir:: def:: DefKind ;
24+ use rustc_hir:: def:: { CtorKind , DefKind } ;
2525use rustc_hir:: def_id:: LocalDefId ;
26- use rustc_hir:: intravisit:: { self , Visitor } ;
2726use rustc_index:: IndexVec ;
2827use rustc_middle:: mir:: {
2928 AnalysisPhase , Body , CallSource , ClearCrossCrate , ConstOperand , ConstQualifs , LocalDecl ,
@@ -224,26 +223,31 @@ fn is_mir_available(tcx: TyCtxt<'_>, def_id: LocalDefId) -> bool {
224223/// MIR associated with them.
225224fn mir_keys ( tcx : TyCtxt < ' _ > , ( ) : ( ) ) -> FxIndexSet < LocalDefId > {
226225 // All body-owners have MIR associated with them.
227- let set: FxIndexSet < _ > = tcx. hir ( ) . body_owners ( ) . collect ( ) ;
226+ let mut set: FxIndexSet < _ > = tcx. hir ( ) . body_owners ( ) . collect ( ) ;
228227
229- // Additionally, tuple struct/variant constructors have MIR, but
230- // they don't have a BodyId, so we need to build them separately.
231- struct GatherCtors {
232- set : FxIndexSet < LocalDefId > ,
228+ // Coroutine-closures (e.g. async closures) have an additional by-move MIR
229+ // body that isn't in the HIR.
230+ for body_owner in tcx. hir ( ) . body_owners ( ) {
231+ if let DefKind :: Closure = tcx. def_kind ( body_owner)
232+ && tcx. needs_coroutine_by_move_body_def_id ( body_owner. to_def_id ( ) )
233+ {
234+ set. insert ( tcx. coroutine_by_move_body_def_id ( body_owner) . expect_local ( ) ) ;
235+ }
233236 }
234- impl < ' tcx > Visitor < ' tcx > for GatherCtors {
235- fn visit_variant_data ( & mut self , v : & ' tcx hir:: VariantData < ' tcx > ) {
236- if let hir:: VariantData :: Tuple ( _, _, def_id) = * v {
237- self . set . insert ( def_id) ;
237+
238+ // tuple struct/variant constructors have MIR, but they don't have a BodyId,
239+ // so we need to build them separately.
240+ for item in tcx. hir_crate_items ( ( ) ) . free_items ( ) {
241+ if let DefKind :: Struct | DefKind :: Enum = tcx. def_kind ( item. owner_id ) {
242+ for variant in tcx. adt_def ( item. owner_id ) . variants ( ) {
243+ if let Some ( ( CtorKind :: Fn , ctor_def_id) ) = variant. ctor {
244+ set. insert ( ctor_def_id. expect_local ( ) ) ;
245+ }
238246 }
239- intravisit:: walk_struct_def ( self , v)
240247 }
241248 }
242249
243- let mut gather_ctors = GatherCtors { set } ;
244- tcx. hir ( ) . visit_all_item_likes_in_crate ( & mut gather_ctors) ;
245-
246- gather_ctors. set
250+ set
247251}
248252
249253fn mir_const_qualif ( tcx : TyCtxt < ' _ > , def : LocalDefId ) -> ConstQualifs {
0 commit comments