Skip to content

Not desugaring to HRTB for closure argument #73433

@alecmocatta

Description

@alecmocatta

My understanding was that FnMut(&T) desugars to for<'a> FnMut(&'a T). In this instance, it is seemingly not doing so. If you comment out line 44 then this compiles. Why is the map function triggering the incorrect (?) desugaring, and how can I fix it?

trait Pipe<In> {
    type Out;
}

struct Identity;
impl<In> Pipe<In> for Identity {
    type Out = In;
}

struct Map<P, F> {
    p: P,
    f: F,
}
impl<P, In, F, R> Pipe<In> for Map<P, F>
where
    P: Pipe<In>,
    F: FnMut(P::Out) -> R,
{
    type Out = R;
}

fn map<P, In, F, R>(p: P, f: F) -> Map<P, F>
where
    P: Pipe<In>,
    F: FnMut(P::Out) -> R,
{
    Map { p, f }
}

fn pipe<T, Sink>(_: Sink)
where
    Sink: for<'a> Pipe<&'a T>,
    T: 'static,
{
}

fn main() {
    fn abc<'a>(_: &'a String) {}
    pipe(Map {
        p: Identity,
        f: |_: &String| {},
    });
    pipe(map(Identity, abc));
    pipe(map(Identity, |_: &String| {}));
}

(Playground)

Errors:

   Compiling playground v0.0.1 (/playground)
error[E0308]: mismatched types
  --> src/main.rs:44:5
   |
44 |     pipe(map(Identity, |_: &String| {}));
   |     ^^^^ one type is more general than the other
   |
   = note: expected type `std::ops::FnOnce<(&'a std::string::String,)>`
              found type `std::ops::FnOnce<(&std::string::String,)>`

error: aborting due to previous error

For more information about this error, try `rustc --explain E0308`.
error: could not compile `playground`.

To learn more, run the command again with --verbose.


Possibly related: #70263

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-closuresArea: Closures (`|…| { … }`)A-lifetimesArea: Lifetimes / regionsT-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions