@@ -193,7 +193,6 @@ pub enum SelectionCandidate<'tcx> {
193193/// The evaluation results are ordered:
194194/// - `EvaluatedToOk` implies `EvaluatedToOkModuloRegions`
195195/// implies `EvaluatedToAmbig` implies `EvaluatedToAmbigStackDependent`
196- /// - `EvaluatedToErr` implies `EvaluatedToErrStackDependent`
197196/// - the "union" of evaluation results is equal to their maximum -
198197/// all the "potential success" candidates can potentially succeed,
199198/// so they are noops when unioned with a definite error, and within
@@ -219,52 +218,9 @@ pub enum EvaluationResult {
219218 /// variables. We are somewhat imprecise there, so we don't actually
220219 /// know the real result.
221220 ///
222- /// This can't be trivially cached for the same reason as `EvaluatedToErrStackDependent`.
221+ /// This can't be trivially cached because the result depends on the
222+ /// stack results.
223223 EvaluatedToAmbigStackDependent ,
224- /// Evaluation failed because we encountered an obligation we are already
225- /// trying to prove on this branch.
226- ///
227- /// We know this branch can't be a part of a minimal proof-tree for
228- /// the "root" of our cycle, because then we could cut out the recursion
229- /// and maintain a valid proof tree. However, this does not mean
230- /// that all the obligations on this branch do not hold -- it's possible
231- /// that we entered this branch "speculatively", and that there
232- /// might be some other way to prove this obligation that does not
233- /// go through this cycle -- so we can't cache this as a failure.
234- ///
235- /// For example, suppose we have this:
236- ///
237- /// ```rust,ignore (pseudo-Rust)
238- /// pub trait Trait { fn xyz(); }
239- /// // This impl is "useless", but we can still have
240- /// // an `impl Trait for SomeUnsizedType` somewhere.
241- /// impl<T: Trait + Sized> Trait for T { fn xyz() {} }
242- ///
243- /// pub fn foo<T: Trait + ?Sized>() {
244- /// <T as Trait>::xyz();
245- /// }
246- /// ```
247- ///
248- /// When checking `foo`, we have to prove `T: Trait`. This basically
249- /// translates into this:
250- ///
251- /// ```plain,ignore
252- /// (T: Trait + Sized →_\impl T: Trait), T: Trait ⊢ T: Trait
253- /// ```
254- ///
255- /// When we try to prove it, we first go the first option, which
256- /// recurses. This shows us that the impl is "useless" -- it won't
257- /// tell us that `T: Trait` unless it already implemented `Trait`
258- /// by some other means. However, that does not prevent `T: Trait`
259- /// does not hold, because of the bound (which can indeed be satisfied
260- /// by `SomeUnsizedType` from another crate).
261- //
262- // FIXME: when an `EvaluatedToErrStackDependent` goes past its parent root, we
263- // ought to convert it to an `EvaluatedToErr`, because we know
264- // there definitely isn't a proof tree for that obligation. Not
265- // doing so is still sound -- there isn't any proof tree, so the
266- // branch still can't be a part of a minimal one -- but does not re-enable caching.
267- EvaluatedToErrStackDependent ,
268224 /// Evaluation failed.
269225 EvaluatedToErr ,
270226}
@@ -290,13 +246,13 @@ impl EvaluationResult {
290246 | EvaluatedToAmbig
291247 | EvaluatedToAmbigStackDependent => true ,
292248
293- EvaluatedToErr | EvaluatedToErrStackDependent => false ,
249+ EvaluatedToErr => false ,
294250 }
295251 }
296252
297253 pub fn is_stack_dependent ( self ) -> bool {
298254 match self {
299- EvaluatedToAmbigStackDependent | EvaluatedToErrStackDependent => true ,
255+ EvaluatedToAmbigStackDependent => true ,
300256
301257 EvaluatedToOkModuloOpaqueTypes
302258 | EvaluatedToOk
0 commit comments