summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLyude Paul <lyude@redhat.com>2025-08-21 15:32:43 -0400
committerAndreas Hindborg <a.hindborg@kernel.org>2025-09-04 16:54:39 +0200
commit3efb9ce91c5279d7ea73563d1fb136077f52dd2e (patch)
treeaeb1203e03e9d62597cca35b59dfbd57ea7b012a
parent0e2aab67f2d5716e8db73b6d0719208b44086ed5 (diff)
rust: hrtimer: Add HrTimer::raw_forward() and forward()
Within the hrtimer API there are quite a number of functions that can only be safely called from one of two contexts: * When we have exclusive access to the hrtimer and the timer is not active. * When we're within the hrtimer's callback context as it is being executed. This commit adds bindings for hrtimer_forward() for the first such context, along with HrTimer::raw_forward() for later use in implementing the hrtimer_forward() in the latter context. Signed-off-by: Lyude Paul <lyude@redhat.com> Reviewed-by: Daniel Almeida <daniel.almeida@collabora.com> Reviewed-by: Andreas Hindborg <a.hindborg@kernel.org> Link: https://lore.kernel.org/r/20250821193259.964504-4-lyude@redhat.com Signed-off-by: Andreas Hindborg <a.hindborg@kernel.org>
-rw-r--r--rust/kernel/time/hrtimer.rs40
1 files changed, 40 insertions, 0 deletions
diff --git a/rust/kernel/time/hrtimer.rs b/rust/kernel/time/hrtimer.rs
index be1bad4aacaa..79fed14b2d98 100644
--- a/rust/kernel/time/hrtimer.rs
+++ b/rust/kernel/time/hrtimer.rs
@@ -168,6 +168,46 @@ impl<T> HrTimer<T> {
// handled on the C side.
unsafe { bindings::hrtimer_cancel(c_timer_ptr) != 0 }
}
+
+ /// Forward the timer expiry for a given timer pointer.
+ ///
+ /// # Safety
+ ///
+ /// - `self_ptr` must point to a valid `Self`.
+ /// - The caller must either have exclusive access to the data pointed at by `self_ptr`, or be
+ /// within the context of the timer callback.
+ #[inline]
+ unsafe fn raw_forward(self_ptr: *mut Self, now: HrTimerInstant<T>, interval: Delta) -> u64
+ where
+ T: HasHrTimer<T>,
+ {
+ // SAFETY:
+ // * The C API requirements for this function are fulfilled by our safety contract.
+ // * `self_ptr` is guaranteed to point to a valid `Self` via our safety contract
+ unsafe {
+ bindings::hrtimer_forward(Self::raw_get(self_ptr), now.as_nanos(), interval.as_nanos())
+ }
+ }
+
+ /// Conditionally forward the timer.
+ ///
+ /// If the timer expires after `now`, this function does nothing and returns 0. If the timer
+ /// expired at or before `now`, this function forwards the timer by `interval` until the timer
+ /// expires after `now` and then returns the number of times the timer was forwarded by
+ /// `interval`.
+ ///
+ /// Returns the number of overruns that occurred as a result of the timer expiry change.
+ pub fn forward(self: Pin<&mut Self>, now: HrTimerInstant<T>, interval: Delta) -> u64
+ where
+ T: HasHrTimer<T>,
+ {
+ // SAFETY: `raw_forward` does not move `Self`
+ let this = unsafe { self.get_unchecked_mut() };
+
+ // SAFETY: By existence of `Pin<&mut Self>`, the pointer passed to `raw_forward` points to a
+ // valid `Self` that we have exclusive access to.
+ unsafe { Self::raw_forward(this, now, interval) }
+ }
}
/// Implemented by pointer types that point to structs that contain a [`HrTimer`].