@@ -11,7 +11,10 @@ use std::iter;
1111pub fn provide ( providers : & mut Providers ) {
1212 * providers = Providers {
1313 assumed_wf_types,
14- assumed_wf_types_for_rpitit : |tcx, def_id| tcx. assumed_wf_types ( def_id) ,
14+ assumed_wf_types_for_rpitit : |tcx, def_id| {
15+ assert ! ( tcx. is_impl_trait_in_trait( def_id. to_def_id( ) ) ) ;
16+ tcx. assumed_wf_types ( def_id)
17+ } ,
1518 ..* providers
1619 } ;
1720}
@@ -52,6 +55,15 @@ fn assumed_wf_types<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> &'tcx [(Ty<'
5255 ty:: ImplTraitInTraitData :: Trait { fn_def_id, opaque_def_id } => {
5356 let hir:: OpaqueTy { lifetime_mapping, .. } =
5457 * tcx. hir ( ) . expect_item ( opaque_def_id. expect_local ( ) ) . expect_opaque_ty ( ) ;
58+ // We need to remap all of the late-bound lifetimes in theassumed wf types
59+ // of the fn (which are represented as ReFree) to the early-bound lifetimes
60+ // of the RPITIT (which are represented by ReEarlyBound owned by the opaque).
61+ // Luckily, this is very easy to do because we already have that mapping
62+ // stored in the HIR of this RPITIT.
63+ //
64+ // Side-note: We don't really need to do this remapping for early-bound
65+ // lifetimes because they're already "linked" by the bidirectional outlives
66+ // predicates we insert in the `explicit_predicates_of` query for RPITITs.
5567 let mut mapping = FxHashMap :: default ( ) ;
5668 let generics = tcx. generics_of ( def_id) ;
5769 for & ( lifetime, new_early_bound_def_id) in
@@ -81,14 +93,24 @@ fn assumed_wf_types<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> &'tcx [(Ty<'
8193 ) ;
8294 }
8395 }
84- let a = tcx. fold_regions (
96+ // FIXME: This could use a real folder, I guess.
97+ let remapped_wf_tys = tcx. fold_regions (
8598 tcx. assumed_wf_types ( fn_def_id. expect_local ( ) ) . to_vec ( ) ,
86- |re, _| {
87- if let Some ( re) = mapping. get ( & re) { * re } else { re }
99+ |region, _| {
100+ // If `region` is a `ReFree` that is captured by the
101+ // opaque, remap it to its corresponding the early-
102+ // bound region.
103+ if let Some ( remapped_region) = mapping. get ( & region) {
104+ * remapped_region
105+ } else {
106+ region
107+ }
88108 } ,
89109 ) ;
90- tcx. arena . alloc_from_iter ( a )
110+ tcx. arena . alloc_from_iter ( remapped_wf_tys )
91111 }
112+ // Assumed wf types for RPITITs in an impl just inherit (and instantiate)
113+ // the assumed wf types of the trait's RPITIT GAT.
92114 ty:: ImplTraitInTraitData :: Impl { .. } => {
93115 let impl_def_id = tcx. local_parent ( def_id) ;
94116 let rpitit_def_id = tcx. associated_item ( def_id) . trait_item_def_id . unwrap ( ) ;
0 commit comments