1 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
2 use crate::backend::c;
3 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
4 #[cfg(fix_y2038)]
5 use crate::timespec::LibcTimespec;
6 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
7 #[cfg(fix_y2038)]
8 use crate::timespec::Timespec;
9 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
10 use bitflags::bitflags;
11
12 /// `struct itimerspec` for use with [`timerfd_gettime`] and
13 /// [`timerfd_settime`].
14 ///
15 /// [`timerfd_gettime`]: crate::time::timerfd_gettime
16 /// [`timerfd_settime`]: crate::time::timerfd_settime
17 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
18 #[cfg(not(fix_y2038))]
19 pub type Itimerspec = c::itimerspec;
20
21 /// `struct itimerspec` for use with [`timerfd_gettime`] and
22 /// [`timerfd_settime`].
23 ///
24 /// [`timerfd_gettime`]: crate::time::timerfd_gettime
25 /// [`timerfd_settime`]: crate::time::timerfd_settime
26 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
27 #[cfg(fix_y2038)]
28 #[repr(C)]
29 #[derive(Debug, Clone)]
30 pub struct Itimerspec {
31 /// The interval of an interval timer.
32 pub it_interval: Timespec,
33 /// Time remaining in the current interval.
34 pub it_value: Timespec,
35 }
36
37 /// On most platforms, `LibcItimerspec` is just `Itimerspec`.
38 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
39 #[cfg(not(fix_y2038))]
40 pub(crate) type LibcItimerspec = Itimerspec;
41
42 /// On 32-bit glibc platforms, `LibcTimespec` differs from `Timespec`, so we
43 /// define our own struct, with bidirectional `From` impls.
44 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
45 #[cfg(fix_y2038)]
46 #[repr(C)]
47 #[derive(Debug, Clone)]
48 pub(crate) struct LibcItimerspec {
49 pub it_interval: LibcTimespec,
50 pub it_value: LibcTimespec,
51 }
52
53 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
54 #[cfg(fix_y2038)]
55 impl From<LibcItimerspec> for Itimerspec {
56 #[inline]
from(t: LibcItimerspec) -> Self57 fn from(t: LibcItimerspec) -> Self {
58 Self {
59 it_interval: t.it_interval.into(),
60 it_value: t.it_value.into(),
61 }
62 }
63 }
64
65 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
66 #[cfg(fix_y2038)]
67 impl From<Itimerspec> for LibcItimerspec {
68 #[inline]
from(t: Itimerspec) -> Self69 fn from(t: Itimerspec) -> Self {
70 Self {
71 it_interval: t.it_interval.into(),
72 it_value: t.it_value.into(),
73 }
74 }
75 }
76
77 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
78 bitflags! {
79 /// `TFD_*` flags for use with [`timerfd_create`].
80 ///
81 /// [`timerfd_create`]: crate::time::timerfd_create
82 #[repr(transparent)]
83 #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
84 pub struct TimerfdFlags: u32 {
85 /// `TFD_NONBLOCK`
86 #[doc(alias = "TFD_NONBLOCK")]
87 const NONBLOCK = bitcast!(c::TFD_NONBLOCK);
88
89 /// `TFD_CLOEXEC`
90 #[doc(alias = "TFD_CLOEXEC")]
91 const CLOEXEC = bitcast!(c::TFD_CLOEXEC);
92
93 /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
94 const _ = !0;
95 }
96 }
97
98 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
99 bitflags! {
100 /// `TFD_TIMER_*` flags for use with [`timerfd_settime`].
101 ///
102 /// [`timerfd_settime`]: crate::time::timerfd_settime
103 #[repr(transparent)]
104 #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
105 pub struct TimerfdTimerFlags: u32 {
106 /// `TFD_TIMER_ABSTIME`
107 #[doc(alias = "TFD_TIMER_ABSTIME")]
108 const ABSTIME = bitcast!(c::TFD_TIMER_ABSTIME);
109
110 /// `TFD_TIMER_CANCEL_ON_SET`
111 #[cfg(linux_kernel)]
112 #[doc(alias = "TFD_TIMER_CANCEL_ON_SET")]
113 const CANCEL_ON_SET = bitcast!(c::TFD_TIMER_CANCEL_ON_SET);
114
115 /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
116 const _ = !0;
117 }
118 }
119
120 /// `CLOCK_*` constants for use with [`timerfd_create`].
121 ///
122 /// [`timerfd_create`]: crate::time::timerfd_create
123 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
124 #[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
125 #[repr(u32)]
126 #[non_exhaustive]
127 pub enum TimerfdClockId {
128 /// `CLOCK_REALTIME`—A clock that tells the “real” time.
129 ///
130 /// This is a clock that tells the amount of time elapsed since the Unix
131 /// epoch, 1970-01-01T00:00:00Z. The clock is externally settable, so it is
132 /// not monotonic. Successive reads may see decreasing times, so it isn't
133 /// reliable for measuring durations.
134 #[doc(alias = "CLOCK_REALTIME")]
135 Realtime = bitcast!(c::CLOCK_REALTIME),
136
137 /// `CLOCK_MONOTONIC`—A clock that tells an abstract time.
138 ///
139 /// Unlike `Realtime`, this clock is not based on a fixed known epoch, so
140 /// individual times aren't meaningful. However, since it isn't settable,
141 /// it is reliable for measuring durations.
142 ///
143 /// This clock does not advance while the system is suspended; see
144 /// `Boottime` for a clock that does.
145 #[doc(alias = "CLOCK_MONOTONIC")]
146 Monotonic = bitcast!(c::CLOCK_MONOTONIC),
147
148 /// `CLOCK_BOOTTIME`—Like `Monotonic`, but advances while suspended.
149 ///
150 /// This clock is similar to `Monotonic`, but does advance while the system
151 /// is suspended.
152 #[doc(alias = "CLOCK_BOOTTIME")]
153 Boottime = bitcast!(c::CLOCK_BOOTTIME),
154
155 /// `CLOCK_REALTIME_ALARM`—Like `Realtime`, but wakes a suspended system.
156 ///
157 /// This clock is like `Realtime`, but can wake up a suspended system.
158 ///
159 /// Use of this clock requires the `CAP_WAKE_ALARM` Linux capability.
160 #[doc(alias = "CLOCK_REALTIME_ALARM")]
161 RealtimeAlarm = bitcast!(c::CLOCK_REALTIME_ALARM),
162
163 /// `CLOCK_BOOTTIME_ALARM`—Like `Boottime`, but wakes a suspended system.
164 ///
165 /// This clock is like `Boottime`, but can wake up a suspended system.
166 ///
167 /// Use of this clock requires the `CAP_WAKE_ALARM` Linux capability.
168 #[doc(alias = "CLOCK_BOOTTIME_ALARM")]
169 BoottimeAlarm = bitcast!(c::CLOCK_BOOTTIME_ALARM),
170 }
171
172 #[cfg(any(linux_kernel, target_os = "fuchsia"))]
173 #[test]
test_types()174 fn test_types() {
175 assert_eq_size!(TimerfdFlags, c::c_int);
176 assert_eq_size!(TimerfdTimerFlags, c::c_int);
177 }
178