async_hal/delay/
ready.rs

1use pin_project_lite::pin_project;
2
3use super::DelayMs;
4use core::{
5    pin::Pin,
6    task::{Context, Poll},
7};
8
9/// Create a timer that's ready as soon as it's started.
10/// ```
11/// use async_hal::delay::{self, DelayMs};
12///
13/// # let fut = async {
14/// let mut delay = delay::ready::<u8>();
15///
16/// // Ready instantly
17/// assert!(delay.delay_ms(100).await.is_ok());
18/// # };
19/// # futures::pin_mut!(fut);
20/// # async_hal::block_on(fut, || {});
21/// ```
22pub fn ready<D>() -> Ready<D> {
23    Ready { delay: None }
24}
25
26#[derive(Clone, Copy, PartialEq, Eq)]
27pub struct AlreadyStarted {
28    _priv: (),
29}
30
31pin_project! {
32    pub struct Ready<D> {
33        delay: Option<D>,
34    }
35}
36
37impl<D> DelayMs for Ready<D> {
38    type Delay = D;
39
40    type Error = AlreadyStarted;
41
42    fn start(&mut self, ms: Self::Delay) -> Result<(), Self::Error> {
43        self.delay = Some(ms);
44        Ok(())
45    }
46
47    fn poll_delay_ms(mut self: Pin<&mut Self>, _cx: &mut Context) -> Poll<Result<(), Self::Error>> {
48        if self.delay.take().is_some() {
49            Poll::Ready(Ok(()))
50        } else {
51            Poll::Ready(Err(AlreadyStarted { _priv: () }))
52        }
53    }
54
55    fn cancel(&mut self) -> Result<(), Self::Error> {
56        self.delay = None;
57        Ok(())
58    }
59}