Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

existential type complains about '_ in concrete type of self-borrowing generators #60655

Closed
cramertj opened this issue May 9, 2019 · 6 comments · Fixed by #60799
Closed

existential type complains about '_ in concrete type of self-borrowing generators #60655

cramertj opened this issue May 9, 2019 · 6 comments · Fixed by #60799
Labels
A-async-await Area: Async & Await A-coroutines Area: Coroutines A-impl-trait Area: impl Trait. Universally / existentially quantified anonymous types with static dispatch. AsyncAwait-Triaged Async-await issues that have been triaged during a working group meeting.

Comments

@cramertj
Copy link
Member

cramertj commented May 9, 2019

Playground

error: non-defining existential type use in defining scope
  --> src/main.rs:9:22
   |
9  |   fn bar() -> ServeFut {
   |  ______________________^
10 | |     async move {
11 | |         let x = 5;
12 | |         await!(foo(&x))
13 | |     }
14 | | }
   | |_^ lifetime `'_` is part of concrete type but not used in parameter list of existential type

error: aborting due to previous error

cc @oli-obk

@cramertj cramertj added A-impl-trait Area: impl Trait. Universally / existentially quantified anonymous types with static dispatch. A-coroutines Area: Coroutines A-async-await Area: Async & Await AsyncAwait-Triaged Async-await issues that have been triaged during a working group meeting. labels May 9, 2019
@oli-obk
Copy link
Contributor

oli-obk commented May 9, 2019

Am I correct in assuming that this should not compile, but report an error about returning a reference to the local variable x? Or is the self-borrowing generator part what makes this work? so the x is part of the generator struct and the &x is the yielded thing?

I'll try pretty printing to the expanded HIR, since I'm not sure what's going on there

@oli-obk
Copy link
Contributor

oli-obk commented May 9, 2019

Expanded version:

#![feature(gen_future)]
#![feature(generators)]
#![feature(async_await, await_macro, existential_type)]

use std::future::{self, Future};

async fn foo(__arg0: &u8) {
}

pub existential type ServeFut: Future<Output = ()>;

fn bar() -> ServeFut {
    ::std::future::from_generator(move || {
        let x = 5;

        {
            let mut pinned = foo(&x);
            loop {
                match future::poll_with_tls_context(unsafe {
                    std::pin::Pin::new_unchecked(&mut pinned)
                }) {
                    std::task::Poll::Ready(x) => {
                        break x;
                    }
                    _ => (),
                }
                yield ()
            }
        }
    })
}
fn main() {}

Playground

@cramertj
Copy link
Member Author

cramertj commented May 9, 2019

Am I correct in assuming that this should not compile, but report an error about returning a reference to the local variable x?

No, this should definitely compile.

Or is the self-borrowing generator part what makes this work? so the x is part of the generator struct and the &x is the yielded thing?

&x isn't yielded, but yes, it's a local variable inside the generator (that references another local variable in the generator).

@oli-obk
Copy link
Contributor

oli-obk commented May 10, 2019

Hmm, so because the generator contains references, it has lifetimes, but these lifetimes actually refer to the generator again? Do we have a special kind of lifetime that we use for this? We should just ignore those generator lifetimes for existential types.

@cramertj
Copy link
Member Author

There's no special lifetime afaik (cc @Zoxc @tmandry).

@matthewjasper
Copy link
Contributor

We should ignore all bound regions. Function pointers have the same issue:

existential type A: Sized;

fn foo() -> A {
    (|x| ()) as for<'a> fn(&'a i32)
}

fn main() {}

Centril added a commit to Centril/rust that referenced this issue May 14, 2019
…n-existential-types, r=oli-obk

Allow late-bound regions in existential types

closes rust-lang#60655
r? @oli-obk
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-async-await Area: Async & Await A-coroutines Area: Coroutines A-impl-trait Area: impl Trait. Universally / existentially quantified anonymous types with static dispatch. AsyncAwait-Triaged Async-await issues that have been triaged during a working group meeting.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants