mirror of https://github.com/xemu-project/xemu.git
ARMv7-M SysTick fix.
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@3727 c046a42c-6fe2-441c-8c8c-71466251a162
This commit is contained in:
parent
aae9366a03
commit
e57ec0168c
|
@ -27,6 +27,7 @@ void arm_load_kernel(CPUState *env, int ram_size, const char *kernel_filename,
|
||||||
int board_id, target_phys_addr_t loader_start);
|
int board_id, target_phys_addr_t loader_start);
|
||||||
|
|
||||||
/* armv7m_nvic.c */
|
/* armv7m_nvic.c */
|
||||||
|
int system_clock_scale;
|
||||||
qemu_irq *armv7m_nvic_init(CPUState *env);
|
qemu_irq *armv7m_nvic_init(CPUState *env);
|
||||||
|
|
||||||
#endif /* !ARM_MISC_H */
|
#endif /* !ARM_MISC_H */
|
||||||
|
|
|
@ -638,7 +638,7 @@ static void gic_reset(gic_state *s)
|
||||||
s->cpu_enabled[i] = 0;
|
s->cpu_enabled[i] = 0;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
for (i = 0; i < 15; i++) {
|
for (i = 0; i < 16; i++) {
|
||||||
GIC_SET_ENABLED(i);
|
GIC_SET_ENABLED(i);
|
||||||
GIC_SET_TRIGGER(i);
|
GIC_SET_TRIGGER(i);
|
||||||
}
|
}
|
||||||
|
|
|
@ -48,14 +48,15 @@ typedef struct {
|
||||||
#define SYSTICK_CLKSOURCE (1 << 2)
|
#define SYSTICK_CLKSOURCE (1 << 2)
|
||||||
#define SYSTICK_COUNTFLAG (1 << 16)
|
#define SYSTICK_COUNTFLAG (1 << 16)
|
||||||
|
|
||||||
/* Conversion factor from qemu timer to SysTick frequencies.
|
/* Multiplication factor to convert from system clock ticks to qemu timer
|
||||||
QEMU uses a base of 1GHz, so these give 20MHz and 1MHz for core and
|
ticks. */
|
||||||
reference frequencies. */
|
int system_clock_scale;
|
||||||
|
|
||||||
|
/* Conversion factor from qemu timer to SysTick frequencies. */
|
||||||
static inline int64_t systick_scale(nvic_state *s)
|
static inline int64_t systick_scale(nvic_state *s)
|
||||||
{
|
{
|
||||||
if (s->systick.control & SYSTICK_CLKSOURCE)
|
if (s->systick.control & SYSTICK_CLKSOURCE)
|
||||||
return 50;
|
return system_clock_scale;
|
||||||
else
|
else
|
||||||
return 1000;
|
return 1000;
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,10 +42,6 @@ typedef const struct {
|
||||||
|
|
||||||
/* General purpose timer module. */
|
/* General purpose timer module. */
|
||||||
|
|
||||||
/* Multiplication factor to convert from GPTM timer ticks to qemu timer
|
|
||||||
ticks. */
|
|
||||||
static int stellaris_clock_scale;
|
|
||||||
|
|
||||||
typedef struct gptm_state {
|
typedef struct gptm_state {
|
||||||
uint32_t config;
|
uint32_t config;
|
||||||
uint32_t mode[2];
|
uint32_t mode[2];
|
||||||
|
@ -90,7 +86,7 @@ static void gptm_reload(gptm_state *s, int n, int reset)
|
||||||
/* 32-bit CountDown. */
|
/* 32-bit CountDown. */
|
||||||
uint32_t count;
|
uint32_t count;
|
||||||
count = s->load[0] | (s->load[1] << 16);
|
count = s->load[0] | (s->load[1] << 16);
|
||||||
tick += (int64_t)count * stellaris_clock_scale;
|
tick += (int64_t)count * system_clock_scale;
|
||||||
} else if (s->config == 1) {
|
} else if (s->config == 1) {
|
||||||
/* 32-bit RTC. 1Hz tick. */
|
/* 32-bit RTC. 1Hz tick. */
|
||||||
tick += ticks_per_sec;
|
tick += ticks_per_sec;
|
||||||
|
@ -480,7 +476,7 @@ static void ssys_write(void *opaque, target_phys_addr_t offset, uint32_t value)
|
||||||
s->int_status |= (1 << 6);
|
s->int_status |= (1 << 6);
|
||||||
}
|
}
|
||||||
s->rcc = value;
|
s->rcc = value;
|
||||||
stellaris_clock_scale = 5 * (((s->rcc >> 23) & 0xf) + 1);
|
system_clock_scale = 5 * (((s->rcc >> 23) & 0xf) + 1);
|
||||||
break;
|
break;
|
||||||
case 0x100: /* RCGC0 */
|
case 0x100: /* RCGC0 */
|
||||||
s->rcgc[0] = value;
|
s->rcgc[0] = value;
|
||||||
|
|
Loading…
Reference in New Issue