File tree Expand file tree Collapse file tree
rustc_next_trait_solver/src/solve
rustc_type_ir/src/ty_kind Expand file tree Collapse file tree Original file line number Diff line number Diff line change @@ -199,6 +199,7 @@ where
199199 /// but prevents incorrect normalization while hiding any trait errors.
200200 fn consider_error_guaranteed_candidate (
201201 ecx : & mut EvalCtxt < ' _ , D > ,
202+ goal : Goal < I , Self > ,
202203 guar : I :: ErrorGuaranteed ,
203204 ) -> Result < Candidate < I > , NoSolution > ;
204205
@@ -539,8 +540,8 @@ where
539540 // Instead of adding the logic here, it's a better idea to add it in
540541 // `EvalCtxt::disqualify_auto_trait_candidate_due_to_possible_impl` in
541542 // `solve::trait_goals` instead.
542- let result = if let Err ( guar) = goal. predicate . error_reported ( ) {
543- G :: consider_error_guaranteed_candidate ( self , guar)
543+ let result = if let ty :: Error ( guar) = goal. predicate . self_ty ( ) . kind ( ) {
544+ G :: consider_error_guaranteed_candidate ( self , goal , guar)
544545 } else if cx. trait_is_auto ( trait_def_id) {
545546 G :: consider_auto_trait_candidate ( self , goal)
546547 } else if cx. trait_is_alias ( trait_def_id) {
Original file line number Diff line number Diff line change @@ -182,6 +182,7 @@ where
182182
183183 fn consider_error_guaranteed_candidate (
184184 ecx : & mut EvalCtxt < ' _ , D > ,
185+ _goal : Goal < I , Self > ,
185186 _guar : I :: ErrorGuaranteed ,
186187 ) -> Result < Candidate < I > , NoSolution > {
187188 ecx. probe_builtin_trait_candidate ( BuiltinImplSource :: Misc )
Original file line number Diff line number Diff line change @@ -396,10 +396,21 @@ where
396396 /// Fail to normalize if the predicate contains an error, alternatively, we could normalize to `ty::Error`
397397 /// and succeed. Can experiment with this to figure out what results in better error messages.
398398 fn consider_error_guaranteed_candidate (
399- _ecx : & mut EvalCtxt < ' _ , D > ,
400- _guar : I :: ErrorGuaranteed ,
399+ ecx : & mut EvalCtxt < ' _ , D > ,
400+ goal : Goal < I , Self > ,
401+ guar : I :: ErrorGuaranteed ,
401402 ) -> Result < Candidate < I > , NoSolution > {
402- Err ( NoSolution )
403+ let cx = ecx. cx ( ) ;
404+ let error_term = match goal. predicate . alias . kind ( cx) {
405+ ty:: AliasTermKind :: ProjectionTy => Ty :: new_error ( cx, guar) . into ( ) ,
406+ ty:: AliasTermKind :: ProjectionConst => Const :: new_error ( cx, guar) . into ( ) ,
407+ kind => panic ! ( "expected projection, found {kind:?}" ) ,
408+ } ;
409+
410+ ecx. probe_builtin_trait_candidate ( BuiltinImplSource :: Misc ) . enter ( |ecx| {
411+ ecx. instantiate_normalizes_to_term ( goal, error_term) ;
412+ ecx. evaluate_added_goals_and_make_canonical_response ( Certainty :: Yes )
413+ } )
403414 }
404415
405416 fn consider_auto_trait_candidate (
Original file line number Diff line number Diff line change @@ -121,6 +121,7 @@ where
121121
122122 fn consider_error_guaranteed_candidate (
123123 ecx : & mut EvalCtxt < ' _ , D > ,
124+ _goal : Goal < I , Self > ,
124125 _guar : I :: ErrorGuaranteed ,
125126 ) -> Result < Candidate < I > , NoSolution > {
126127 ecx. probe_builtin_trait_candidate ( BuiltinImplSource :: Misc )
Original file line number Diff line number Diff line change @@ -462,6 +462,15 @@ impl<I: Interner> CoroutineClosureSignature<I> {
462462 coroutine_captures_by_ref_ty : I :: Ty ,
463463 env_region : I :: Region ,
464464 ) -> I :: Ty {
465+ // If either of the tupled capture types are constrained to error
466+ // (e.g. during typeck when the infcx is tainted), then just return
467+ // the error type directly.
468+ if let ty:: Error ( _) = tupled_inputs_ty. kind ( ) {
469+ return tupled_inputs_ty;
470+ } else if let ty:: Error ( _) = coroutine_captures_by_ref_ty. kind ( ) {
471+ return coroutine_captures_by_ref_ty;
472+ }
473+
465474 match kind {
466475 ty:: ClosureKind :: Fn | ty:: ClosureKind :: FnMut => {
467476 let ty:: FnPtr ( sig_tys, _) = coroutine_captures_by_ref_ty. kind ( ) else {
You can’t perform that action at this time.
0 commit comments