Skip to content

Commit

Permalink
task: clarify what happens to spawned work during runtime shutdown (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
e00E committed Feb 9, 2023
1 parent d7d5d05 commit 061325b
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 23 deletions.
8 changes: 5 additions & 3 deletions tokio/src/runtime/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -156,9 +156,11 @@
//! multi-thread scheduler spawns threads to schedule tasks and for `spawn_blocking`
//! calls.
//!
//! While the `Runtime` is active, threads may shutdown after periods of being
//! idle. Once `Runtime` is dropped, all runtime threads are forcibly shutdown.
//! Any tasks that have not yet completed will be dropped.
//! While the `Runtime` is active, threads may shut down after periods of being
//! idle. Once `Runtime` is dropped, all runtime threads have usually been
//! terminated, but in the presence of unstoppable spawned work are not
//! guaranteed to have been terminated. See the
//! [struct level documentation](Runtime#shutdown) for more details.
//!
//! [tasks]: crate::task
//! [`Runtime`]: Runtime
Expand Down
46 changes: 26 additions & 20 deletions tokio/src/runtime/runtime.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,16 +24,29 @@ cfg_rt_multi_thread! {
///
/// # Shutdown
///
/// Shutting down the runtime is done by dropping the value. The current
/// thread will block until the shut down operation has completed.
/// Shutting down the runtime is done by dropping the value, or calling
/// [`Runtime::shutdown_background`] or [`Runtime::shutdown_timeout`].
///
/// * Drain any scheduled work queues.
/// * Drop any futures that have not yet completed.
/// * Drop the reactor.
/// Tasks spawned through [`Runtime::spawn`] keep running until they yield.
/// Then they are dropped. They are not *guaranteed* to run to completion, but
/// *might* do so if they do not yield until completion.
///
/// Once the reactor has dropped, any outstanding I/O resources bound to
/// that reactor will no longer function. Calling any method on them will
/// result in an error.
/// Blocking functions spawned through [`Runtime::spawn_blocking`] keep running
/// until they return.
///
/// The thread initiating the shutdown blocks until all spawned work has been
/// stopped. This can take an indefinite amount of time. The `Drop`
/// implementation waits forever for this.
///
/// `shutdown_background` and `shutdown_timeout` can be used if waiting forever
/// is undesired. When the timeout is reached, spawned work that did not stop
/// in time and threads running it are leaked. The work continues to run until
/// one of the stopping conditions is fulfilled, but the thread initiating the
/// shutdown is unblocked.
///
/// Once the runtime has been dropped, any outstanding I/O resources bound to
/// it will no longer function. Calling any method on them will result in an
/// error.
///
/// # Sharing
///
Expand Down Expand Up @@ -322,18 +335,9 @@ impl Runtime {
}

/// Shuts down the runtime, waiting for at most `duration` for all spawned
/// task to shutdown.
/// work to stop.
///
/// Usually, dropping a `Runtime` handle is sufficient as tasks are able to
/// shutdown in a timely fashion. However, dropping a `Runtime` will wait
/// indefinitely for all tasks to terminate, and there are cases where a long
/// blocking task has been spawned, which can block dropping `Runtime`.
///
/// In this case, calling `shutdown_timeout` with an explicit wait timeout
/// can work. The `shutdown_timeout` will signal all tasks to shutdown and
/// will wait for at most `duration` for all spawned tasks to terminate. If
/// `timeout` elapses before all tasks are dropped, the function returns and
/// outstanding tasks are potentially leaked.
/// See the [struct level documentation](Runtime#shutdown) for more details.
///
/// # Examples
///
Expand Down Expand Up @@ -362,7 +366,7 @@ impl Runtime {
self.blocking_pool.shutdown(Some(duration));
}

/// Shuts down the runtime, without waiting for any spawned tasks to shutdown.
/// Shuts down the runtime, without waiting for any spawned work to stop.
///
/// This can be useful if you want to drop a runtime from within another runtime.
/// Normally, dropping a runtime will block indefinitely for spawned blocking tasks
Expand All @@ -373,6 +377,8 @@ impl Runtime {
/// may result in a resource leak (in that any blocking tasks are still running until they
/// return.
///
/// See the [struct level documentation](Runtime#shutdown) for more details.
///
/// This function is equivalent to calling `shutdown_timeout(Duration::from_nanos(0))`.
///
/// ```
Expand Down

0 comments on commit 061325b

Please sign in to comment.