use crate::{
ManualMonotonicClock,
MonotonicInstant,
TimeError,
};
use std::future::Future;
use std::pin::Pin;
use std::sync::Arc;
use std::task::{
Context,
Poll,
};
pub(crate) struct ManualTimerFuture {
clock: Arc<ManualMonotonicClock>,
waiter_id: Option<u64>,
}
impl ManualTimerFuture {
pub(crate) fn register(
clock: Arc<ManualMonotonicClock>,
deadline: MonotonicInstant,
) -> Result<Self, TimeError> {
let waiter_id = clock.register_timer_waiter(deadline)?;
Ok(Self { clock, waiter_id })
}
}
impl Future for ManualTimerFuture {
type Output = Result<(), TimeError>;
fn poll(
self: Pin<&mut Self>,
context: &mut Context<'_>,
) -> Poll<Self::Output> {
let this = self.get_mut();
let Some(waiter_id) = this.waiter_id else {
return Poll::Ready(Ok(()));
};
let result = this.clock.poll_timer_waiter(waiter_id, context);
if result.is_ready() {
this.waiter_id = None;
}
result.map(Ok)
}
}
impl Drop for ManualTimerFuture {
#[inline]
fn drop(&mut self) {
if let Some(waiter_id) = self.waiter_id.take() {
self.clock.unregister_timer_waiter(waiter_id);
}
}
}