Commit c6d86a33d36891bd5090ea72134b9854d6811173

Authored by balrog
1 parent a4a771c0

sh4: Add IRL (4-bit encoded interrupt input) support (Takashi YOSHII).

This patch adds IRL(4bit encoded 15 level interrupt input) support
to SH using qemu_irq as a multi level (!=on/off) signal.

Signed-off-by: Takashi YOSHII <takasi-y@ops.dti.ne.jp>
Signed-off-by: Andrzej Zaborowski <andrew.zaborowski@intel.com>


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@5925 c046a42c-6fe2-441c-8c8c-71466251a162
@@ -42,6 +42,9 @@ void sh_serial_init (target_phys_addr_t base, int feat, @@ -42,6 +42,9 @@ void sh_serial_init (target_phys_addr_t base, int feat,
42 qemu_irq tei_source, 42 qemu_irq tei_source,
43 qemu_irq bri_source); 43 qemu_irq bri_source);
44 44
  45 +/* sh7750.c */
  46 +qemu_irq sh7750_irl(struct SH7750State *s);
  47 +
45 /* tc58128.c */ 48 /* tc58128.c */
46 int tc58128_init(struct SH7750State *s, const char *zone1, const char *zone2); 49 int tc58128_init(struct SH7750State *s, const char *zone1, const char *zone2);
47 50
hw/sh7750.c
@@ -412,7 +412,9 @@ enum { @@ -412,7 +412,9 @@ enum {
412 UNUSED = 0, 412 UNUSED = 0,
413 413
414 /* interrupt sources */ 414 /* interrupt sources */
415 - IRL0, IRL1, IRL2, IRL3, /* only IRLM mode supported */ 415 + IRL_0, IRL_1, IRL_2, IRL_3, IRL_4, IRL_5, IRL_6, IRL_7,
  416 + IRL_8, IRL_9, IRL_A, IRL_B, IRL_C, IRL_D, IRL_E,
  417 + IRL0, IRL1, IRL2, IRL3,
416 HUDI, GPIOI, 418 HUDI, GPIOI,
417 DMAC_DMTE0, DMAC_DMTE1, DMAC_DMTE2, DMAC_DMTE3, 419 DMAC_DMTE0, DMAC_DMTE1, DMAC_DMTE2, DMAC_DMTE3,
418 DMAC_DMTE4, DMAC_DMTE5, DMAC_DMTE6, DMAC_DMTE7, 420 DMAC_DMTE4, DMAC_DMTE5, DMAC_DMTE6, DMAC_DMTE7,
@@ -428,6 +430,8 @@ enum { @@ -428,6 +430,8 @@ enum {
428 430
429 /* interrupt groups */ 431 /* interrupt groups */
430 DMAC, PCIC1, TMU2, RTC, SCI1, SCIF, REF, 432 DMAC, PCIC1, TMU2, RTC, SCI1, SCIF, REF,
  433 + /* irl bundle */
  434 + IRL,
431 435
432 NR_SOURCES, 436 NR_SOURCES,
433 }; 437 };
@@ -529,6 +533,29 @@ static struct intc_group groups_pci[] = { @@ -529,6 +533,29 @@ static struct intc_group groups_pci[] = {
529 PCIC1_PCIDMA0, PCIC1_PCIDMA1, PCIC1_PCIDMA2, PCIC1_PCIDMA3), 533 PCIC1_PCIDMA0, PCIC1_PCIDMA1, PCIC1_PCIDMA2, PCIC1_PCIDMA3),
530 }; 534 };
531 535
  536 +static struct intc_vect vectors_irl[] = {
  537 + INTC_VECT(IRL_0, 0x200),
  538 + INTC_VECT(IRL_1, 0x220),
  539 + INTC_VECT(IRL_2, 0x240),
  540 + INTC_VECT(IRL_3, 0x260),
  541 + INTC_VECT(IRL_4, 0x280),
  542 + INTC_VECT(IRL_5, 0x2a0),
  543 + INTC_VECT(IRL_6, 0x2c0),
  544 + INTC_VECT(IRL_7, 0x2e0),
  545 + INTC_VECT(IRL_8, 0x300),
  546 + INTC_VECT(IRL_9, 0x320),
  547 + INTC_VECT(IRL_A, 0x340),
  548 + INTC_VECT(IRL_B, 0x360),
  549 + INTC_VECT(IRL_C, 0x380),
  550 + INTC_VECT(IRL_D, 0x3a0),
  551 + INTC_VECT(IRL_E, 0x3c0),
  552 +};
  553 +
  554 +static struct intc_group groups_irl[] = {
  555 + INTC_GROUP(IRL, IRL_0, IRL_1, IRL_2, IRL_3, IRL_4, IRL_5, IRL_6,
  556 + IRL_7, IRL_8, IRL_9, IRL_A, IRL_B, IRL_C, IRL_D, IRL_E),
  557 +};
  558 +
532 /********************************************************************** 559 /**********************************************************************
533 Memory mapped cache and TLB 560 Memory mapped cache and TLB
534 **********************************************************************/ 561 **********************************************************************/
@@ -718,5 +745,16 @@ SH7750State *sh7750_init(CPUSH4State * cpu) @@ -718,5 +745,16 @@ SH7750State *sh7750_init(CPUSH4State * cpu)
718 NULL, 0); 745 NULL, 0);
719 } 746 }
720 747
  748 + sh_intc_register_sources(&s->intc,
  749 + _INTC_ARRAY(vectors_irl),
  750 + _INTC_ARRAY(groups_irl));
721 return s; 751 return s;
722 } 752 }
  753 +
  754 +qemu_irq sh7750_irl(SH7750State *s)
  755 +{
  756 + sh_intc_toggle_source(sh_intc_source(&s->intc, IRL), 1, 0); /* enable */
  757 + return qemu_allocate_irqs(sh_intc_set_irl, sh_intc_source(&s->intc, IRL),
  758 + 1)[0];
  759 +}
  760 +
hw/sh_intc.c
@@ -465,3 +465,18 @@ int sh_intc_init(struct intc_desc *desc, @@ -465,3 +465,18 @@ int sh_intc_init(struct intc_desc *desc,
465 465
466 return 0; 466 return 0;
467 } 467 }
  468 +
  469 +/* Assert level <n> IRL interrupt.
  470 + 0:deassert. 1:lowest priority,... 15:highest priority. */
  471 +void sh_intc_set_irl(void *opaque, int n, int level)
  472 +{
  473 + struct intc_source *s = opaque;
  474 + int i, irl = level ^ 15;
  475 + for (i = 0; (s = sh_intc_source(s->parent, s->next_enum_id)); i++) {
  476 + if (i == irl)
  477 + sh_intc_toggle_source(s, s->enable_count?0:1, s->asserted?0:1);
  478 + else
  479 + if (s->asserted)
  480 + sh_intc_toggle_source(s, 0, -1);
  481 + }
  482 +}
hw/sh_intc.h
@@ -75,4 +75,6 @@ int sh_intc_init(struct intc_desc *desc, @@ -75,4 +75,6 @@ int sh_intc_init(struct intc_desc *desc,
75 struct intc_prio_reg *prio_regs, 75 struct intc_prio_reg *prio_regs,
76 int nr_prio_regs); 76 int nr_prio_regs);
77 77
  78 +void sh_intc_set_irl(void *opaque, int n, int level);
  79 +
78 #endif /* __SH_INTC_H__ */ 80 #endif /* __SH_INTC_H__ */