11use crate :: errors:: DumpVTableEntries ;
2+ use crate :: traits;
23use crate :: traits:: { impossible_predicates, is_vtable_safe_method} ;
34use rustc_hir:: def_id:: DefId ;
45use rustc_hir:: lang_items:: LangItem ;
@@ -13,6 +14,7 @@ use rustc_span::{sym, Span};
1314use smallvec:: SmallVec ;
1415
1516use std:: fmt:: Debug ;
17+ use std:: iter;
1618use std:: ops:: ControlFlow ;
1719
1820#[ derive( Clone , Debug ) ]
@@ -232,6 +234,32 @@ fn own_existential_vtable_entries_iter(
232234 own_entries
233235}
234236
237+ fn trait_object_ty < ' tcx > ( tcx : TyCtxt < ' tcx > , poly_trait_ref : ty:: PolyTraitRef < ' tcx > ) -> Ty < ' tcx > {
238+ let principal_pred = poly_trait_ref. map_bound ( |trait_ref| {
239+ ty:: ExistentialPredicate :: Trait ( ty:: ExistentialTraitRef :: erase_self_ty ( tcx, trait_ref) )
240+ } ) ;
241+ let assoc_preds = traits:: supertraits ( tcx, poly_trait_ref) . flat_map ( |super_poly_trait_ref| {
242+ tcx. associated_items ( super_poly_trait_ref. def_id ( ) )
243+ . in_definition_order ( )
244+ . filter ( |item| item. kind == ty:: AssocKind :: Type )
245+ . map ( move |assoc_ty| {
246+ super_poly_trait_ref. map_bound ( |super_trait_ref| {
247+ let alias_ty = ty:: AliasTy :: new ( tcx, assoc_ty. def_id , super_trait_ref. args ) ;
248+ let resolved = tcx
249+ . normalize_erasing_regions ( ty:: ParamEnv :: reveal_all ( ) , alias_ty. to_ty ( tcx) ) ;
250+ ty:: ExistentialPredicate :: Projection ( ty:: ExistentialProjection {
251+ def_id : assoc_ty. def_id ,
252+ args : ty:: ExistentialTraitRef :: erase_self_ty ( tcx, super_trait_ref) . args ,
253+ term : resolved. into ( ) ,
254+ } )
255+ } )
256+ } )
257+ } ) ;
258+ let preds =
259+ tcx. mk_poly_existential_predicates_from_iter ( iter:: once ( principal_pred) . chain ( assoc_preds) ) ;
260+ Ty :: new_dynamic ( tcx, preds, tcx. lifetimes . re_erased , ty:: Dyn )
261+ }
262+
235263/// Given a trait `trait_ref`, iterates the vtable entries
236264/// that come from `trait_ref`, including its supertraits.
237265fn vtable_entries < ' tcx > (
@@ -403,6 +431,7 @@ pub(super) fn provide(providers: &mut Providers) {
403431 own_existential_vtable_entries,
404432 vtable_entries,
405433 vtable_trait_upcasting_coercion_new_vptr_slot,
434+ trait_object_ty,
406435 ..* providers
407436 } ;
408437}
0 commit comments