@@ -27,6 +27,7 @@ use super::{
2727
2828use crate :: infer:: { InferCtxt , InferOk , TypeFreshener } ;
2929use crate :: traits:: error_reporting:: TypeErrCtxtExt ;
30+ use crate :: traits:: project:: try_normalize_with_depth_to;
3031use crate :: traits:: project:: ProjectAndUnifyResult ;
3132use crate :: traits:: project:: ProjectionCacheKeyExt ;
3233use crate :: traits:: ProjectionCacheKey ;
@@ -1049,7 +1050,51 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
10491050 return Ok ( cycle_result) ;
10501051 }
10511052
1052- let ( result, dep_node) = self . in_task ( |this| this. evaluate_stack ( & stack) ) ;
1053+ let ( result, dep_node) = self . in_task ( |this| {
1054+ let mut result = this. evaluate_stack ( & stack) ?;
1055+
1056+ // fix issue #103563, we don't normalize
1057+ // nested obligations which produced by `TraitDef` candidate
1058+ // (i.e. using bounds on assoc items as assumptions).
1059+ // because we don't have enough information to
1060+ // normalize these obligations before evaluating.
1061+ // so we will try to normalize the obligation and evaluate again.
1062+ // we will replace it with new solver in the future.
1063+ if EvaluationResult :: EvaluatedToErr == result
1064+ && fresh_trait_pred. has_projections ( )
1065+ && fresh_trait_pred. is_global ( )
1066+ {
1067+ let mut nested_obligations = Vec :: new ( ) ;
1068+ let predicate = try_normalize_with_depth_to (
1069+ this,
1070+ param_env,
1071+ obligation. cause . clone ( ) ,
1072+ obligation. recursion_depth + 1 ,
1073+ obligation. predicate ,
1074+ & mut nested_obligations,
1075+ ) ;
1076+ if predicate != obligation. predicate {
1077+ let mut nested_result = EvaluationResult :: EvaluatedToOk ;
1078+ for obligation in nested_obligations {
1079+ nested_result = cmp:: max (
1080+ this. evaluate_predicate_recursively ( stack. list ( ) , obligation) ?,
1081+ nested_result,
1082+ ) ;
1083+ }
1084+
1085+ if nested_result. must_apply_modulo_regions ( ) {
1086+ let obligation = obligation. with ( this. tcx ( ) , predicate) ;
1087+ result = cmp:: max (
1088+ nested_result,
1089+ this. evaluate_trait_predicate_recursively ( stack. list ( ) , obligation) ?,
1090+ ) ;
1091+ }
1092+ }
1093+ }
1094+
1095+ Ok :: < _ , OverflowError > ( result)
1096+ } ) ;
1097+
10531098 let result = result?;
10541099
10551100 if !result. must_apply_modulo_regions ( ) {
0 commit comments