@@ -18,7 +18,7 @@ use rustc_macros::{HashStable, TyDecodable, TyEncodable, TypeFoldable, extension
18
18
use rustc_span:: { DUMMY_SP , Span , Symbol , sym} ;
19
19
use rustc_type_ir:: TyKind :: * ;
20
20
use rustc_type_ir:: visit:: TypeVisitableExt ;
21
- use rustc_type_ir:: { self as ir, BoundVar , CollectAndApply , DynKind } ;
21
+ use rustc_type_ir:: { self as ir, BoundVar , CollectAndApply , DynKind , elaborate } ;
22
22
use tracing:: instrument;
23
23
use ty:: util:: { AsyncDropGlueMorphology , IntTypeExt } ;
24
24
@@ -720,6 +720,34 @@ impl<'tcx> Ty<'tcx> {
720
720
reg : ty:: Region < ' tcx > ,
721
721
repr : DynKind ,
722
722
) -> Ty < ' tcx > {
723
+ if cfg ! ( debug_assertions) {
724
+ let projection_count = obj. projection_bounds ( ) . count ( ) ;
725
+ let expected_count: usize = obj
726
+ . principal_def_id ( )
727
+ . into_iter ( )
728
+ . flat_map ( |principal_def_id| {
729
+ // NOTE: This should agree with `needed_associated_types` in
730
+ // dyn trait lowering, or else we'll have ICEs.
731
+ elaborate:: supertraits (
732
+ tcx,
733
+ ty:: Binder :: dummy ( ty:: TraitRef :: identity ( tcx, principal_def_id) ) ,
734
+ )
735
+ . map ( |principal| {
736
+ tcx. associated_items ( principal. def_id ( ) )
737
+ . in_definition_order ( )
738
+ . filter ( |item| item. kind == ty:: AssocKind :: Type )
739
+ . filter ( |item| !item. is_impl_trait_in_trait ( ) )
740
+ . filter ( |item| !tcx. generics_require_sized_self ( item. def_id ) )
741
+ . count ( )
742
+ } )
743
+ } )
744
+ . sum ( ) ;
745
+ assert_eq ! (
746
+ projection_count, expected_count,
747
+ "expected {obj:?} to have {expected_count} projections, \
748
+ but it has {projection_count}"
749
+ ) ;
750
+ }
723
751
Ty :: new ( tcx, Dynamic ( obj, reg, repr) )
724
752
}
725
753
0 commit comments