rust-lang / trait-system-refactor-initiative

The Rustc Trait System Refactor Initiative
21 stars 0 forks source link

generalization ambiguity 2 - even yoke-ier #110

Closed lcnr closed 4 months ago

lcnr commented 4 months ago
#![allow(unused)]
trait Yokeable<'a> {
    type Output;
}
trait Id {
    type Refl;
}

fn into_deserialized<M: Id>() -> M
where
    M::Refl: for<'a> Yokeable<'a>,
{
    try_map_project::<M, _>(|_| todo!())
}

fn try_map_project<M: Id, F>(_f: F) -> M
where
    M::Refl: for<'a> Yokeable<'a>,
    F: for<'a> FnOnce(&'a ()) -> <<M as Id>::Refl as Yokeable<'a>>::Output,
{
    todo!()
}

fn main() {}
lcnr commented 4 months ago

likely caused by closure signature inference

lcnr commented 4 months ago
#![allow(unused)]
trait HigherRanked {
    type Output<'a>;
}
trait Id {
    type Refl: HigherRanked;
}

fn foo<T: Id>() -> for<'a> fn(<<T as Id>::Refl as HigherRanked>::Output<'a>) {
    todo!()
}

fn bar<T: Id>() {
    // generalize here:
    let x = foo::<T>();
}

fn main() {}
lcnr commented 4 months ago

not caused by closure signature inference: if the outer alias refernces a bound var, the generalizer recurses into it, but then if the nested alias does not refer to bound vars, it gets replaced with an inference variable:

https://github.com/rust-lang/rust/blob/5ae5d135372c4b576edc73c191d2dc86b1d16b5c/compiler/rustc_infer/src/infer/relate/generalize.rs#L353-L358

We generalize for<'a> fn(<<T as Id>::Refl as HigherRanked>::Output<'a>) to for<'a> fn(<?new as HigherRanked>::Output<'a>)

lcnr commented 4 months ago

fixed by https://github.com/rust-lang/rust/pull/124827