* [PATCH v2 2/4] lib: sbi_timer: Introduce per-HART timer state
2026-04-25 10:40 [PATCH v2 0/4] Timer events for OpenSBI Anup Patel
2026-04-25 10:40 ` [PATCH v2 1/4] include: sbi: Add sbi_scratch_hartindex() macro Anup Patel
@ 2026-04-25 10:40 ` Anup Patel
2026-04-25 10:40 ` [PATCH v2 3/4] lib: sbi_timer: Add support for timer events Anup Patel
` (2 subsequent siblings)
4 siblings, 0 replies; 8+ messages in thread
From: Anup Patel @ 2026-04-25 10:40 UTC (permalink / raw)
To: Atish Patra
Cc: Andrew Jones, Samuel Holland, Anup Patel, opensbi, Anup Patel,
Nicholas Piggin
Currently, only time_delta is per-HART so introduce per-HART timer
state for having more per-HART timer information.
Signed-off-by: Anup Patel <anup.patel@oss.qualcomm.com>
Reviewed-by: Nicholas Piggin <npiggin@gmail.com>
---
lib/sbi/sbi_timer.c | 44 +++++++++++++++++++++++++-------------------
1 file changed, 25 insertions(+), 19 deletions(-)
diff --git a/lib/sbi/sbi_timer.c b/lib/sbi/sbi_timer.c
index 4088a597..9806c033 100644
--- a/lib/sbi/sbi_timer.c
+++ b/lib/sbi/sbi_timer.c
@@ -18,7 +18,11 @@
#include <sbi/sbi_scratch.h>
#include <sbi/sbi_timer.h>
-static unsigned long time_delta_off;
+struct timer_state {
+ u64 time_delta;
+};
+
+static unsigned long timer_state_off;
static u64 (*get_time_val)(void);
static const struct sbi_timer_device *timer_dev = NULL;
@@ -98,35 +102,37 @@ u64 sbi_timer_value(void)
u64 sbi_timer_virt_value(void)
{
- u64 *time_delta = sbi_scratch_offset_ptr(sbi_scratch_thishart_ptr(),
- time_delta_off);
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
- return sbi_timer_value() + *time_delta;
+ return sbi_timer_value() + tstate->time_delta;
}
u64 sbi_timer_get_delta(void)
{
- u64 *time_delta = sbi_scratch_offset_ptr(sbi_scratch_thishart_ptr(),
- time_delta_off);
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
- return *time_delta;
+ return tstate->time_delta;
}
void sbi_timer_set_delta(ulong delta)
{
- ulong *time_delta = sbi_scratch_offset_ptr(sbi_scratch_thishart_ptr(),
- time_delta_off);
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
- *time_delta = delta;
+#if __riscv_xlen == 32
+ tstate->time_delta &= ~0xffffffffUL;
+ tstate->time_delta |= (u32)delta;
+#else
+ tstate->time_delta = delta;
+#endif
}
#if __riscv_xlen == 32
void sbi_timer_set_delta_upper(ulong delta_upper)
{
- ulong *time_delta = sbi_scratch_offset_ptr(sbi_scratch_thishart_ptr(),
- time_delta_off);
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
- *(time_delta + 1) = delta_upper;
+ tstate->time_delta &= 0xffffffffUL;
+ tstate->time_delta |= (u64)delta << 32;
}
#endif
@@ -176,13 +182,13 @@ void sbi_timer_set_device(const struct sbi_timer_device *dev)
int sbi_timer_init(struct sbi_scratch *scratch, bool cold_boot)
{
- u64 *time_delta;
const struct sbi_platform *plat = sbi_platform_ptr(scratch);
+ struct timer_state *tstate;
int ret;
if (cold_boot) {
- time_delta_off = sbi_scratch_alloc_offset(sizeof(*time_delta));
- if (!time_delta_off)
+ timer_state_off = sbi_scratch_alloc_offset(sizeof(*tstate));
+ if (!timer_state_off)
return SBI_ENOMEM;
if (sbi_hart_has_csr(scratch, SBI_HART_CSR_TIME))
@@ -192,12 +198,12 @@ int sbi_timer_init(struct sbi_scratch *scratch, bool cold_boot)
if (ret)
return ret;
} else {
- if (!time_delta_off)
+ if (!timer_state_off)
return SBI_ENOMEM;
}
- time_delta = sbi_scratch_offset_ptr(scratch, time_delta_off);
- *time_delta = 0;
+ tstate = sbi_scratch_offset_ptr(scratch, timer_state_off);
+ tstate->time_delta = 0;
if (timer_dev && timer_dev->warm_init) {
ret = timer_dev->warm_init();
--
2.43.0
--
opensbi mailing list
opensbi@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/opensbi
^ permalink raw reply related [flat|nested] 8+ messages in thread* [PATCH v2 3/4] lib: sbi_timer: Add support for timer events
2026-04-25 10:40 [PATCH v2 0/4] Timer events for OpenSBI Anup Patel
2026-04-25 10:40 ` [PATCH v2 1/4] include: sbi: Add sbi_scratch_hartindex() macro Anup Patel
2026-04-25 10:40 ` [PATCH v2 2/4] lib: sbi_timer: Introduce per-HART timer state Anup Patel
@ 2026-04-25 10:40 ` Anup Patel
2026-04-29 8:18 ` Nicholas Piggin
2026-04-25 10:40 ` [PATCH v2 4/4] lib: sbi_timer: Introduce sbi_timer_compute_delta() and friends Anup Patel
2026-05-09 7:46 ` [PATCH v2 0/4] Timer events for OpenSBI Anup Patel
4 siblings, 1 reply; 8+ messages in thread
From: Anup Patel @ 2026-04-25 10:40 UTC (permalink / raw)
To: Atish Patra; +Cc: Andrew Jones, Samuel Holland, Anup Patel, opensbi, Anup Patel
Currently, the sbi_timer only supports timer events configured via
SBI calls. Introduce struct sbi_timer_event and related functions
to allow configuring timer events from any part of OpenSBI.
Signed-off-by: Anup Patel <anup.patel@oss.qualcomm.com>
---
include/sbi/sbi_timer.h | 65 +++++++++++-
lib/sbi/sbi_ecall_legacy.c | 4 +-
lib/sbi/sbi_ecall_time.c | 4 +-
lib/sbi/sbi_timer.c | 198 ++++++++++++++++++++++++++++++++++---
4 files changed, 248 insertions(+), 23 deletions(-)
diff --git a/include/sbi/sbi_timer.h b/include/sbi/sbi_timer.h
index 2e1a7879..914a5f12 100644
--- a/include/sbi/sbi_timer.h
+++ b/include/sbi/sbi_timer.h
@@ -10,7 +10,60 @@
#ifndef __SBI_TIMER_H__
#define __SBI_TIMER_H__
-#include <sbi/sbi_types.h>
+#include <sbi/sbi_list.h>
+
+/** Timer event re-start details */
+struct sbi_timer_event_restart {
+ /** Flag indicating whether event re-start is required */
+ bool required;
+ /** Next time stamp for event if re-start is required */
+ u64 next_event;
+};
+
+/** Timer event abstraction */
+struct sbi_timer_event {
+ /** List head for per-HART event list (Internal) */
+ struct sbi_dlist head;
+
+ /** Hart on which the event is started / running (Internal) */
+ int hart_index;
+
+ /** Time stamp when the event expires (Internal) */
+ u64 time_stamp;
+
+ /**
+ * Event callback to be called upon expiry.
+ *
+ * If the callback wants to re-start the event then
+ * it must update the event re-start details.
+ *
+ * NOTE: This will be called with the per-HART timer
+ * event list lock held.
+ */
+ void (*callback)(struct sbi_timer_event *ev,
+ struct sbi_timer_event_restart *restart);
+
+ /**
+ * Event cleanup to be called upon sbi_timer_exit()
+ *
+ * NOTE: This will be called with per-HART timer
+ * event list lock held.
+ */
+ void (*cleanup)(struct sbi_timer_event *ev);
+
+ /** Event specific private data */
+ void *priv;
+};
+
+#define SBI_INIT_TIMER_EVENT(__ptr, __callback, __cleanup, __priv) \
+do { \
+ SBI_INIT_LIST_HEAD(&(__ptr)->head); \
+ (__ptr)->hart_index = -1; \
+ (__ptr)->time_stamp = 0; \
+ (__ptr)->callback = (__callback); \
+ (__ptr)->cleanup = (__cleanup); \
+ (__ptr)->priv = (__priv); \
+} while (0)
/** Timer hardware device */
struct sbi_timer_device {
@@ -86,8 +139,14 @@ void sbi_timer_set_delta(ulong delta);
void sbi_timer_set_delta_upper(ulong delta_upper);
#endif
-/** Start timer event for current HART */
-void sbi_timer_event_start(u64 next_event);
+/** Start timer event on current HART */
+void sbi_timer_event_start(struct sbi_timer_event *ev, u64 next_event);
+
+/** Stop timer event on current HART */
+void sbi_timer_event_stop(struct sbi_timer_event *ev);
+
+/** Start supervisor timer event on current HART */
+void sbi_timer_smode_event_start(u64 next_event);
/** Process timer event for current HART */
void sbi_timer_process(void);
diff --git a/lib/sbi/sbi_ecall_legacy.c b/lib/sbi/sbi_ecall_legacy.c
index 50a7660d..4501c4ad 100644
--- a/lib/sbi/sbi_ecall_legacy.c
+++ b/lib/sbi/sbi_ecall_legacy.c
@@ -54,9 +54,9 @@ static int sbi_ecall_legacy_handler(unsigned long extid, unsigned long funcid,
switch (extid) {
case SBI_EXT_0_1_SET_TIMER:
#if __riscv_xlen == 32
- sbi_timer_event_start((((u64)regs->a1 << 32) | (u64)regs->a0));
+ sbi_timer_smode_event_start((((u64)regs->a1 << 32) | (u64)regs->a0));
#else
- sbi_timer_event_start((u64)regs->a0);
+ sbi_timer_smode_event_start((u64)regs->a0);
#endif
break;
case SBI_EXT_0_1_CONSOLE_PUTCHAR:
diff --git a/lib/sbi/sbi_ecall_time.c b/lib/sbi/sbi_ecall_time.c
index 6ea6f054..a0aa580d 100644
--- a/lib/sbi/sbi_ecall_time.c
+++ b/lib/sbi/sbi_ecall_time.c
@@ -22,9 +22,9 @@ static int sbi_ecall_time_handler(unsigned long extid, unsigned long funcid,
if (funcid == SBI_EXT_TIME_SET_TIMER) {
#if __riscv_xlen == 32
- sbi_timer_event_start((((u64)regs->a1 << 32) | (u64)regs->a0));
+ sbi_timer_smode_event_start((((u64)regs->a1 << 32) | (u64)regs->a0));
#else
- sbi_timer_event_start((u64)regs->a0);
+ sbi_timer_smode_event_start((u64)regs->a0);
#endif
} else
ret = SBI_ENOTSUPP;
diff --git a/lib/sbi/sbi_timer.c b/lib/sbi/sbi_timer.c
index 9806c033..4b16dbb2 100644
--- a/lib/sbi/sbi_timer.c
+++ b/lib/sbi/sbi_timer.c
@@ -10,9 +10,11 @@
#include <sbi/riscv_asm.h>
#include <sbi/riscv_barrier.h>
#include <sbi/riscv_encoding.h>
+#include <sbi/riscv_locks.h>
#include <sbi/sbi_console.h>
#include <sbi/sbi_error.h>
#include <sbi/sbi_hart.h>
+#include <sbi/sbi_hartmask.h>
#include <sbi/sbi_platform.h>
#include <sbi/sbi_pmu.h>
#include <sbi/sbi_scratch.h>
@@ -20,6 +22,9 @@
struct timer_state {
u64 time_delta;
+ spinlock_t event_list_lock;
+ struct sbi_dlist event_list;
+ struct sbi_timer_event smode_ev;
};
static unsigned long timer_state_off;
@@ -136,8 +141,130 @@ void sbi_timer_set_delta_upper(ulong delta_upper)
}
#endif
-void sbi_timer_event_start(u64 next_event)
+static void __sbi_timer_update_device(struct timer_state *tstate)
{
+ struct sbi_timer_event *ev;
+
+ if (!timer_dev)
+ return;
+
+ if (sbi_list_empty(&tstate->event_list)) {
+ if (timer_dev->timer_event_stop)
+ timer_dev->timer_event_stop();
+ csr_clear(CSR_MIE, MIP_MTIP);
+ } else {
+ ev = sbi_list_first_entry(&tstate->event_list, struct sbi_timer_event, head);
+ if (timer_dev->timer_event_start)
+ timer_dev->timer_event_start(ev->time_stamp);
+ csr_set(CSR_MIE, MIP_MTIP);
+ }
+}
+
+static void __sbi_timer_event_stop(struct sbi_timer_event *ev)
+{
+ if (ev->hart_index > -1) {
+ sbi_list_del(&ev->head);
+ ev->hart_index = -1;
+ }
+}
+
+static void __sbi_timer_event_start(struct timer_state *tstate,
+ struct sbi_timer_event *ev, u64 next_event)
+{
+ struct sbi_timer_event *tev, *next_ev = NULL;
+
+ /* Find where to insert the event in per-HART event list */
+ sbi_list_for_each_entry(tev, &tstate->event_list, head) {
+ if (next_event < tev->time_stamp) {
+ next_ev = tev;
+ break;
+ }
+ }
+
+ /* Insert the event in per-HART event list */
+ ev->hart_index = current_hartindex();
+ ev->time_stamp = next_event;
+ if (next_ev)
+ sbi_list_add(&ev->head, &next_ev->head);
+ else
+ sbi_list_add_tail(&ev->head, &tstate->event_list);
+}
+
+void sbi_timer_event_start(struct sbi_timer_event *ev, u64 next_event)
+{
+ struct timer_state *tstate;
+
+ if (!ev)
+ return;
+
+ /* Ensure that event is not on the per-HART event list */
+ if (ev->hart_index > -1) {
+ tstate = sbi_scratch_offset_ptr(sbi_hartindex_to_scratch(ev->hart_index),
+ timer_state_off);
+ spin_lock(&tstate->event_list_lock);
+ __sbi_timer_event_stop(ev);
+ spin_unlock(&tstate->event_list_lock);
+ }
+
+ tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
+ spin_lock(&tstate->event_list_lock);
+
+ __sbi_timer_event_start(tstate, ev, next_event);
+ __sbi_timer_update_device(tstate);
+
+ spin_unlock(&tstate->event_list_lock);
+}
+
+void sbi_timer_event_stop(struct sbi_timer_event *ev)
+{
+ struct timer_state *tstate;
+ int ev_hart_index;
+
+ if (!ev)
+ return;
+
+ /* Ensure that event is not on the per-HART event list */
+ ev_hart_index = ev->hart_index;
+ if (ev->hart_index > -1) {
+ tstate = sbi_scratch_offset_ptr(sbi_hartindex_to_scratch(ev->hart_index),
+ timer_state_off);
+ spin_lock(&tstate->event_list_lock);
+ __sbi_timer_event_stop(ev);
+ spin_unlock(&tstate->event_list_lock);
+ }
+
+ /* Re-program timer device on the current HART */
+ if (ev_hart_index == current_hartindex()) {
+ tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
+ spin_lock(&tstate->event_list_lock);
+ __sbi_timer_update_device(tstate);
+ spin_unlock(&tstate->event_list_lock);
+ }
+}
+
+static void sbi_timer_smode_event_callback(struct sbi_timer_event *ev,
+ struct sbi_timer_event_restart *restart)
+{
+ /*
+ * If sstc extension is available, supervisor can receive the timer
+ * directly without M-mode come in between. This function should
+ * only invoked if M-mode programs the timer for its own purpose.
+ */
+ if (!sbi_hart_has_extension(sbi_scratch_thishart_ptr(), SBI_HART_EXT_SSTC))
+ csr_set(CSR_MIP, MIP_STIP);
+}
+
+static void sbi_timer_smode_event_cleanup(struct sbi_timer_event *ev)
+{
+ if (!sbi_hart_has_extension(sbi_scratch_thishart_ptr(), SBI_HART_EXT_SSTC))
+ csr_clear(CSR_MIP, MIP_STIP);
+}
+
+void sbi_timer_smode_event_start(u64 next_event)
+{
+ struct timer_state *tstate = sbi_scratch_offset_ptr(sbi_scratch_thishart_ptr(),
+ timer_state_off);
+
sbi_pmu_ctr_incr_fw(SBI_PMU_FW_SET_TIMER);
/**
@@ -146,23 +273,47 @@ void sbi_timer_event_start(u64 next_event)
*/
if (sbi_hart_has_extension(sbi_scratch_thishart_ptr(), SBI_HART_EXT_SSTC)) {
csr_write64(CSR_STIMECMP, next_event);
- } else if (timer_dev && timer_dev->timer_event_start) {
- timer_dev->timer_event_start(next_event);
+ } else {
csr_clear(CSR_MIP, MIP_STIP);
+ sbi_timer_event_start(&tstate->smode_ev, next_event);
}
- csr_set(CSR_MIE, MIP_MTIP);
}
void sbi_timer_process(void)
{
- csr_clear(CSR_MIE, MIP_MTIP);
- /*
- * If sstc extension is available, supervisor can receive the timer
- * directly without M-mode come in between. This function should
- * only invoked if M-mode programs the timer for its own purpose.
- */
- if (!sbi_hart_has_extension(sbi_scratch_thishart_ptr(), SBI_HART_EXT_SSTC))
- csr_set(CSR_MIP, MIP_STIP);
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
+ struct sbi_timer_event_restart restart;
+ SBI_LIST_HEAD(restart_list);
+ struct sbi_timer_event *ev;
+
+ spin_lock(&tstate->event_list_lock);
+
+ while (!sbi_list_empty(&tstate->event_list)) {
+ ev = sbi_list_first_entry(&tstate->event_list, struct sbi_timer_event, head);
+ if (ev->time_stamp > sbi_timer_value())
+ break;
+
+ __sbi_timer_event_stop(ev);
+ if (ev->callback) {
+ restart.required = false;
+ restart.next_event = 0;
+ ev->callback(ev, &restart);
+ if (restart.required) {
+ ev->time_stamp = restart.next_event;
+ sbi_list_add_tail(&ev->head, &restart_list);
+ }
+ }
+ }
+
+ while (!sbi_list_empty(&restart_list)) {
+ ev = sbi_list_first_entry(&tstate->event_list, struct sbi_timer_event, head);
+ sbi_list_del(&ev->head);
+ __sbi_timer_event_start(tstate, ev, ev->time_stamp);
+ }
+
+ __sbi_timer_update_device(tstate);
+
+ spin_unlock(&tstate->event_list_lock);
}
const struct sbi_timer_device *sbi_timer_get_device(void)
@@ -204,6 +355,11 @@ int sbi_timer_init(struct sbi_scratch *scratch, bool cold_boot)
tstate = sbi_scratch_offset_ptr(scratch, timer_state_off);
tstate->time_delta = 0;
+ SPIN_LOCK_INIT(tstate->event_list_lock);
+ SBI_INIT_LIST_HEAD(&tstate->event_list);
+ SBI_INIT_TIMER_EVENT(&tstate->smode_ev,
+ sbi_timer_smode_event_callback,
+ sbi_timer_smode_event_cleanup, NULL);
if (timer_dev && timer_dev->warm_init) {
ret = timer_dev->warm_init();
@@ -216,9 +372,19 @@ int sbi_timer_init(struct sbi_scratch *scratch, bool cold_boot)
void sbi_timer_exit(struct sbi_scratch *scratch)
{
- if (timer_dev && timer_dev->timer_event_stop)
- timer_dev->timer_event_stop();
+ struct timer_state *tstate = sbi_scratch_thishart_offset_ptr(timer_state_off);
+ struct sbi_timer_event *ev;
+
+ spin_lock(&tstate->event_list_lock);
+
+ while (!sbi_list_empty(&tstate->event_list)) {
+ ev = sbi_list_first_entry(&tstate->event_list, struct sbi_timer_event, head);
+ __sbi_timer_event_stop(ev);
+ if (ev->cleanup)
+ ev->cleanup(ev);
+ }
+
+ __sbi_timer_update_device(tstate);
- csr_clear(CSR_MIP, MIP_STIP);
- csr_clear(CSR_MIE, MIP_MTIP);
+ spin_unlock(&tstate->event_list_lock);
}
--
2.43.0
--
opensbi mailing list
opensbi@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/opensbi
^ permalink raw reply related [flat|nested] 8+ messages in thread* [PATCH v2 4/4] lib: sbi_timer: Introduce sbi_timer_compute_delta() and friends
2026-04-25 10:40 [PATCH v2 0/4] Timer events for OpenSBI Anup Patel
` (2 preceding siblings ...)
2026-04-25 10:40 ` [PATCH v2 3/4] lib: sbi_timer: Add support for timer events Anup Patel
@ 2026-04-25 10:40 ` Anup Patel
2026-04-29 8:20 ` Nicholas Piggin
2026-05-09 7:46 ` [PATCH v2 0/4] Timer events for OpenSBI Anup Patel
4 siblings, 1 reply; 8+ messages in thread
From: Anup Patel @ 2026-04-25 10:40 UTC (permalink / raw)
To: Atish Patra; +Cc: Andrew Jones, Samuel Holland, Anup Patel, opensbi, Anup Patel
The users of timer event have to compute next_event (aka timer value
in the future) based on desired units and unit frequency. Introduce
sbi_timer_compute_delta() and friends to simplify computing next_event
for timer event users.
Signed-off-by: Anup Patel <anup.patel@oss.qualcomm.com>
---
include/sbi/sbi_timer.h | 27 +++++++++++++++++++++++++++
lib/sbi/sbi_timer.c | 14 ++++++++++----
2 files changed, 37 insertions(+), 4 deletions(-)
diff --git a/include/sbi/sbi_timer.h b/include/sbi/sbi_timer.h
index 914a5f12..2a040927 100644
--- a/include/sbi/sbi_timer.h
+++ b/include/sbi/sbi_timer.h
@@ -88,6 +88,21 @@ struct sbi_timer_device {
struct sbi_scratch;
+/** Compute timer value delta based on arbitary units */
+u64 sbi_timer_compute_delta(ulong units, u64 unit_freq);
+
+/** Compute timer value delta from milliseconds */
+static inline u64 sbi_timer_compute_mdelta(ulong msecs)
+{
+ return sbi_timer_compute_delta(msecs, 1000);
+}
+
+/** Compute timer value delta from microseconds */
+static inline u64 sbi_timer_compute_udelta(ulong usecs)
+{
+ return sbi_timer_compute_delta(usecs, 1000000);
+}
+
/** Generic delay loop of desired granularity */
void sbi_timer_delay_loop(ulong units, u64 unit_freq,
void (*delay_fn)(void *), void *opaque);
@@ -125,6 +140,18 @@ bool sbi_timer_waitms_until(bool (*predicate)(void *), void *arg,
/** Get timer value for current HART */
u64 sbi_timer_value(void);
+/** Compute timer value after specified milliseconds */
+static inline u64 sbi_timer_value_after_msecs(ulong msecs)
+{
+ return sbi_timer_value() + sbi_timer_compute_mdelta(msecs);
+}
+
+/** Compute timer value after specified microseconds */
+static inline u64 sbi_timer_value_after_usecs(ulong usecs)
+{
+ return sbi_timer_value() + sbi_timer_compute_udelta(usecs);
+}
+
/** Get virtualized timer value for current HART */
u64 sbi_timer_virt_value(void);
diff --git a/lib/sbi/sbi_timer.c b/lib/sbi/sbi_timer.c
index 4b16dbb2..ec25e5ce 100644
--- a/lib/sbi/sbi_timer.c
+++ b/lib/sbi/sbi_timer.c
@@ -58,6 +58,15 @@ static void nop_delay_fn(void *opaque)
cpu_relax();
}
+u64 sbi_timer_compute_delta(ulong units, u64 unit_freq)
+{
+ u64 delta;
+
+ delta = ((u64)timer_dev->timer_freq * (u64)units);
+ delta = delta / unit_freq;
+ return delta;
+}
+
void sbi_timer_delay_loop(ulong units, u64 unit_freq,
void (*delay_fn)(void *), void *opaque)
{
@@ -72,15 +81,12 @@ void sbi_timer_delay_loop(ulong units, u64 unit_freq,
/* Save starting timer value */
start_val = get_time_val();
- /* Compute desired timer value delta */
- delta = ((u64)timer_dev->timer_freq * (u64)units);
- delta = delta / unit_freq;
-
/* Use NOP delay function if delay function not available */
if (!delay_fn)
delay_fn = nop_delay_fn;
/* Busy loop until desired timer value delta reached */
+ delta = sbi_timer_compute_delta(units, unit_freq);
while ((get_time_val() - start_val) < delta)
delay_fn(opaque);
}
--
2.43.0
--
opensbi mailing list
opensbi@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/opensbi
^ permalink raw reply related [flat|nested] 8+ messages in thread