Maybe a duplicate of #52924, but maybe also something else.
I observed that the sizes of Futures generated by async fns can grow exponentially.
The following code shows an async fn, which produces a 1kB future. Each layering in another async fn doubles it's size:
#![feature(async_await)]
async fn i_am_1kb() -> bool
{
let x: [u8; 1*1024] = [0; 1*1024];
async{}.await;
let _sum: u8 = x.iter().sum();
true
}
fn main() {
let fut1 = i_am_1kb();
dbg!(std::mem::size_of_val(&fut1));
let composed_1 = async {
let inner = i_am_1kb();
inner.await;
};
dbg!(std::mem::size_of_val(&composed_1));
let composed_2 = async {
let inner = i_am_1kb();
dbg!(std::mem::size_of_val(&inner));
inner.await;
};
dbg!(std::mem::size_of_val(&composed_2));
let composed_3 = async {
let inner = async {
let inner = async {
i_am_1kb().await;
};
dbg!(std::mem::size_of_val(&inner));
inner.await;
};
dbg!(std::mem::size_of_val(&inner));
inner.await;
};
dbg!(std::mem::size_of_val(&composed_3));
}
Output:
[src/main.rs:16] std::mem::size_of_val(&fut1) = 1032
[src/main.rs:22] std::mem::size_of_val(&composed_1) = 1036
[src/main.rs:29] std::mem::size_of_val(&composed_2) = 2072
[src/main.rs:44] std::mem::size_of_val(&composed_3) = 4168
It doesn't matter whether the statement between the future generation and await! references the future or not. A simply println("") will have the same effect.
Only if the future is directly awaited (as in composed_1) the size will stay constant.
cc @cramertj , @nikomatsakis , @Nemo157
Maybe a duplicate of #52924, but maybe also something else.
I observed that the sizes of
Futures generated by async fns can grow exponentially.The following code shows an async fn, which produces a 1kB future. Each layering in another async fn doubles it's size:
Output:
It doesn't matter whether the statement between the future generation and
await!references the future or not. A simplyprintln("")will have the same effect.Only if the future is directly awaited (as in
composed_1) the size will stay constant.cc @cramertj , @nikomatsakis , @Nemo157