You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
41 lines
1.7 KiB
41 lines
1.7 KiB
//! Mechanism to defer dropping of large objects to background threads
|
|
use super::*;
|
|
use futures::{
|
|
prelude::*,
|
|
future::OptionFuture,
|
|
};
|
|
|
|
pub const DEFER_DROP_VEC_SIZE_FLOOR: usize = 1024 * 1024; // 1 MB
|
|
|
|
/// Drop a `Vec<T>` that is `Send` and `'static`.
|
|
///
|
|
/// This will move the object to a background task if it is deemed nessisary.
|
|
/// # Note
|
|
/// This *must* be `await`ed to work properly. If you are not in an async context, use `drop_vec_sync`.
|
|
pub fn drop_vec<T>(vec: Vec<T>) -> impl Future<Output = ()> + 'static
|
|
where T: Send + 'static
|
|
{
|
|
let len_bytes = vec.len() * std::mem::size_of::<T>();
|
|
OptionFuture::from(if len_bytes > DEFER_DROP_VEC_SIZE_FLOOR {
|
|
cfg_eprintln!(Verbose; config::get_global(), "Size of vector ({} bytes, {} elements of {:?}) exceeds defer drop size floor {}. Moving vector to a seperate thread for de-allocation", len_bytes, vec.len(), std::any::type_name::<T>(), DEFER_DROP_VEC_SIZE_FLOOR);
|
|
Some(async move {
|
|
tokio::task::spawn_blocking(move || drop(vec)).await.expect("Child panic while dropping vector");
|
|
})
|
|
} else {
|
|
None
|
|
}).map(|_| ())
|
|
}
|
|
|
|
/// Drop a `Vec<T>` that is `Send` and `'static`.
|
|
///
|
|
/// This will move the object to a background task if it is deemed nessisary.
|
|
pub fn drop_vec_sync<T>(vec: Vec<T>)
|
|
where T: Send + 'static
|
|
{
|
|
let len_bytes = vec.len() * std::mem::size_of::<T>();
|
|
if len_bytes > DEFER_DROP_VEC_SIZE_FLOOR {
|
|
cfg_eprintln!(Verbose; config::get_global(), "Size of vector ({} bytes, {} elements of {:?}) exceeds defer drop size floor {}. Moving vector to a seperate thread for de-allocation", len_bytes, vec.len(), std::any::type_name::<T>(), DEFER_DROP_VEC_SIZE_FLOOR);
|
|
tokio::task::spawn_blocking(move || drop(vec));
|
|
}
|
|
}
|