Timer should fire interrupt only if IT(interrupt enable) bit state of control register is enabled and timer should update IRQ status on IT bit change as it would mask/unmask the interrupt line.
Signed-off-by: Dmitry Osipenko <dig...@gmail.com> --- v2: Added missed IRQ status update on control register write as per Peter Crosthwaite comment. hw/timer/arm_mptimer.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/hw/timer/arm_mptimer.c b/hw/timer/arm_mptimer.c index 0e132b1..22fa46e 100644 --- a/hw/timer/arm_mptimer.c +++ b/hw/timer/arm_mptimer.c @@ -38,7 +38,7 @@ static inline int get_current_cpu(ARMMPTimerState *s) static inline void timerblock_update_irq(TimerBlock *tb) { - qemu_set_irq(tb->irq, tb->status); + qemu_set_irq(tb->irq, tb->status && (tb->control & 4)); } /* Return conversion factor from mpcore timer ticks to qemu timer ticks. */ @@ -122,6 +122,9 @@ static void timerblock_write(void *opaque, hwaddr addr, case 8: /* Control. */ old = tb->control; tb->control = value; + if ((old & 4) != (value & 4)) { + timerblock_update_irq(tb); + } if (value & 1) { if ((old & 1) && (tb->count != 0)) { /* Do nothing if timer is ticking right now. */ -- 2.4.4