diff options
author | Magnus Damm <damm@igel.co.jp> | 2007-06-15 18:56:19 +0900 |
---|---|---|
committer | Paul Mundt <lethal@linux-sh.org> | 2007-06-15 18:56:19 +0900 |
commit | 68abdbbb03476a60d932eeba0035dd5069afec38 (patch) | |
tree | de3854f76d6d9aec121c432a3cd276bb756003c9 /arch/sh/boards/se | |
parent | 50f63f2518ee68bc132d357d2b6fdb7f60ef79e0 (diff) |
sh: rework ipr code
This patch reworks the ipr code by grouping the offset array together
with the ipr_data structure in a new data structure called ipr_desc.
This new structure also contains the name of the controller in struct
irq_chip. The idea behind putting struct irq_chip in there is that we
can use offsetof() to locate the base addresses in the irq_chip
callbacks. This strategy has much in common with the recently merged
intc2 code.
One logic change has been made - the original ipr code enabled the
interrupts by default but with this patch they are all disabled by
default.
Signed-off-by: Magnus Damm <damm@igel.co.jp>
Signed-off-by: Paul Mundt <lethal@linux-sh.org>
Diffstat (limited to 'arch/sh/boards/se')
-rw-r--r-- | arch/sh/boards/se/770x/irq.c | 124 | ||||
-rw-r--r-- | arch/sh/boards/se/7722/irq.c | 15 | ||||
-rw-r--r-- | arch/sh/boards/se/7751/irq.c | 59 |
3 files changed, 88 insertions, 110 deletions
diff --git a/arch/sh/boards/se/770x/irq.c b/arch/sh/boards/se/770x/irq.c index c8eccff77a0..cdb0807928a 100644 --- a/arch/sh/boards/se/770x/irq.c +++ b/arch/sh/boards/se/770x/irq.c @@ -15,46 +15,7 @@ #include <asm/io.h> #include <asm/se.h> -/* - * If the problem of make_ipr_irq is solved, - * this code will become unnecessary. :-) - */ -static void se770x_disable_ipr_irq(unsigned int irq) -{ - struct ipr_data *p = get_irq_chip_data(irq); - - ctrl_outw(ctrl_inw(p->addr) & (0xffff ^ (0xf << p->shift)), p->addr); -} - -static void se770x_enable_ipr_irq(unsigned int irq) -{ - struct ipr_data *p = get_irq_chip_data(irq); - - ctrl_outw(ctrl_inw(p->addr) | (p->priority << p->shift), p->addr); -} - -static struct irq_chip se770x_irq_chip = { - .name = "MS770xSE-FPGA", - .mask = se770x_disable_ipr_irq, - .unmask = se770x_enable_ipr_irq, - .mask_ack = se770x_disable_ipr_irq, -}; - -void make_se770x_irq(struct ipr_data *table, unsigned int nr_irqs) -{ - int i; - - for (i = 0; i < nr_irqs; i++) { - unsigned int irq = table[i].irq; - disable_irq_nosync(irq); - set_irq_chip_and_handler_name(irq, &se770x_irq_chip, - handle_level_irq, "level"); - set_irq_chip_data(irq, &table[i]); - se770x_enable_ipr_irq(irq); - } -} - -static struct ipr_data se770x_ipr_map[] = { +static struct ipr_data ipr_irq_table[] = { /* * Super I/O (Just mimic PC): * 1: keyboard @@ -68,46 +29,67 @@ static struct ipr_data se770x_ipr_map[] = { */ #if defined(CONFIG_CPU_SUBTYPE_SH7705) /* This is default value */ - { 13, 0, 8, 0x0f-13 ,BCR_ILCRA}, - { 5 , 0, 4, 0x0f- 5 ,BCR_ILCRA}, - { 10, 0, 0, 0x0f-10, BCR_ILCRB}, - { 7 , 0, 4, 0x0f- 7, BCR_ILCRC}, - { 3 , 0, 0, 0x0f- 3, BCR_ILCRC}, - { 1 , 0, 12, 0x0f- 1, BCR_ILCRD}, - { 12, 0, 4, 0x0f-12, BCR_ILCRD}, /* LAN */ - { 2 , 0, 8, 0x0f- 2, BCR_ILCRE}, /* PCIRQ2 */ - { 6 , 0, 4, 0x0f- 6, BCR_ILCRE}, /* PCIRQ1 */ - { 14, 0, 0, 0x0f-14, BCR_ILCRE}, /* PCIRQ0 */ - { 0 , 0, 12, 0x0f , BCR_ILCRF}, - { 4 , 0, 4, 0x0f- 4, BCR_ILCRF}, - { 8 , 0, 12, 0x0f- 8, BCR_ILCRG}, - { 9 , 0, 8, 0x0f- 9, BCR_ILCRG}, - { 11, 0, 4, 0x0f-11, BCR_ILCRG}, + { 13, 0, 8, 0x0f-13, }, + { 5 , 0, 4, 0x0f- 5, }, + { 10, 1, 0, 0x0f-10, }, + { 7 , 2, 4, 0x0f- 7, }, + { 3 , 2, 0, 0x0f- 3, }, + { 1 , 3, 12, 0x0f- 1, }, + { 12, 3, 4, 0x0f-12, }, /* LAN */ + { 2 , 4, 8, 0x0f- 2, }, /* PCIRQ2 */ + { 6 , 4, 4, 0x0f- 6, }, /* PCIRQ1 */ + { 14, 4, 0, 0x0f-14, }, /* PCIRQ0 */ + { 0 , 5, 12, 0x0f , }, + { 4 , 5, 4, 0x0f- 4, }, + { 8 , 6, 12, 0x0f- 8, }, + { 9 , 6, 8, 0x0f- 9, }, + { 11, 6, 4, 0x0f-11, }, #else - { 14, 0, 8, 0x0f-14 ,BCR_ILCRA}, - { 12, 0, 4, 0x0f-12 ,BCR_ILCRA}, - { 8, 0, 4, 0x0f- 8 ,BCR_ILCRB}, - { 6, 0, 12, 0x0f- 6 ,BCR_ILCRC}, - { 5, 0, 8, 0x0f- 5 ,BCR_ILCRC}, - { 4, 0, 4, 0x0f- 4 ,BCR_ILCRC}, - { 3, 0, 0, 0x0f- 3 ,BCR_ILCRC}, - { 1, 0, 12, 0x0f- 1 ,BCR_ILCRD}, + { 14, 0, 8, 0x0f-14, }, + { 12, 0, 4, 0x0f-12, }, + { 8, 1, 4, 0x0f- 8, }, + { 6, 2, 12, 0x0f- 6, }, + { 5, 2, 8, 0x0f- 5, }, + { 4, 2, 4, 0x0f- 4, }, + { 3, 2, 0, 0x0f- 3, }, + { 1, 3, 12, 0x0f- 1, }, #if defined(CONFIG_STNIC) /* ST NIC */ - { 10, 0, 4, 0x0f-10 ,BCR_ILCRD}, /* LAN */ + { 10, 3, 4, 0x0f-10, }, /* LAN */ #endif /* MRSHPC IRQs setting */ - { 0, 0, 12, 0x0f- 0 ,BCR_ILCRE}, /* PCIRQ3 */ - { 11, 0, 8, 0x0f-11 ,BCR_ILCRE}, /* PCIRQ2 */ - { 9, 0, 4, 0x0f- 9 ,BCR_ILCRE}, /* PCIRQ1 */ - { 7, 0, 0, 0x0f- 7 ,BCR_ILCRE}, /* PCIRQ0 */ + { 0, 4, 12, 0x0f- 0, }, /* PCIRQ3 */ + { 11, 4, 8, 0x0f-11, }, /* PCIRQ2 */ + { 9, 4, 4, 0x0f- 9, }, /* PCIRQ1 */ + { 7, 4, 0, 0x0f- 7, }, /* PCIRQ0 */ /* #2, #13 are allocated for SLOT IRQ #1 and #2 (for now) */ /* NOTE: #2 and #13 are not used on PC */ - { 13, 0, 4, 0x0f-13 ,BCR_ILCRG}, /* SLOTIRQ2 */ - { 2, 0, 0, 0x0f- 2 ,BCR_ILCRG}, /* SLOTIRQ1 */ + { 13, 6, 4, 0x0f-13, }, /* SLOTIRQ2 */ + { 2, 6, 0, 0x0f- 2, }, /* SLOTIRQ1 */ #endif }; +static unsigned long ipr_offsets[] = { + BCR_ILCRA, + BCR_ILCRB, + BCR_ILCRC, + BCR_ILCRD, + BCR_ILCRE, + BCR_ILCRF, + BCR_ILCRG, +}; + +static struct ipr_desc ipr_irq_desc = { + .ipr_offsets = ipr_offsets, + .nr_offsets = ARRAY_SIZE(ipr_offsets), + + .ipr_data = ipr_irq_table, + .nr_irqs = ARRAY_SIZE(ipr_irq_table), + .chip = { + .name = "IPR-se770x", + }, +}; + /* * Initialize IRQ setting */ @@ -122,5 +104,5 @@ void __init init_se_IRQ(void) ctrl_outw(0, BCR_ILCRF); ctrl_outw(0, BCR_ILCRG); - make_se770x_irq(se770x_ipr_map, ARRAY_SIZE(se770x_ipr_map)); + register_ipr_controller(&ipr_irq_desc); } diff --git a/arch/sh/boards/se/7722/irq.c b/arch/sh/boards/se/7722/irq.c index 099e5deb77f..26cff0efda4 100644 --- a/arch/sh/boards/se/7722/irq.c +++ b/arch/sh/boards/se/7722/irq.c @@ -19,15 +19,24 @@ #define INTC_INTMSK0 0xFFD00044 #define INTC_INTMSKCLR0 0xFFD00064 +struct se7722_data { + unsigned char irq; + unsigned char ipr_idx; + unsigned char shift; + unsigned short priority; + unsigned long addr; +}; + + static void disable_se7722_irq(unsigned int irq) { - struct ipr_data *p = get_irq_chip_data(irq); + struct se7722_data *p = get_irq_chip_data(irq); ctrl_outw( ctrl_inw( p->addr ) | p->priority , p->addr ); } static void enable_se7722_irq(unsigned int irq) { - struct ipr_data *p = get_irq_chip_data(irq); + struct se7722_data *p = get_irq_chip_data(irq); ctrl_outw( ctrl_inw( p->addr ) & ~p->priority , p->addr ); } @@ -38,7 +47,7 @@ static struct irq_chip se7722_irq_chip __read_mostly = { .mask_ack = disable_se7722_irq, }; -static struct ipr_data ipr_irq_table[] = { +static struct se7722_data ipr_irq_table[] = { /* irq ,idx,sft, priority , addr */ { MRSHPC_IRQ0 , 0 , 0 , MRSHPC_BIT0 , IRQ01_MASK } , { MRSHPC_IRQ1 , 0 , 0 , MRSHPC_BIT1 , IRQ01_MASK } , diff --git a/arch/sh/boards/se/7751/irq.c b/arch/sh/boards/se/7751/irq.c index e4c63a48296..c3d12590e5d 100644 --- a/arch/sh/boards/se/7751/irq.c +++ b/arch/sh/boards/se/7751/irq.c @@ -14,44 +14,31 @@ #include <asm/irq.h> #include <asm/se7751.h> -static struct ipr_data se7751_ipr_map[] = { - /* Leave old Solution Engine code in for reference. */ -#if defined(CONFIG_SH_SOLUTION_ENGINE) - /* - * Super I/O (Just mimic PC): - * 1: keyboard - * 3: serial 0 - * 4: serial 1 - * 5: printer - * 6: floppy - * 8: rtc - * 12: mouse - * 14: ide0 - */ - { 14, BCR_ILCRA, 2, 0x0f-14 }, - { 12, BCR_ILCRA, 1, 0x0f-12 }, - { 8, BCR_ILCRB, 1, 0x0f- 8 }, - { 6, BCR_ILCRC, 3, 0x0f- 6 }, - { 5, BCR_ILCRC, 2, 0x0f- 5 }, - { 4, BCR_ILCRC, 1, 0x0f- 4 }, - { 3, BCR_ILCRC, 0, 0x0f- 3 }, - { 1, BCR_ILCRD, 3, 0x0f- 1 }, +static struct ipr_data ipr_irq_table[] = { + { 13, 3, 3, 2 }, + /* Add additional entries here as drivers are added and tested. */ +}; - { 10, BCR_ILCRD, 1, 0x0f-10 }, /* LAN */ +static unsigned long ipr_offsets[] = { + BCR_ILCRA, + BCR_ILCRB, + BCR_ILCRC, + BCR_ILCRD, + BCR_ILCRE, + BCR_ILCRF, + BCR_ILCRG, +}; - { 0, BCR_ILCRE, 3, 0x0f- 0 }, /* PCIRQ3 */ - { 11, BCR_ILCRE, 2, 0x0f-11 }, /* PCIRQ2 */ - { 9, BCR_ILCRE, 1, 0x0f- 9 }, /* PCIRQ1 */ - { 7, BCR_ILCRE, 0, 0x0f- 7 }, /* PCIRQ0 */ +static struct ipr_desc ipr_irq_desc = { + .ipr_offsets = ipr_offsets, + .nr_offsets = ARRAY_SIZE(ipr_offsets), - /* #2, #13 are allocated for SLOT IRQ #1 and #2 (for now) */ - /* NOTE: #2 and #13 are not used on PC */ - { 13, BCR_ILCRG, 1, 0x0f-13 }, /* SLOTIRQ2 */ - { 2, BCR_ILCRG, 0, 0x0f- 2 }, /* SLOTIRQ1 */ -#elif defined(CONFIG_SH_7751_SOLUTION_ENGINE) - { 13, BCR_ILCRD, 3, 2 }, - /* Add additional entries here as drivers are added and tested. */ -#endif + .ipr_data = ipr_irq_table, + .nr_irqs = ARRAY_SIZE(ipr_irq_table), + + .chip = { + .name = "IPR-se7751", + }, }; /* @@ -59,5 +46,5 @@ static struct ipr_data se7751_ipr_map[] = { */ void __init init_7751se_IRQ(void) { - make_ipr_irq(se7751_ipr_map, ARRAY_SIZE(se7751_ipr_map)); + register_ipr_controller(&ipr_irq_desc); } |