1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
use std::io::{Error, Result};
use std::os::unix::io::{AsRawFd, RawFd};
use std::pin::Pin;
use std::task::{Context, Poll};
use std::time::{Duration, Instant};
use futures_core::ready;
use timerfd::{SetTimeFlags, TimerFd as InnerTimerFd, TimerState};
use tokio::io::unix::AsyncFd;
use tokio::io::{AsyncRead, Interest, ReadBuf};
pub use timerfd::ClockId;
mod delay;
mod interval;
pub use delay::Delay;
pub use interval::Interval;
pub struct TimerFd(AsyncFd<InnerTimerFd>);
impl TimerFd {
pub fn new(clock: ClockId) -> std::io::Result<Self> {
let fd = InnerTimerFd::new_custom(clock, true, true)?;
let inner = AsyncFd::with_interest(fd, Interest::READABLE)?;
Ok(TimerFd(inner))
}
fn set_state(&mut self, state: TimerState, flags: SetTimeFlags) {
(self.0).get_mut().set_state(state, flags);
}
}
fn read_u64(fd: RawFd) -> Result<u64> {
let mut buf = [0u8; 8];
let rv = unsafe { libc::read(fd, buf.as_mut_ptr() as *mut _, 8) };
match rv {
len if len >= 0 => Ok(u64::from_ne_bytes(buf)),
_err => Err(Error::last_os_error()),
}
}
impl AsyncRead for TimerFd {
fn poll_read(
mut self: Pin<&mut Self>,
cx: &mut Context<'_>,
buf: &mut ReadBuf<'_>,
) -> Poll<Result<()>> {
let inner = self.as_mut();
let fd = inner.0.as_raw_fd();
loop {
let mut guard = ready!(inner.0.poll_read_ready(cx))?;
match guard.try_io(|_| read_u64(fd)) {
Ok(res) => {
let num = res?;
buf.put_slice(&num.to_ne_bytes());
break;
}
Err(_) => continue,
}
}
Poll::Ready(Ok(()))
}
}
pub fn sleep(duration: Duration) -> Delay {
Delay::new(Instant::now() + duration).expect("can't create delay")
}