Skip to content

Commit 81cfd5a

Browse files
authored
Unrolled build for rust-lang#121497
Rollup merge of rust-lang#121497 - lcnr:coherence-suggest-increasing-recursion-limit, r=compiler-errors `-Znext-solver=coherence`: suggest increasing recursion limit r? `@compiler-errors`
2 parents e612d07 + 8c5e83d commit 81cfd5a

29 files changed

+342
-256
lines changed

compiler/rustc_infer/src/traits/mod.rs

+6-4
Original file line numberDiff line numberDiff line change
@@ -135,16 +135,18 @@ pub struct FulfillmentError<'tcx> {
135135

136136
#[derive(Clone)]
137137
pub enum FulfillmentErrorCode<'tcx> {
138-
/// Inherently impossible to fulfill; this trait is implemented if and only if it is already implemented.
138+
/// Inherently impossible to fulfill; this trait is implemented if and only
139+
/// if it is already implemented.
139140
Cycle(Vec<PredicateObligation<'tcx>>),
140141
SelectionError(SelectionError<'tcx>),
141142
ProjectionError(MismatchedProjectionTypes<'tcx>),
142143
SubtypeError(ExpectedFound<Ty<'tcx>>, TypeError<'tcx>), // always comes from a SubtypePredicate
143144
ConstEquateError(ExpectedFound<Const<'tcx>>, TypeError<'tcx>),
144145
Ambiguity {
145-
/// Overflow reported from the new solver `-Znext-solver`, which will
146-
/// be reported as an regular error as opposed to a fatal error.
147-
overflow: bool,
146+
/// Overflow is only `Some(suggest_recursion_limit)` when using the next generation
147+
/// trait solver `-Znext-solver`. With the old solver overflow is eagerly handled by
148+
/// emitting a fatal error instead.
149+
overflow: Option<bool>,
148150
},
149151
}
150152

compiler/rustc_infer/src/traits/structural_impls.rs

+4-2
Original file line numberDiff line numberDiff line change
@@ -47,8 +47,10 @@ impl<'tcx> fmt::Debug for traits::FulfillmentErrorCode<'tcx> {
4747
ConstEquateError(ref a, ref b) => {
4848
write!(f, "CodeConstEquateError({a:?}, {b:?})")
4949
}
50-
Ambiguity { overflow: false } => write!(f, "Ambiguity"),
51-
Ambiguity { overflow: true } => write!(f, "Overflow"),
50+
Ambiguity { overflow: None } => write!(f, "Ambiguity"),
51+
Ambiguity { overflow: Some(suggest_increasing_limit) } => {
52+
write!(f, "Overflow({suggest_increasing_limit})")
53+
}
5254
Cycle(ref cycle) => write!(f, "Cycle({cycle:?})"),
5355
}
5456
}

compiler/rustc_middle/src/traits/solve.rs

+20-10
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,6 @@ pub enum Certainty {
6060

6161
impl Certainty {
6262
pub const AMBIGUOUS: Certainty = Certainty::Maybe(MaybeCause::Ambiguity);
63-
pub const OVERFLOW: Certainty = Certainty::Maybe(MaybeCause::Overflow);
6463

6564
/// Use this function to merge the certainty of multiple nested subgoals.
6665
///
@@ -79,16 +78,13 @@ impl Certainty {
7978
(Certainty::Yes, Certainty::Yes) => Certainty::Yes,
8079
(Certainty::Yes, Certainty::Maybe(_)) => other,
8180
(Certainty::Maybe(_), Certainty::Yes) => self,
82-
(Certainty::Maybe(MaybeCause::Ambiguity), Certainty::Maybe(MaybeCause::Ambiguity)) => {
83-
Certainty::Maybe(MaybeCause::Ambiguity)
84-
}
85-
(Certainty::Maybe(MaybeCause::Ambiguity), Certainty::Maybe(MaybeCause::Overflow))
86-
| (Certainty::Maybe(MaybeCause::Overflow), Certainty::Maybe(MaybeCause::Ambiguity))
87-
| (Certainty::Maybe(MaybeCause::Overflow), Certainty::Maybe(MaybeCause::Overflow)) => {
88-
Certainty::Maybe(MaybeCause::Overflow)
89-
}
81+
(Certainty::Maybe(a), Certainty::Maybe(b)) => Certainty::Maybe(a.unify_with(b)),
9082
}
9183
}
84+
85+
pub const fn overflow(suggest_increasing_limit: bool) -> Certainty {
86+
Certainty::Maybe(MaybeCause::Overflow { suggest_increasing_limit })
87+
}
9288
}
9389

9490
/// Why we failed to evaluate a goal.
@@ -99,7 +95,21 @@ pub enum MaybeCause {
9995
/// or we hit a case where we just don't bother, e.g. `?x: Trait` goals.
10096
Ambiguity,
10197
/// We gave up due to an overflow, most often by hitting the recursion limit.
102-
Overflow,
98+
Overflow { suggest_increasing_limit: bool },
99+
}
100+
101+
impl MaybeCause {
102+
fn unify_with(self, other: MaybeCause) -> MaybeCause {
103+
match (self, other) {
104+
(MaybeCause::Ambiguity, MaybeCause::Ambiguity) => MaybeCause::Ambiguity,
105+
(MaybeCause::Ambiguity, MaybeCause::Overflow { .. }) => other,
106+
(MaybeCause::Overflow { .. }, MaybeCause::Ambiguity) => self,
107+
(
108+
MaybeCause::Overflow { suggest_increasing_limit: a },
109+
MaybeCause::Overflow { suggest_increasing_limit: b },
110+
) => MaybeCause::Overflow { suggest_increasing_limit: a || b },
111+
}
112+
}
103113
}
104114

105115
#[derive(Debug, PartialEq, Eq, Clone, Copy, Hash, HashStable, TypeFoldable, TypeVisitable)]

compiler/rustc_trait_selection/src/solve/alias_relate.rs

+4-2
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,13 @@ impl<'tcx> EvalCtxt<'_, 'tcx> {
3636
let Goal { param_env, predicate: (lhs, rhs, direction) } = goal;
3737

3838
let Some(lhs) = self.try_normalize_term(param_env, lhs)? else {
39-
return self.evaluate_added_goals_and_make_canonical_response(Certainty::OVERFLOW);
39+
return self
40+
.evaluate_added_goals_and_make_canonical_response(Certainty::overflow(true));
4041
};
4142

4243
let Some(rhs) = self.try_normalize_term(param_env, rhs)? else {
43-
return self.evaluate_added_goals_and_make_canonical_response(Certainty::OVERFLOW);
44+
return self
45+
.evaluate_added_goals_and_make_canonical_response(Certainty::overflow(true));
4446
};
4547

4648
let variance = match direction {

compiler/rustc_trait_selection/src/solve/eval_ctxt/mod.rs

+16-17
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ use rustc_infer::infer::{
77
BoundRegionConversionTime, DefineOpaqueTypes, InferCtxt, InferOk, TyCtxtInferExt,
88
};
99
use rustc_infer::traits::query::NoSolution;
10+
use rustc_infer::traits::solve::MaybeCause;
1011
use rustc_infer::traits::ObligationCause;
1112
use rustc_middle::infer::canonical::CanonicalVarInfos;
1213
use rustc_middle::infer::unify_key::{ConstVariableOrigin, ConstVariableOriginKind};
@@ -29,7 +30,7 @@ use std::ops::ControlFlow;
2930
use crate::traits::vtable::{count_own_vtable_entries, prepare_vtable_segments, VtblSegment};
3031

3132
use super::inspect::ProofTreeBuilder;
32-
use super::{search_graph, GoalEvaluationKind};
33+
use super::{search_graph, GoalEvaluationKind, FIXPOINT_STEP_LIMIT};
3334
use super::{search_graph::SearchGraph, Goal};
3435
use super::{GoalSource, SolverMode};
3536
pub use select::InferCtxtSelectExt;
@@ -154,10 +155,6 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> {
154155
self.search_graph.solver_mode()
155156
}
156157

157-
pub(super) fn local_overflow_limit(&self) -> usize {
158-
self.search_graph.local_overflow_limit()
159-
}
160-
161158
/// Creates a root evaluation context and search graph. This should only be
162159
/// used from outside of any evaluation, and other methods should be preferred
163160
/// over using this manually (such as [`InferCtxtEvalExt::evaluate_root_goal`]).
@@ -167,7 +164,7 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> {
167164
f: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> R,
168165
) -> (R, Option<inspect::GoalEvaluation<'tcx>>) {
169166
let mode = if infcx.intercrate { SolverMode::Coherence } else { SolverMode::Normal };
170-
let mut search_graph = search_graph::SearchGraph::new(infcx.tcx, mode);
167+
let mut search_graph = search_graph::SearchGraph::new(mode);
171168

172169
let mut ecx = EvalCtxt {
173170
search_graph: &mut search_graph,
@@ -388,16 +385,18 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> {
388385
&& source != GoalSource::ImplWhereBound
389386
};
390387

391-
if response.value.certainty == Certainty::OVERFLOW && !keep_overflow_constraints() {
392-
(Certainty::OVERFLOW, false)
393-
} else {
394-
let has_changed = !response.value.var_values.is_identity_modulo_regions()
395-
|| !response.value.external_constraints.opaque_types.is_empty();
396-
397-
let certainty =
398-
self.instantiate_and_apply_query_response(param_env, original_values, response);
399-
(certainty, has_changed)
388+
if let Certainty::Maybe(MaybeCause::Overflow { .. }) = response.value.certainty
389+
&& !keep_overflow_constraints()
390+
{
391+
return (response.value.certainty, false);
400392
}
393+
394+
let has_changed = !response.value.var_values.is_identity_modulo_regions()
395+
|| !response.value.external_constraints.opaque_types.is_empty();
396+
397+
let certainty =
398+
self.instantiate_and_apply_query_response(param_env, original_values, response);
399+
(certainty, has_changed)
401400
}
402401

403402
fn compute_goal(&mut self, goal: Goal<'tcx, ty::Predicate<'tcx>>) -> QueryResult<'tcx> {
@@ -466,8 +465,8 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> {
466465
let inspect = self.inspect.new_evaluate_added_goals();
467466
let inspect = core::mem::replace(&mut self.inspect, inspect);
468467

469-
let mut response = Ok(Certainty::OVERFLOW);
470-
for _ in 0..self.local_overflow_limit() {
468+
let mut response = Ok(Certainty::overflow(false));
469+
for _ in 0..FIXPOINT_STEP_LIMIT {
471470
// FIXME: This match is a bit ugly, it might be nice to change the inspect
472471
// stuff to use a closure instead. which should hopefully simplify this a bit.
473472
match self.evaluate_added_goals_step() {

0 commit comments

Comments
 (0)