use futures::future::pending; #[cfg(tokio_unstable)] use std::rc::Rc; use tokio::sync::mpsc; use tokio::task::LocalSet; use tokio_test::{assert_pending, assert_ready, task}; use tokio_util::task::TaskTracker;
for close_spot in0..=ITERS { let tracker = TaskTracker::new(); let tokens: Vec<_> = (0..ITERS).map(|_| tracker.token()).collect();
letmut wait = task::spawn(tracker.wait());
for (i, token) in tokens.into_iter().enumerate() {
assert_pending!(wait.poll()); if i == close_spot {
tracker.close();
assert_pending!(wait.poll());
}
drop(token);
}
if close_spot == ITERS {
assert_pending!(wait.poll());
tracker.close();
}
assert_ready!(wait.poll());
}
}
#[test] fn notify_many() { let tracker = TaskTracker::new();
#[cfg(tokio_unstable)] mod spawn_local { usesuper::*;
#[test] #[should_panic(
expected = "`spawn_local` called from outside of a `task::LocalSet` or `runtime::LocalRuntime`"
)] fn panic_outside_any_runtime() { let tracker = TaskTracker::new();
tracker.spawn_local(async {});
}
#[tokio::test(flavor = "multi_thread")] #[should_panic(
expected = "`spawn_local` called from outside of a `task::LocalSet` or `runtime::LocalRuntime`"
)] asyncfn panic_in_multi_thread_runtime() { let tracker = TaskTracker::new();
tracker.spawn_local(async {});
}
/// Spawn several tasks, and then close the [`TaskTracker`]. #[tokio::test(flavor = "local")] asyncfn spawn_then_close() { const N: usize = 8;
let tracker = TaskTracker::new();
for _ in0..N { let rc = Rc::new(());
tracker.spawn_local(asyncmove {
drop(rc);
});
}
#[cfg(tokio_unstable)] mod local_runtime { usesuper::*;
/// Spawn several tasks, and then close the [`TaskTracker`]. #[tokio::test(flavor = "local")] asyncfn spawn_then_close() { const N: usize = 8; let local_set = LocalSet::new();
let tracker = TaskTracker::new();
for _ in0..N { let rc = Rc::new(());
tracker.spawn_local_on( asyncmove {
drop(rc);
},
&local_set,
);
}
/// Spawn several pending-forever tasks, and then drop the [`TaskTracker`] /// while the `LocalSet` is already driven. #[tokio::test(flavor = "current_thread")] asyncfn spawn_then_drop() { const N: usize = 8; let local = LocalSet::new(); let tracker = TaskTracker::new(); let (tx, mut rx) = mpsc::unbounded_channel::<()>();
for _i in0..N { let tx = tx.clone();
tracker.spawn_local_on( asyncmove {
pending::<()>().await;
drop(tx);
},
&local,
);
}
drop(tx);
local
.run_until(asyncmove {
drop(tracker);
tokio::task::yield_now().await;
/// Close the tracker first, spawn several pending-forever tasks, /// then wait while the`LocalSet` is already driven. #[tokio::test(flavor = "current_thread")] asyncfn close_then_spawn() { const N: usize = 8; let local = LocalSet::new(); let tracker = TaskTracker::new();
tracker.close();
for _ in0..N { let rc = std::rc::Rc::new(());
tracker.spawn_local_on( asyncmove {
drop(rc);
},
&local,
);
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.