diff --git a/compiler/rustc_trait_selection/src/solve/mod.rs b/compiler/rustc_trait_selection/src/solve/mod.rs index e56588c58bd0..e3f8f7cddaba 100644 --- a/compiler/rustc_trait_selection/src/solve/mod.rs +++ b/compiler/rustc_trait_selection/src/solve/mod.rs @@ -485,35 +485,38 @@ impl<'tcx> EvalCtxt<'_, 'tcx> { mut goals: Vec>>, ) -> Result { let mut new_goals = Vec::new(); - self.repeat_while_none(|this| { - let mut has_changed = Err(Certainty::Yes); - for goal in goals.drain(..) { - let (changed, certainty) = match this.evaluate_goal(goal) { - Ok(result) => result, - Err(NoSolution) => return Some(Err(NoSolution)), - }; + self.repeat_while_none( + |_| Certainty::Maybe(MaybeCause::Overflow), + |this| { + let mut has_changed = Err(Certainty::Yes); + for goal in goals.drain(..) { + let (changed, certainty) = match this.evaluate_goal(goal) { + Ok(result) => result, + Err(NoSolution) => return Some(Err(NoSolution)), + }; - if changed { - has_changed = Ok(()); - } + if changed { + has_changed = Ok(()); + } - match certainty { - Certainty::Yes => {} - Certainty::Maybe(_) => { - new_goals.push(goal); - has_changed = has_changed.map_err(|c| c.unify_and(certainty)); + match certainty { + Certainty::Yes => {} + Certainty::Maybe(_) => { + new_goals.push(goal); + has_changed = has_changed.map_err(|c| c.unify_and(certainty)); + } } } - } - match has_changed { - Ok(()) => { - mem::swap(&mut new_goals, &mut goals); - None + match has_changed { + Ok(()) => { + mem::swap(&mut new_goals, &mut goals); + None + } + Err(certainty) => Some(Ok(certainty)), } - Err(certainty) => Some(Ok(certainty)), - } - }) + }, + ) } // Recursively evaluates a list of goals to completion, making a query response. diff --git a/compiler/rustc_trait_selection/src/solve/search_graph/overflow.rs b/compiler/rustc_trait_selection/src/solve/search_graph/overflow.rs index 1dd3894c91ad..c472dfe5a009 100644 --- a/compiler/rustc_trait_selection/src/solve/search_graph/overflow.rs +++ b/compiler/rustc_trait_selection/src/solve/search_graph/overflow.rs @@ -63,10 +63,11 @@ impl<'tcx> SearchGraph<'tcx> { impl<'tcx> EvalCtxt<'_, 'tcx> { /// A `while`-loop which tracks overflow. - pub fn repeat_while_none( + pub fn repeat_while_none( &mut self, - mut loop_body: impl FnMut(&mut Self) -> Option>, - ) -> Result { + mut overflow_body: impl FnMut(&mut Self) -> T, + mut loop_body: impl FnMut(&mut Self) -> Option>, + ) -> Result { let start_depth = self.search_graph.overflow_data.additional_depth; let depth = self.search_graph.stack.len(); while !self.search_graph.overflow_data.has_overflow(depth) { @@ -79,6 +80,6 @@ impl<'tcx> EvalCtxt<'_, 'tcx> { } self.search_graph.overflow_data.additional_depth = start_depth; self.search_graph.overflow_data.deal_with_overflow(); - Ok(Certainty::Maybe(MaybeCause::Overflow)) + Ok(overflow_body(self)) } }