-
Notifications
You must be signed in to change notification settings - Fork 653
Buffered stream losing Send
marker
#2636
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
Comments
Hmm, if the stream, future, and output are futures-rs/futures/tests/auto_traits.rs Lines 1117 to 1120 in 183f8c6
|
Yeah, hence why I completely fail to see how the compiler gets confused here, and why some combinations do work while some don't. Do you think it could be a rustc bug? |
Can be worked around with: use futures::stream::{empty, StreamExt};
use std::future::ready;
use std::sync::Arc;
fn send<T: Send>(_: T) {}
fn main() {
// send(async { empty().map(ready::<&()>).buffered(0).next().await });
let sem = Arc::new(tokio::sync::Semaphore::new(5));
send(async {
empty()
.map(ready::<&()>)
.map(|x| {
let sem = sem.clone();
async move {
// This must be `_permit` not just `_` otherwise the object is destroyed immediately.
// https://users.rust-lang.org/t/tokio-semaphore-mystery-acquire-vs-aquire-owned/79646/3
let _permit = sem.acquire().await.unwrap();
x
}
})
.next()
.await
});
println!("done");
} |
I ran into this issue today. I won't post a code example because it's not materially different than the one that @Tuetuopay posted, but I should point out that the same issue exists for It does seem like a rustc bug or at least a limitation of the current compiler, especially given the "could not prove" error message and the fact that it's not giving a concrete reason why the future is not Another workaround is if you call use futures::stream::{empty, StreamExt};
use std::future::ready;
fn send<T: Send>(_: T) {}
fn main() {
send(async {
empty().map(ready::<&()>).boxed().buffered(0).next().await
});
} |
@mikeyhew wait what? that actually works, including in my actual code that's much more complex than the example. thank you so much! With this it's more and more looks like a rustc bug, because the |
I just finished debugging a bunch of weird errors that ultimately was caused by this issue again — I must have forgotten to add the |
Closing in favor of the upstream issue. Thanks all for the investigation! |
Hi,
I hit a higher-ranked lifetime error when using buffered streams, where the compiler complains that it cannot prove the future consuming the stream are
Send
, despite the stream itself beingSend
.Resulting error:
Buffered is the key here, as dropping it to use
.then()
instead of.map()
+buffered()
compiles fine. This shows that the stream and its future is definitely send, and the buffering makes it weird. I cannot see which bound in theBuffered
struct/future makes the resulting stream!Send
.Obviously, I need
buffered
for parallelism of the futures, as they do some long-ish network calls; and theSend
requirement comes from Tonic's usage ofasync_trait
that requires futures to beSend
.Thanks!
The text was updated successfully, but these errors were encountered: