From 68a67a0ad29fc03c6b627c3ff31612514c11861e Mon Sep 17 00:00:00 2001 From: Axel Heider Date: Wed, 29 Nov 2023 21:14:56 +0100 Subject: [PATCH] wip debug QEMU reset issues --- src/arch/riscv/machine/hardware.c | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/src/arch/riscv/machine/hardware.c b/src/arch/riscv/machine/hardware.c index 1c1ba6cad5..c50491dde6 100644 --- a/src/arch/riscv/machine/hardware.c +++ b/src/arch/riscv/machine/hardware.c @@ -220,16 +220,24 @@ static inline void ackInterrupt(irq_t irq) #ifndef CONFIG_KERNEL_MCS void resetTimer(void) { - assert(TIMER_CLOCK_HZ > 1000000); /* timer must be > 1 MHz */ + /* timer must be > 1 kHz */ + SEL4_COMPILE_ASSERT(timer_clock_1mhz, TIMER_CLOCK_HZ > 1000); const uint64_t ticks_per_ms = TIMER_CLOCK_HZ / MS_IN_S; const uint64_t delta = ticks_per_ms * CONFIG_TIMER_TICK_MS; - uint64_t target; - // repeatedly try and set the timer in a loop as otherwise there is a race and we - // may set a timeout in the past, resulting in it never getting triggered - do { - target = riscv_read_time() + delta; - sbi_set_timer(target); - } while (riscv_read_time() > target); + uint64_t target = riscv_read_time() + delta; + sbi_set_timer(target); +#if defined(CONFIG_PLAT_QEMU_RISCV_VIRT) || defined(CONFIG_PLAT_SPIKE) + /* Perform a sanity check that the margin is big enough that we end up + * with a timestamp in the future. Seems it happened in QEMU that the + * simulation was too slow. + */ + uint64_t now = riscv_read_time(); + if (likely(now >= target)) { + printf("Timer reset failed, %"PRIu64" (now) >= %"PRIu64"\n", now, target); + fail("Timer reset failed"); + UNREACHABLE(); + } +#endif } /**