@@ -375,58 +375,56 @@ impl<'a, 'gcx> CheckTypeWellFormedVisitor<'a, 'gcx> {
375
375
use ty:: subst:: Subst ;
376
376
use rustc:: ty:: TypeFoldable ;
377
377
378
+ let mut predicates = fcx. tcx . predicates_of ( def_id) ;
379
+ let mut substituted_predicates = Vec :: new ( ) ;
380
+
378
381
let generics = self . tcx . generics_of ( def_id) ;
379
382
let defaulted_params = generics. types . iter ( )
380
383
. filter ( |def| def. has_default &&
381
384
def. index >= generics. parent_count ( ) as u32 ) ;
382
- // Defaults must be well-formed.
383
- for d in defaulted_params. map ( |p| p. def_id ) {
385
+ for param_def in defaulted_params {
386
+ // Defaults must be well-formed.
387
+ let d = param_def. def_id ;
384
388
fcx. register_wf_obligation ( fcx. tcx . type_of ( d) , fcx. tcx . def_span ( d) , self . code . clone ( ) ) ;
385
- }
386
- // Check that each default fulfills the bounds on it's parameter.
387
- // We go over each predicate and duplicate it, substituting defaults in the self type.
388
- let mut predicates = fcx. tcx . predicates_of ( def_id) ;
389
- let mut default_predicates = Vec :: new ( ) ;
390
- // In `trait Trait : Super` predicates as `Self: Trait` and `Self: Super` are a problem.
391
- // Therefore we skip such predicates. This means we check less than we could.
392
- for pred in predicates. predicates . iter ( ) . filter ( |p| !( is_trait && p. has_self_ty ( ) ) ) {
393
- let mut skip = false ;
394
- let mut no_default = true ;
395
- let substs = ty:: subst:: Substs :: for_item ( fcx. tcx , def_id, |def, _| {
396
- // All regions are identity.
397
- fcx. tcx . mk_region ( ty:: ReEarlyBound ( def. to_early_bound_region_data ( ) ) )
398
- } , |def, _| {
399
- // No default or generic comes from parent, identity substitution.
400
- if !def. has_default || ( def. index as usize ) < generics. parent_count ( ) {
401
- fcx. tcx . mk_param_from_def ( def)
402
- } else {
403
- no_default = false ;
404
- // Has a default, use it in the substitution.
405
- let default_ty = fcx. tcx . type_of ( def. def_id ) ;
406
-
407
- match default_ty. sty {
408
- // Skip `Self: Sized` when `Self` is the default. Needed in traits.
409
- ty:: TyParam ( ref p) if is_trait && p. is_self ( ) => {
410
- if let ty:: Predicate :: Trait ( p) = pred {
411
- if Some ( p. def_id ( ) ) == fcx. tcx . lang_items ( ) . sized_trait ( ) {
412
- skip = true ;
413
- }
414
- }
389
+ // Check the clauses are well-formed when the param is substituted by it's default.
390
+ // In trait definitions, predicates as `Self: Trait` and `Self: Super` are problematic.
391
+ // Therefore we skip such predicates. This means we check less than we could.
392
+ for pred in predicates. predicates . iter ( ) . filter ( |p| !( is_trait && p. has_self_ty ( ) ) ) {
393
+ let mut skip = true ;
394
+ let substs = ty:: subst:: Substs :: for_item ( fcx. tcx , def_id, |def, _| {
395
+ // All regions are identity.
396
+ fcx. tcx . mk_region ( ty:: ReEarlyBound ( def. to_early_bound_region_data ( ) ) )
397
+ } , |def, _| {
398
+ let identity_substs = fcx. tcx . mk_param_from_def ( def) ;
399
+ if def. index != param_def. index {
400
+ identity_substs
401
+ } else {
402
+ let sized = fcx. tcx . lang_items ( ) . sized_trait ( ) ;
403
+ let pred_is_sized = match pred {
404
+ ty:: Predicate :: Trait ( p) => Some ( p. def_id ( ) ) == sized,
405
+ _ => false ,
406
+ } ;
407
+ let default_ty = fcx. tcx . type_of ( def. def_id ) ;
408
+ let default_is_self = match default_ty. sty {
409
+ ty:: TyParam ( ref p) => p. is_self ( ) ,
410
+ _ => false
411
+ } ;
412
+ // In trait defs, skip `Self: Sized` when `Self` is the default.
413
+ if is_trait && pred_is_sized && default_is_self {
414
+ identity_substs
415
+ } else {
416
+ skip = false ;
417
+ default_ty
415
418
}
416
- _ => ( )
417
419
}
418
- default_ty
420
+ } ) ;
421
+ if !skip {
422
+ substituted_predicates. push ( pred. subst ( fcx. tcx , substs) ) ;
419
423
}
420
- } ) ;
421
-
422
- if skip || no_default {
423
- continue ;
424
424
}
425
-
426
- default_predicates. push ( pred. subst ( fcx. tcx , substs) ) ;
427
425
}
428
426
429
- predicates. predicates . extend ( default_predicates ) ;
427
+ predicates. predicates . extend ( substituted_predicates ) ;
430
428
let predicates = predicates. instantiate_identity ( fcx. tcx ) ;
431
429
let predicates = fcx. normalize_associated_types_in ( span, & predicates) ;
432
430
0 commit comments