diff options
Diffstat (limited to 'hw/mips_timer.c')
-rw-r--r-- | hw/mips_timer.c | 36 |
1 files changed, 22 insertions, 14 deletions
diff --git a/hw/mips_timer.c b/hw/mips_timer.c index e3beee8..8c32087 100644 --- a/hw/mips_timer.c +++ b/hw/mips_timer.c @@ -42,16 +42,6 @@ uint32_t cpu_mips_get_random (CPUState *env) } /* MIPS R4K timer */ -uint32_t cpu_mips_get_count (CPUState *env) -{ - if (env->CP0_Cause & (1 << CP0Ca_DC)) - return env->CP0_Count; - else - return env->CP0_Count + - (uint32_t)muldiv64(qemu_get_clock(vm_clock), - TIMER_FREQ, get_ticks_per_sec()); -} - static void cpu_mips_timer_update(CPUState *env) { uint64_t now, next; @@ -64,6 +54,27 @@ static void cpu_mips_timer_update(CPUState *env) qemu_mod_timer(env->timer, next); } +/* Expire the timer. */ +static void cpu_mips_timer_expire(CPUState *env) +{ + cpu_mips_timer_update(env); + if (env->insn_flags & ISA_MIPS32R2) { + env->CP0_Cause |= 1 << CP0Ca_TI; + } + qemu_irq_raise(env->irq[(env->CP0_IntCtl >> CP0IntCtl_IPTI) & 0x7]); +} + +uint32_t cpu_mips_get_count (CPUState *env) +{ + if (env->CP0_Cause & (1 << CP0Ca_DC)) { + return env->CP0_Count; + } else { + return env->CP0_Count + + (uint32_t)muldiv64(qemu_get_clock(vm_clock), + TIMER_FREQ, get_ticks_per_sec()); + } +} + void cpu_mips_store_count (CPUState *env, uint32_t count) { if (env->CP0_Cause & (1 << CP0Ca_DC)) @@ -116,11 +127,8 @@ static void mips_timer_cb (void *opaque) the comparator value. Offset the count by one to avoid immediately retriggering the callback before any virtual time has passed. */ env->CP0_Count++; - cpu_mips_timer_update(env); + cpu_mips_timer_expire(env); env->CP0_Count--; - if (env->insn_flags & ISA_MIPS32R2) - env->CP0_Cause |= 1 << CP0Ca_TI; - qemu_irq_raise(env->irq[(env->CP0_IntCtl >> CP0IntCtl_IPTI) & 0x7]); } void cpu_mips_clock_init (CPUState *env) |