[][src]Module async_io::parking

Thread parking and unparking.

This module exposes the exact same API as parking. The only difference is that Parker in this module will wait on epoll/kqueue/wepoll and wake tasks blocked on I/O or timers.

Executors may use this mechanism to go to sleep when idle and wake up when more work is scheduled. By waking tasks blocked on I/O and then running those tasks on the same thread, no thread context switch is necessary when going between task execution and I/O.

You can treat this module as merely an optimization over the parking crate.

Examples

A simple block_on() that runs a single future and waits on I/O:

use std::future::Future;
use std::task::{Context, Poll};

use futures_lite::{future, pin};
use waker_fn::waker_fn;

// Blocks on a future to complete, waiting on I/O when idle.
fn block_on<T>(future: impl Future<Output = T>) -> T {
    // Create a waker that notifies through I/O when done.
    let (p, u) = parking::pair();
    let waker = waker_fn(move || u.unpark());
    let cx = &mut Context::from_waker(&waker);

    pin!(future);
    loop {
        match future.as_mut().poll(cx) {
            Poll::Ready(t) => return t, // Done!
            Poll::Pending => p.park(),  // Wait for an I/O event.
        }
    }
}

block_on(async {
    println!("Hello world!");
    future::yield_now().await;
    println!("Hello again!");
});

Structs

Parker

Waits for a notification.

Unparker

Notifies a parker.

Functions

pair

Creates a parker and an associated unparker.