pub struct HrTimer<T> {
#[pin]
timer: Opaque<bindings::hrtimer>,
- mode: HrTimerMode,
+ mode: bindings::hrtimer_mode,
_t: PhantomData<T>,
}
impl<T> HrTimer<T> {
/// Return an initializer for a new timer instance.
- pub fn new<U: ClockSource>(mode: HrTimerMode) -> impl PinInit<Self>
+ pub fn new<U: ClockSource, M: HrTimerMode>() -> impl PinInit<Self>
where
T: HrTimerCallback,
{
place,
Some(T::Pointer::run),
U::ID,
- mode.into_c(),
+ M::C_MODE,
);
}
}),
- mode: mode,
+ mode: M::C_MODE,
_t: PhantomData,
})
}
Self::c_timer_ptr(this).cast_mut(),
expires.to_ns(),
0,
- (*Self::raw_get_timer(this)).mode.into_c(),
+ (*Self::raw_get_timer(this)).mode,
);
}
}
}
/// Operational mode of [`HrTimer`].
-// NOTE: Some of these have the same encoding on the C side, so we keep
-// `repr(Rust)` and convert elsewhere.
-#[derive(Clone, Copy, PartialEq, Eq, Debug)]
-pub enum HrTimerMode {
- /// Timer expires at the given expiration time.
- Absolute,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- Relative,
- /// Timer does not move between CPU cores.
- Pinned,
- /// Timer handler is executed in soft irq context.
- Soft,
- /// Timer handler is executed in hard irq context.
- Hard,
- /// Timer expires at the given expiration time.
- /// Timer does not move between CPU cores.
- AbsolutePinned,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- /// Timer does not move between CPU cores.
- RelativePinned,
- /// Timer expires at the given expiration time.
- /// Timer handler is executed in soft irq context.
- AbsoluteSoft,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- /// Timer handler is executed in soft irq context.
- RelativeSoft,
- /// Timer expires at the given expiration time.
- /// Timer does not move between CPU cores.
- /// Timer handler is executed in soft irq context.
- AbsolutePinnedSoft,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- /// Timer does not move between CPU cores.
- /// Timer handler is executed in soft irq context.
- RelativePinnedSoft,
- /// Timer expires at the given expiration time.
- /// Timer handler is executed in hard irq context.
- AbsoluteHard,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- /// Timer handler is executed in hard irq context.
- RelativeHard,
- /// Timer expires at the given expiration time.
- /// Timer does not move between CPU cores.
- /// Timer handler is executed in hard irq context.
- AbsolutePinnedHard,
- /// Timer expires after the given expiration time interpreted as a duration from now.
- /// Timer does not move between CPU cores.
- /// Timer handler is executed in hard irq context.
- RelativePinnedHard,
+pub trait HrTimerMode {
+ /// The C representation of hrtimer mode.
+ const C_MODE: bindings::hrtimer_mode;
}
-impl HrTimerMode {
- fn into_c(self) -> bindings::hrtimer_mode {
- use bindings::*;
- match self {
- HrTimerMode::Absolute => hrtimer_mode_HRTIMER_MODE_ABS,
- HrTimerMode::Relative => hrtimer_mode_HRTIMER_MODE_REL,
- HrTimerMode::Pinned => hrtimer_mode_HRTIMER_MODE_PINNED,
- HrTimerMode::Soft => hrtimer_mode_HRTIMER_MODE_SOFT,
- HrTimerMode::Hard => hrtimer_mode_HRTIMER_MODE_HARD,
- HrTimerMode::AbsolutePinned => hrtimer_mode_HRTIMER_MODE_ABS_PINNED,
- HrTimerMode::RelativePinned => hrtimer_mode_HRTIMER_MODE_REL_PINNED,
- HrTimerMode::AbsoluteSoft => hrtimer_mode_HRTIMER_MODE_ABS_SOFT,
- HrTimerMode::RelativeSoft => hrtimer_mode_HRTIMER_MODE_REL_SOFT,
- HrTimerMode::AbsolutePinnedSoft => hrtimer_mode_HRTIMER_MODE_ABS_PINNED_SOFT,
- HrTimerMode::RelativePinnedSoft => hrtimer_mode_HRTIMER_MODE_REL_PINNED_SOFT,
- HrTimerMode::AbsoluteHard => hrtimer_mode_HRTIMER_MODE_ABS_HARD,
- HrTimerMode::RelativeHard => hrtimer_mode_HRTIMER_MODE_REL_HARD,
- HrTimerMode::AbsolutePinnedHard => hrtimer_mode_HRTIMER_MODE_ABS_PINNED_HARD,
- HrTimerMode::RelativePinnedHard => hrtimer_mode_HRTIMER_MODE_REL_PINNED_HARD,
- }
- }
+/// Timer that expires at a fixed point in time.
+pub struct AbsoluteMode;
+
+impl HrTimerMode for AbsoluteMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS;
+}
+
+/// Timer that expires after a delay from now.
+pub struct RelativeMode;
+
+impl HrTimerMode for RelativeMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL;
+}
+
+/// Timer with absolute expiration time, pinned to its current CPU.
+pub struct AbsolutePinnedMode;
+
+impl HrTimerMode for AbsolutePinnedMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS_PINNED;
+}
+
+/// Timer with relative expiration time, pinned to its current CPU.
+pub struct RelativePinnedMode;
+
+impl HrTimerMode for RelativePinnedMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL_PINNED;
+}
+
+/// Timer with absolute expiration, handled in soft irq context.
+pub struct AbsoluteSoftMode;
+
+impl HrTimerMode for AbsoluteSoftMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS_SOFT;
+}
+
+/// Timer with relative expiration, handled in soft irq context.
+pub struct RelativeSoftMode;
+
+impl HrTimerMode for RelativeSoftMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL_SOFT;
+}
+
+/// Timer with absolute expiration, pinned to CPU and handled in soft irq context.
+pub struct AbsolutePinnedSoftMode;
+
+impl HrTimerMode for AbsolutePinnedSoftMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS_PINNED_SOFT;
+}
+
+/// Timer with relative expiration, pinned to CPU and handled in soft irq context.
+pub struct RelativePinnedSoftMode;
+
+impl HrTimerMode for RelativePinnedSoftMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL_PINNED_SOFT;
+}
+
+/// Timer with absolute expiration, handled in hard irq context.
+pub struct AbsoluteHardMode;
+
+impl HrTimerMode for AbsoluteHardMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS_HARD;
+}
+
+/// Timer with relative expiration, handled in hard irq context.
+pub struct RelativeHardMode;
+
+impl HrTimerMode for RelativeHardMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL_HARD;
+}
+
+/// Timer with absolute expiration, pinned to CPU and handled in hard irq context.
+pub struct AbsolutePinnedHardMode;
+
+impl HrTimerMode for AbsolutePinnedHardMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_ABS_PINNED_HARD;
+}
+
+/// Timer with relative expiration, pinned to CPU and handled in hard irq context.
+pub struct RelativePinnedHardMode;
+
+impl HrTimerMode for RelativePinnedHardMode {
+ const C_MODE: bindings::hrtimer_mode = bindings::hrtimer_mode_HRTIMER_MODE_REL_PINNED_HARD;
}
/// Use to implement the [`HasHrTimer<T>`] trait.