1 // Copyright 2020 The ChromiumOS Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 use std::time::Duration; 6 7 use base::Result as SysResult; 8 use base::Timer; 9 10 use crate::AsyncResult; 11 use crate::Error; 12 use crate::Executor; 13 use crate::IntoAsync; 14 use crate::IoSource; 15 16 /// An async version of base::Timer. 17 pub struct TimerAsync { 18 pub(crate) io_source: IoSource<Timer>, 19 } 20 21 impl TimerAsync { new(timer: Timer, ex: &Executor) -> AsyncResult<TimerAsync>22 pub fn new(timer: Timer, ex: &Executor) -> AsyncResult<TimerAsync> { 23 ex.async_from(timer) 24 .map(|io_source| TimerAsync { io_source }) 25 } 26 27 /// Gets the next value from the timer. 28 /// 29 /// NOTE: on Windows, this may return/wake early. See `base::Timer` docs 30 /// for details. next_val(&self) -> AsyncResult<u64>31 pub async fn next_val(&self) -> AsyncResult<u64> { 32 self.io_source.wait_for_handle().await 33 } 34 35 /// Async sleep for the given duration. 36 /// 37 /// NOTE: on Windows, this sleep may wake early. See `base::Timer` docs 38 /// for details. sleep(ex: &Executor, dur: Duration) -> std::result::Result<(), Error>39 pub async fn sleep(ex: &Executor, dur: Duration) -> std::result::Result<(), Error> { 40 let mut tfd = Timer::new().map_err(Error::Timer)?; 41 tfd.reset(dur, None).map_err(Error::Timer)?; 42 let t = TimerAsync::new(tfd, ex).map_err(Error::TimerAsync)?; 43 t.next_val().await.map_err(Error::TimerAsync)?; 44 Ok(()) 45 } 46 47 /// Sets the timer to expire after `dur`. If `interval` is not `None` and non-zero it 48 /// represents the period for repeated expirations after the initial expiration. Otherwise 49 /// the timer will expire just once. Cancels any existing duration and repeating interval. reset(&mut self, dur: Duration, interval: Option<Duration>) -> SysResult<()>50 pub fn reset(&mut self, dur: Duration, interval: Option<Duration>) -> SysResult<()> { 51 self.io_source.as_source_mut().reset(dur, interval) 52 } 53 54 /// Disarms the timer. clear(&mut self) -> SysResult<()>55 pub fn clear(&mut self) -> SysResult<()> { 56 self.io_source.as_source_mut().clear() 57 } 58 } 59 60 impl IntoAsync for Timer {} 61