@@ -10,8 +10,8 @@ use rustc_infer::traits::{
1010 FromSolverError , PredicateObligation , PredicateObligations , TraitEngine ,
1111} ;
1212use rustc_middle:: ty:: {
13- self , DelayedSet , Ty , TyCtxt , TypeSuperVisitable , TypeVisitable , TypeVisitableExt , TypeVisitor ,
14- TypingMode ,
13+ self , DelayedSet , Ty , TyCtxt , TyVid , TypeSuperVisitable , TypeVisitable , TypeVisitableExt ,
14+ TypeVisitor , TypingMode ,
1515} ;
1616use rustc_next_trait_solver:: delegate:: SolverDelegate as _;
1717use rustc_next_trait_solver:: solve:: {
@@ -85,8 +85,30 @@ impl<'tcx> ObligationStorage<'tcx> {
8585 obligations. extend ( self . overflowed . iter ( ) . cloned ( ) ) ;
8686 obligations
8787 }
88+ fn clone_pending_potentially_referencing_sub_root (
89+ & self ,
90+ vid : TyVid ,
91+ ) -> PredicateObligations < ' tcx > {
92+ let mut obligations: PredicateObligations < ' tcx > = self
93+ . pending
94+ . iter ( )
95+ . filter ( |( _, stalled_on) | {
96+ // This may incorrectly return `false` in case we've made
97+ // inference progress since the last time we tried to evaluate
98+ // this obligation.
99+ if let Some ( stalled_on) = stalled_on {
100+ stalled_on. sub_roots . iter ( ) . any ( |& r| r == vid)
101+ } else {
102+ true
103+ }
104+ } )
105+ . map ( |( o, _) | o. clone ( ) )
106+ . collect ( ) ;
107+ obligations. extend ( self . overflowed . iter ( ) . cloned ( ) ) ;
108+ obligations
109+ }
88110
89- fn drain_pending (
111+ fn drain_pending_ignoring_overflowed (
90112 & mut self ,
91113 cond : impl Fn ( & PredicateObligation < ' tcx > ) -> bool ,
92114 ) -> PendingObligations < ' tcx > {
@@ -184,7 +206,9 @@ where
184206 let mut errors = Vec :: new ( ) ;
185207 loop {
186208 let mut any_changed = false ;
187- for ( mut obligation, stalled_on) in self . obligations . drain_pending ( |_| true ) {
209+ for ( mut obligation, stalled_on) in
210+ self . obligations . drain_pending_ignoring_overflowed ( |_| true )
211+ {
188212 if !infcx. tcx . recursion_limit ( ) . value_within_limit ( obligation. recursion_depth ) {
189213 self . obligations . on_fulfillment_overflow ( infcx) ;
190214 // Only return true errors that we have accumulated while processing.
@@ -277,6 +301,12 @@ where
277301 fn pending_obligations ( & self ) -> PredicateObligations < ' tcx > {
278302 self . obligations . clone_pending ( )
279303 }
304+ fn pending_obligations_potentially_referencing_sub_root (
305+ & self ,
306+ vid : ty:: TyVid ,
307+ ) -> PredicateObligations < ' tcx > {
308+ self . obligations . clone_pending_potentially_referencing_sub_root ( vid)
309+ }
280310
281311 fn drain_stalled_obligations_for_coroutines (
282312 & mut self ,
@@ -297,7 +327,7 @@ where
297327 }
298328
299329 self . obligations
300- . drain_pending ( |obl| {
330+ . drain_pending_ignoring_overflowed ( |obl| {
301331 infcx. probe ( |_| {
302332 infcx
303333 . visit_proof_tree (
0 commit comments