Make evaluate_obligation
not succeed unconditionally if it registered new hidden types for opaque types
This commit is contained in:
parent
ade2a96ff1
commit
84fc551664
8 changed files with 31 additions and 11 deletions
|
@ -891,6 +891,10 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
||||||
.region_constraints_added_in_snapshot(&snapshot.undo_snapshot)
|
.region_constraints_added_in_snapshot(&snapshot.undo_snapshot)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn opaque_types_added_in_snapshot(&self, snapshot: &CombinedSnapshot<'a, 'tcx>) -> bool {
|
||||||
|
self.inner.borrow().undo_log.opaque_types_in_snapshot(&snapshot.undo_snapshot)
|
||||||
|
}
|
||||||
|
|
||||||
pub fn add_given(&self, sub: ty::Region<'tcx>, sup: ty::RegionVid) {
|
pub fn add_given(&self, sub: ty::Region<'tcx>, sup: ty::RegionVid) {
|
||||||
self.inner.borrow_mut().unwrap_region_constraints().add_given(sub, sup);
|
self.inner.borrow_mut().unwrap_region_constraints().add_given(sub, sup);
|
||||||
}
|
}
|
||||||
|
|
|
@ -185,6 +185,10 @@ impl<'tcx> InferCtxtUndoLogs<'tcx> {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(crate) fn opaque_types_in_snapshot(&self, s: &Snapshot<'tcx>) -> bool {
|
||||||
|
self.logs[s.undo_len..].iter().any(|log| matches!(log, UndoLog::OpaqueTypes(..)))
|
||||||
|
}
|
||||||
|
|
||||||
pub(crate) fn region_constraints(
|
pub(crate) fn region_constraints(
|
||||||
&self,
|
&self,
|
||||||
) -> impl Iterator<Item = &'_ region_constraints::UndoLog<'tcx>> + Clone {
|
) -> impl Iterator<Item = &'_ region_constraints::UndoLog<'tcx>> + Clone {
|
||||||
|
|
|
@ -174,6 +174,10 @@ pub enum SelectionCandidate<'tcx> {
|
||||||
pub enum EvaluationResult {
|
pub enum EvaluationResult {
|
||||||
/// Evaluation successful.
|
/// Evaluation successful.
|
||||||
EvaluatedToOk,
|
EvaluatedToOk,
|
||||||
|
/// Evaluation successful, but need to rerun because opaque types got
|
||||||
|
/// hidden types assigned without it being known whether the opaque types
|
||||||
|
/// are within their defining scope
|
||||||
|
EvaluatedToOkModuloOpaqueTypes,
|
||||||
/// Evaluation successful, but there were unevaluated region obligations.
|
/// Evaluation successful, but there were unevaluated region obligations.
|
||||||
EvaluatedToOkModuloRegions,
|
EvaluatedToOkModuloRegions,
|
||||||
/// Evaluation is known to be ambiguous -- it *might* hold for some
|
/// Evaluation is known to be ambiguous -- it *might* hold for some
|
||||||
|
@ -252,9 +256,11 @@ impl EvaluationResult {
|
||||||
|
|
||||||
pub fn may_apply(self) -> bool {
|
pub fn may_apply(self) -> bool {
|
||||||
match self {
|
match self {
|
||||||
EvaluatedToOk | EvaluatedToOkModuloRegions | EvaluatedToAmbig | EvaluatedToUnknown => {
|
EvaluatedToOkModuloOpaqueTypes
|
||||||
true
|
| EvaluatedToOk
|
||||||
}
|
| EvaluatedToOkModuloRegions
|
||||||
|
| EvaluatedToAmbig
|
||||||
|
| EvaluatedToUnknown => true,
|
||||||
|
|
||||||
EvaluatedToErr | EvaluatedToRecur => false,
|
EvaluatedToErr | EvaluatedToRecur => false,
|
||||||
}
|
}
|
||||||
|
@ -264,7 +270,11 @@ impl EvaluationResult {
|
||||||
match self {
|
match self {
|
||||||
EvaluatedToUnknown | EvaluatedToRecur => true,
|
EvaluatedToUnknown | EvaluatedToRecur => true,
|
||||||
|
|
||||||
EvaluatedToOk | EvaluatedToOkModuloRegions | EvaluatedToAmbig | EvaluatedToErr => false,
|
EvaluatedToOkModuloOpaqueTypes
|
||||||
|
| EvaluatedToOk
|
||||||
|
| EvaluatedToOkModuloRegions
|
||||||
|
| EvaluatedToAmbig
|
||||||
|
| EvaluatedToErr => false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -207,11 +207,6 @@ impl FlagComputation {
|
||||||
|
|
||||||
&ty::FnDef(_, substs) => {
|
&ty::FnDef(_, substs) => {
|
||||||
self.add_substs(substs);
|
self.add_substs(substs);
|
||||||
// HACK(#98608, oli-obk): Function items with opaque types in their signature will
|
|
||||||
// end up not having the HAS_TY_OPAQUE flag set, causing `evaluate_obligation` to
|
|
||||||
// optimistically assume the function item matches any signature. See documentation
|
|
||||||
// on `HAS_FREE_LOCAL_NAMES` for details.
|
|
||||||
self.add_flags(TypeFlags::HAS_TY_OPAQUE);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
&ty::FnPtr(fn_sig) => self.bound_computation(fn_sig, |computation, fn_sig| {
|
&ty::FnPtr(fn_sig) => self.bound_computation(fn_sig, |computation, fn_sig| {
|
||||||
|
|
|
@ -777,6 +777,7 @@ impl<'a, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'a, 'tcx> {
|
||||||
Ok(
|
Ok(
|
||||||
EvaluationResult::EvaluatedToOk
|
EvaluationResult::EvaluatedToOk
|
||||||
| EvaluationResult::EvaluatedToOkModuloRegions
|
| EvaluationResult::EvaluatedToOkModuloRegions
|
||||||
|
| EvaluationResult::EvaluatedToOkModuloOpaqueTypes
|
||||||
| EvaluationResult::EvaluatedToAmbig,
|
| EvaluationResult::EvaluatedToAmbig,
|
||||||
) => {}
|
) => {}
|
||||||
_ => return false,
|
_ => return false,
|
||||||
|
|
|
@ -394,6 +394,10 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
||||||
Err(_) => return Ok(EvaluatedToErr),
|
Err(_) => return Ok(EvaluatedToErr),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if self.infcx.opaque_types_added_in_snapshot(snapshot) {
|
||||||
|
return Ok(result.max(EvaluatedToOkModuloOpaqueTypes));
|
||||||
|
}
|
||||||
|
|
||||||
match self.infcx.region_constraints_added_in_snapshot(snapshot) {
|
match self.infcx.region_constraints_added_in_snapshot(snapshot) {
|
||||||
None => Ok(result),
|
None => Ok(result),
|
||||||
Some(_) => Ok(result.max(EvaluatedToOkModuloRegions)),
|
Some(_) => Ok(result.max(EvaluatedToOkModuloRegions)),
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
type Foo = impl Fn() -> Foo;
|
type Foo = impl Fn() -> Foo;
|
||||||
|
|
||||||
fn foo() -> Foo {
|
fn foo() -> Foo {
|
||||||
foo //~ ERROR: overflow evaluating the requirement `<fn() -> Foo {foo} as FnOnce<()>>::Output == fn() -> Foo {foo}`
|
foo //~ ERROR: overflow evaluating the requirement `fn() -> Foo {foo}: Sized`
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
|
|
@ -1,8 +1,10 @@
|
||||||
error[E0275]: overflow evaluating the requirement `<fn() -> Foo {foo} as FnOnce<()>>::Output == fn() -> Foo {foo}`
|
error[E0275]: overflow evaluating the requirement `fn() -> Foo {foo}: Sized`
|
||||||
--> $DIR/issue-53398-cyclic-types.rs:6:5
|
--> $DIR/issue-53398-cyclic-types.rs:6:5
|
||||||
|
|
|
|
||||||
LL | foo
|
LL | foo
|
||||||
| ^^^
|
| ^^^
|
||||||
|
|
|
||||||
|
= help: consider increasing the recursion limit by adding a `#![recursion_limit = "256"]` attribute to your crate (`issue_53398_cyclic_types`)
|
||||||
|
|
||||||
error: aborting due to previous error
|
error: aborting due to previous error
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue