Revision 703243a0
b/hw/sh.h | ||
---|---|---|
2 | 2 |
#define QEMU_SH_H |
3 | 3 |
/* Definitions for SH board emulation. */ |
4 | 4 |
|
5 |
#include "sh_intc.h" |
|
6 |
|
|
5 | 7 |
/* sh7750.c */ |
6 | 8 |
struct SH7750State; |
7 | 9 |
|
... | ... | |
25 | 27 |
#define TMU012_FEAT_TOCR (1 << 0) |
26 | 28 |
#define TMU012_FEAT_3CHAN (1 << 1) |
27 | 29 |
#define TMU012_FEAT_EXTCLK (1 << 2) |
28 |
void tmu012_init(uint32_t base, int feat, uint32_t freq); |
|
30 |
void tmu012_init(target_phys_addr_t base, int feat, uint32_t freq, |
|
31 |
struct intc_source *ch0_irq, struct intc_source *ch1_irq, |
|
32 |
struct intc_source *ch2_irq0, struct intc_source *ch2_irq1); |
|
33 |
|
|
29 | 34 |
|
30 | 35 |
/* sh_serial.c */ |
31 | 36 |
#define SH_SERIAL_FEAT_SCIF (1 << 0) |
b/hw/sh7750.c | ||
---|---|---|
559 | 559 |
|
560 | 560 |
tmu012_init(0x1fd80000, |
561 | 561 |
TMU012_FEAT_TOCR | TMU012_FEAT_3CHAN | TMU012_FEAT_EXTCLK, |
562 |
s->periph_freq); |
|
563 |
|
|
562 |
s->periph_freq, |
|
563 |
sh_intc_source(&s->intc, TMU0), |
|
564 |
sh_intc_source(&s->intc, TMU1), |
|
565 |
sh_intc_source(&s->intc, TMU2_TUNI), |
|
566 |
sh_intc_source(&s->intc, TMU2_TICPI)); |
|
564 | 567 |
|
565 | 568 |
if (cpu_model & (SH_CPU_SH7750 | SH_CPU_SH7750S | SH_CPU_SH7751)) { |
566 | 569 |
sh_intc_register_sources(&s->intc, |
... | ... | |
578 | 581 |
sh_intc_register_sources(&s->intc, |
579 | 582 |
_INTC_ARRAY(vectors_tmu34), |
580 | 583 |
NULL, 0); |
581 |
tmu012_init(0x1e100000, 0, s->periph_freq); |
|
584 |
tmu012_init(0x1e100000, 0, s->periph_freq, |
|
585 |
sh_intc_source(&s->intc, TMU3), |
|
586 |
sh_intc_source(&s->intc, TMU4), |
|
587 |
NULL, NULL); |
|
582 | 588 |
} |
583 | 589 |
|
584 | 590 |
if (cpu_model & (SH_CPU_SH7751_ALL)) { |
b/hw/sh_timer.c | ||
---|---|---|
33 | 33 |
uint32_t tcpr; |
34 | 34 |
int freq; |
35 | 35 |
int int_level; |
36 |
int old_level; |
|
36 | 37 |
int feat; |
37 | 38 |
int enabled; |
38 |
qemu_irq irq;
|
|
39 |
struct intc_source *irq;
|
|
39 | 40 |
} sh_timer_state; |
40 | 41 |
|
41 | 42 |
/* Check all active timers, and schedule the next timer interrupt. */ |
42 | 43 |
|
43 | 44 |
static void sh_timer_update(sh_timer_state *s) |
44 | 45 |
{ |
45 |
#if 0 /* not yet */ |
|
46 |
/* Update interrupts. */ |
|
47 |
if (s->int_level && (s->tcr & TIMER_TCR_UNIE)) { |
|
48 |
qemu_irq_raise(s->irq); |
|
49 |
} else { |
|
50 |
qemu_irq_lower(s->irq); |
|
51 |
} |
|
52 |
#endif |
|
46 |
int new_level = s->int_level && (s->tcr & TIMER_TCR_UNIE); |
|
47 |
|
|
48 |
if (new_level != s->old_level) |
|
49 |
sh_intc_toggle_source(s->irq, 0, new_level ? 1 : -1); |
|
50 |
|
|
51 |
s->old_level = s->int_level; |
|
52 |
s->int_level = new_level; |
|
53 | 53 |
} |
54 | 54 |
|
55 | 55 |
static uint32_t sh_timer_read(void *opaque, target_phys_addr_t offset) |
... | ... | |
185 | 185 |
sh_timer_update(s); |
186 | 186 |
} |
187 | 187 |
|
188 |
static void *sh_timer_init(uint32_t freq, int feat) |
|
188 |
static void *sh_timer_init(uint32_t freq, int feat, struct intc_source *irq)
|
|
189 | 189 |
{ |
190 | 190 |
sh_timer_state *s; |
191 | 191 |
QEMUBH *bh; |
... | ... | |
198 | 198 |
s->tcpr = 0xdeadbeef; |
199 | 199 |
s->tcor = 0; |
200 | 200 |
s->enabled = 0; |
201 |
s->irq = irq; |
|
201 | 202 |
|
202 | 203 |
bh = qemu_bh_new(sh_timer_tick, s); |
203 | 204 |
s->timer = ptimer_init(bh); |
... | ... | |
305 | 306 |
tmu012_write |
306 | 307 |
}; |
307 | 308 |
|
308 |
void tmu012_init(uint32_t base, int feat, uint32_t freq) |
|
309 |
void tmu012_init(target_phys_addr_t base, int feat, uint32_t freq, |
|
310 |
struct intc_source *ch0_irq, struct intc_source *ch1_irq, |
|
311 |
struct intc_source *ch2_irq0, struct intc_source *ch2_irq1) |
|
309 | 312 |
{ |
310 | 313 |
int iomemtype; |
311 | 314 |
tmu012_state *s; |
... | ... | |
314 | 317 |
s = (tmu012_state *)qemu_mallocz(sizeof(tmu012_state)); |
315 | 318 |
s->base = base; |
316 | 319 |
s->feat = feat; |
317 |
s->timer[0] = sh_timer_init(freq, timer_feat); |
|
318 |
s->timer[1] = sh_timer_init(freq, timer_feat); |
|
320 |
s->timer[0] = sh_timer_init(freq, timer_feat, ch0_irq);
|
|
321 |
s->timer[1] = sh_timer_init(freq, timer_feat, ch1_irq);
|
|
319 | 322 |
if (feat & TMU012_FEAT_3CHAN) |
320 |
s->timer[2] = sh_timer_init(freq, timer_feat | TIMER_FEAT_CAPT); |
|
323 |
s->timer[2] = sh_timer_init(freq, timer_feat | TIMER_FEAT_CAPT, |
|
324 |
ch2_irq0); /* ch2_irq1 not supported */ |
|
321 | 325 |
iomemtype = cpu_register_io_memory(0, tmu012_readfn, |
322 | 326 |
tmu012_writefn, s); |
323 | 327 |
cpu_register_physical_memory(base, 0x00001000, iomemtype); |
Also available in: Unified diff