You can subscribe to this list here.
2000 |
Jan
|
Feb
|
Mar
|
Apr
(12) |
May
(82) |
Jun
(72) |
Jul
(39) |
Aug
(104) |
Sep
(61) |
Oct
(55) |
Nov
(101) |
Dec
(48) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2001 |
Jan
(52) |
Feb
(67) |
Mar
(18) |
Apr
(16) |
May
(33) |
Jun
(12) |
Jul
(102) |
Aug
(168) |
Sep
(65) |
Oct
(60) |
Nov
(43) |
Dec
(121) |
2002 |
Jan
(69) |
Feb
(32) |
Mar
(90) |
Apr
(59) |
May
(45) |
Jun
(43) |
Jul
(33) |
Aug
(21) |
Sep
(11) |
Oct
(20) |
Nov
(26) |
Dec
(3) |
2003 |
Jan
(12) |
Feb
(18) |
Mar
(11) |
Apr
(11) |
May
(41) |
Jun
(76) |
Jul
(77) |
Aug
(15) |
Sep
(38) |
Oct
(56) |
Nov
(19) |
Dec
(39) |
2004 |
Jan
(17) |
Feb
(52) |
Mar
(36) |
Apr
(34) |
May
(48) |
Jun
(85) |
Jul
(38) |
Aug
(42) |
Sep
(41) |
Oct
(77) |
Nov
(27) |
Dec
(19) |
2005 |
Jan
(32) |
Feb
(35) |
Mar
(29) |
Apr
(8) |
May
(7) |
Jun
(31) |
Jul
(46) |
Aug
(93) |
Sep
(65) |
Oct
(85) |
Nov
(219) |
Dec
(47) |
2006 |
Jan
(170) |
Feb
(103) |
Mar
(49) |
Apr
(43) |
May
(45) |
Jun
(29) |
Jul
(77) |
Aug
(82) |
Sep
(43) |
Oct
(45) |
Nov
(26) |
Dec
(85) |
2007 |
Jan
(42) |
Feb
(48) |
Mar
(64) |
Apr
(31) |
May
(88) |
Jun
(53) |
Jul
(175) |
Aug
(212) |
Sep
(91) |
Oct
(103) |
Nov
(110) |
Dec
(5) |
2008 |
Jan
(20) |
Feb
(11) |
Mar
(1) |
Apr
|
May
|
Jun
|
Jul
(1) |
Aug
(5) |
Sep
(3) |
Oct
(12) |
Nov
|
Dec
|
From: Paul M. <le...@li...> - 2007-07-18 01:43:21
|
On Wed, Jul 18, 2007 at 10:23:05AM +0900, Magnus Damm wrote: > --- 0001/arch/sh/kernel/irq.c > +++ work/arch/sh/kernel/irq.c 2007-07-17 17:01:58.000000000 +0900 > @@ -254,12 +254,9 @@ void __init init_IRQ(void) > init_IRQ_pint(); > #endif > > -#ifdef CONFIG_CPU_HAS_INTC2_IRQ > - init_IRQ_intc2(); > -#endif > - > -#ifdef CONFIG_CPU_HAS_IPR_IRQ > - init_IRQ_ipr(); > +#if defined(CONFIG_CPU_HAS_INTC2_IRQ) || defined(CONFIG_CPU_HAS_INTC2_IRQ) || \ > + defined(CONFIG_CPU_HAS_INTC_IRQ) > + plat_irq_setup(); > #endif > Eek. How about a weak dummy symbol instead? You've also double-cased CPU_HAS_INTC2_IRQ, whereas I assume you meant to make one of them CPU_HAS_IPR_IRQ. On the other hand, is it really a valid state for any CPU not to have at least one of INTC2/INTC/IPR? In which case, make the reference to the symbol explicit, and let the linker whine. |
From: Paul M. <le...@li...> - 2007-07-18 01:39:52
|
On Wed, Jul 18, 2007 at 10:20:36AM +0900, Magnus Damm wrote: > +void (*intc_reg_fns[])(struct intc_desc *, unsigned int) = { > + NULL, /* index 0 used as error code */ > + enable_mask_8, disable_mask_8, > + enable_mask_32, disable_mask_32, > + enable_prio_16, disable_prio_16, > + enable_prio_32, disable_prio_32, > +}; > + Shouldn't this be static? > +static void intc_enable(unsigned int irq) > +{ > + struct intc_desc *desc = get_intc_desc(irq); > + unsigned int data = (unsigned int) get_irq_chip_data(irq); > + > + intc_reg_fns[_INTC_FN(data)](desc, data); > +} > + > +static void intc_disable(unsigned int irq) > +{ > + struct intc_desc *desc = get_intc_desc(irq); > + unsigned int data = (unsigned int) get_irq_chip_data(irq); > + > + intc_reg_fns[_INTC_FN(data) + 1](desc, data); > +} > + Hmm.. this should probably be reworked a little, it looks a little clunky, and the + 1 thing isn't obvious without first looking at intc_reg_fns[]. |
From: Magnus D. <mag...@gm...> - 2007-07-18 01:23:56
|
sh: replace init_IRQ_ipr() and init_IRQ_intc2() with plat_irq_setup() This patch unifies the cpu specific interrupt setup functions for interrupt controller blocks such as ipr, intc2 and intc. There is no point in having separate functions for each interrupt controller, so let's clean this up. Signed-off-by: Magnus Damm <da...@ig...> --- Applies to git linux-2.6 a5fcaa210626a79465321e344c91a6a7dc3881fa Needs to be applied on top of sh7722 intc code. arch/sh/kernel/cpu/sh2/setup-sh7619.c | 2 +- arch/sh/kernel/cpu/sh2a/setup-sh7206.c | 2 +- arch/sh/kernel/cpu/sh3/setup-sh7705.c | 2 +- arch/sh/kernel/cpu/sh3/setup-sh7709.c | 2 +- arch/sh/kernel/cpu/sh3/setup-sh7710.c | 2 +- arch/sh/kernel/cpu/sh4/setup-sh7750.c | 2 +- arch/sh/kernel/cpu/sh4/setup-sh7760.c | 8 ++------ arch/sh/kernel/cpu/sh4a/setup-sh7722.c | 2 +- arch/sh/kernel/cpu/sh4a/setup-sh7780.c | 2 +- arch/sh/kernel/cpu/sh4a/setup-sh7785.c | 2 +- arch/sh/kernel/cpu/sh4a/setup-shx3.c | 2 +- arch/sh/kernel/irq.c | 9 +++------ include/asm-sh/hw_irq.h | 4 ++-- 13 files changed, 17 insertions(+), 24 deletions(-) --- 0001/arch/sh/kernel/cpu/sh2/setup-sh7619.c +++ work/arch/sh/kernel/cpu/sh2/setup-sh7619.c 2007-07-17 17:01:58.000000000 +0900 @@ -88,7 +88,7 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh2a/setup-sh7206.c +++ work/arch/sh/kernel/cpu/sh2a/setup-sh7206.c 2007-07-17 17:01:58.000000000 +0900 @@ -107,7 +107,7 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh3/setup-sh7705.c +++ work/arch/sh/kernel/cpu/sh3/setup-sh7705.c 2007-07-17 17:01:58.000000000 +0900 @@ -92,7 +92,7 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh3/setup-sh7709.c +++ work/arch/sh/kernel/cpu/sh3/setup-sh7709.c 2007-07-17 17:01:58.000000000 +0900 @@ -139,7 +139,7 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh3/setup-sh7710.c +++ work/arch/sh/kernel/cpu/sh3/setup-sh7710.c 2007-07-17 17:01:58.000000000 +0900 @@ -101,7 +101,7 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh4/setup-sh7750.c +++ work/arch/sh/kernel/cpu/sh4/setup-sh7750.c 2007-07-17 17:01:58.000000000 +0900 @@ -151,7 +151,7 @@ static struct ipr_desc ipr_irq_desc_sh77 }; #endif -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_ipr_controller(&ipr_irq_desc); #ifdef CONFIG_CPU_SUBTYPE_SH7751 --- 0001/arch/sh/kernel/cpu/sh4/setup-sh7760.c +++ work/arch/sh/kernel/cpu/sh4/setup-sh7760.c 2007-07-17 17:01:58.000000000 +0900 @@ -109,11 +109,6 @@ static struct intc2_desc intc2_irq_desc }, }; -void __init init_IRQ_intc2(void) -{ - register_intc2_controller(&intc2_irq_desc); -} - static struct ipr_data ipr_irq_table[] = { /* IRQ, IPR-idx, shift, priority */ { 16, 0, 12, 2 }, /* TMU0 TUNI*/ @@ -163,7 +158,8 @@ static struct ipr_desc ipr_irq_desc = { }, }; -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { + register_intc2_controller(&intc2_irq_desc); register_ipr_controller(&ipr_irq_desc); } --- 0006/arch/sh/kernel/cpu/sh4a/setup-sh7722.c +++ work/arch/sh/kernel/cpu/sh4a/setup-sh7722.c 2007-07-17 17:01:58.000000000 +0900 @@ -194,7 +194,7 @@ static struct intc_sense_reg sense_regis DECLARE_INTC_DESC(intc_desc, "sh7722", vectors, groups, priorities, mask_registers, prio_registers, sense_registers); -void __init init_IRQ_ipr(void) +void __init plat_irq_setup(void) { register_intc_controller(&intc_desc); } --- 0001/arch/sh/kernel/cpu/sh4a/setup-sh7780.c +++ work/arch/sh/kernel/cpu/sh4a/setup-sh7780.c 2007-07-17 17:01:58.000000000 +0900 @@ -115,7 +115,7 @@ static struct intc2_desc intc2_irq_desc }, }; -void __init init_IRQ_intc2(void) +void __init plat_irq_setup(void) { register_intc2_controller(&intc2_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh4a/setup-sh7785.c +++ work/arch/sh/kernel/cpu/sh4a/setup-sh7785.c 2007-07-17 17:01:58.000000000 +0900 @@ -110,7 +110,7 @@ static struct intc2_desc intc2_irq_desc }, }; -void __init init_IRQ_intc2(void) +void __init plat_irq_setup(void) { register_intc2_controller(&intc2_irq_desc); } --- 0001/arch/sh/kernel/cpu/sh4a/setup-shx3.c +++ work/arch/sh/kernel/cpu/sh4a/setup-shx3.c 2007-07-17 17:01:58.000000000 +0900 @@ -79,7 +79,7 @@ static struct intc2_desc intc2_irq_desc }, }; -void __init init_IRQ_intc2(void) +void __init plat_irq_setup(void) { register_intc2_controller(&intc2_irq_desc); } --- 0001/arch/sh/kernel/irq.c +++ work/arch/sh/kernel/irq.c 2007-07-17 17:01:58.000000000 +0900 @@ -254,12 +254,9 @@ void __init init_IRQ(void) init_IRQ_pint(); #endif -#ifdef CONFIG_CPU_HAS_INTC2_IRQ - init_IRQ_intc2(); -#endif - -#ifdef CONFIG_CPU_HAS_IPR_IRQ - init_IRQ_ipr(); +#if defined(CONFIG_CPU_HAS_INTC2_IRQ) || defined(CONFIG_CPU_HAS_INTC2_IRQ) || \ + defined(CONFIG_CPU_HAS_INTC_IRQ) + plat_irq_setup(); #endif /* Perform the machine specific initialisation */ --- 0004/include/asm-sh/hw_irq.h +++ work/include/asm-sh/hw_irq.h 2007-07-17 17:04:28.000000000 +0900 @@ -23,7 +23,6 @@ struct intc2_desc { }; void register_intc2_controller(struct intc2_desc *); -void init_IRQ_intc2(void); struct ipr_data { unsigned char irq; @@ -41,7 +40,6 @@ struct ipr_desc { }; void register_ipr_controller(struct ipr_desc *); -void init_IRQ_ipr(void); /* * Enable individual interrupt mode for external IPR IRQs. @@ -115,4 +113,6 @@ static struct intc_desc symbol = { \ void __init register_intc_controller(struct intc_desc *desc); +void __init plat_irq_setup(void); + #endif /* __ASM_SH_HW_IRQ_H */ |
From: Magnus D. <mag...@gm...> - 2007-07-18 01:23:01
|
sh: clean up interrupt code for solution engine 7722 board This patch cleans up solution engine 7722 specific interrupt code. The main purpose is to replace the mux function with use of set_irq_chained_handler() and replace hard coded register poking code with set_irq_type(). The board specific interrupts are also moved to start from SE7722_FPGA_IRQ_BASE. Signed-off-by: Magnus Damm <da...@ig...> --- Applies to git linux-2.6 a5fcaa210626a79465321e344c91a6a7dc3881fa Needs cpu specific intc support for set_irq_type() arch/sh/boards/se/7722/irq.c | 98 ++++++++++++-------------------------- arch/sh/boards/se/7722/setup.c | 5 - arch/sh/configs/se7722_defconfig | 2 include/asm-sh/se7722.h | 40 ++++++--------- 4 files changed, 53 insertions(+), 92 deletions(-) --- 0001/arch/sh/boards/se/7722/irq.c +++ work/arch/sh/boards/se/7722/irq.c 2007-07-17 16:32:09.000000000 +0900 @@ -16,95 +16,61 @@ #include <asm/io.h> #include <asm/se7722.h> -#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 se7722_data *p = get_irq_chip_data(irq); - ctrl_outw( ctrl_inw( p->addr ) | p->priority , p->addr ); + unsigned int bit = irq - SE7722_FPGA_IRQ_BASE; + ctrl_outw(ctrl_inw(IRQ01_MASK) | 1 << bit, IRQ01_MASK); } static void enable_se7722_irq(unsigned int irq) { - struct se7722_data *p = get_irq_chip_data(irq); - ctrl_outw( ctrl_inw( p->addr ) & ~p->priority , p->addr ); + unsigned int bit = irq - SE7722_FPGA_IRQ_BASE; + ctrl_outw(ctrl_inw(IRQ01_MASK) & ~(1 << bit), IRQ01_MASK); } static struct irq_chip se7722_irq_chip __read_mostly = { - .name = "SE7722", + .name = "SE7722-FPGA", .mask = disable_se7722_irq, .unmask = enable_se7722_irq, .mask_ack = disable_se7722_irq, }; -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 } , - { MRSHPC_IRQ2 , 0 , 0 , MRSHPC_BIT2 , IRQ01_MASK } , - { MRSHPC_IRQ3 , 0 , 0 , MRSHPC_BIT3 , IRQ01_MASK } , - { SMC_IRQ , 0 , 0 , SMC_BIT , IRQ01_MASK } , - { EXT_IRQ , 0 , 0 , EXT_BIT , IRQ01_MASK } , -}; - -int se7722_irq_demux(int irq) +static void se7722_irq_demux(unsigned int irq, struct irq_desc *desc) { - - if ((irq == IRQ0_IRQ)||(irq == IRQ1_IRQ)) { - volatile unsigned short intv = - *(volatile unsigned short *)IRQ01_STS; - if (irq == IRQ0_IRQ){ - if(intv & SMC_BIT ) { - return SMC_IRQ; - } else if(intv & USB_BIT) { - return USB_IRQ; - } else { - printk("intv =%04x\n", intv); - return SMC_IRQ; - } - } else if(irq == IRQ1_IRQ){ - if(intv & MRSHPC_BIT0) { - return MRSHPC_IRQ0; - } else if(intv & MRSHPC_BIT1) { - return MRSHPC_IRQ1; - } else if(intv & MRSHPC_BIT2) { - return MRSHPC_IRQ2; - } else if(intv & MRSHPC_BIT3) { - return MRSHPC_IRQ3; - } else { - printk("BIT_EXTENTION =%04x\n", intv); - return EXT_IRQ; - } + unsigned short intv = ctrl_inw(IRQ01_STS); + struct irq_desc *ext_desc; + unsigned int ext_irq = SE7722_FPGA_IRQ_BASE; + + intv &= (1 << SE7722_FPGA_IRQ_NR) - 1; + + while (intv) { + if (intv & 1) { + ext_desc = irq_desc + ext_irq; + handle_level_irq(ext_irq, ext_desc); } + intv >>= 1; + ext_irq++; } - return irq; - } + /* * Initialize IRQ setting */ void __init init_se7722_IRQ(void) { - int i = 0; + int i; + + ctrl_outw(0, IRQ01_MASK); /* disable all irqs */ ctrl_outw(0x2000, 0xb03fffec); /* mrshpc irq enable */ - ctrl_outl((3 << ((7 - 0) * 4))|(3 << ((7 - 1) * 4)), INTC_INTPRI0); /* irq0 pri=3,irq1,pri=3 */ - ctrl_outw((2 << ((7 - 0) * 2))|(2 << ((7 - 1) * 2)), INTC_ICR1); /* irq0,1 low-level irq */ - for (i = 0; i < ARRAY_SIZE(ipr_irq_table); i++) { - disable_irq_nosync(ipr_irq_table[i].irq); - set_irq_chip_and_handler_name( ipr_irq_table[i].irq, &se7722_irq_chip, - handle_level_irq, "level"); - set_irq_chip_data( ipr_irq_table[i].irq, &ipr_irq_table[i] ); - disable_se7722_irq(ipr_irq_table[i].irq); - } + for (i = 0; i < SE7722_FPGA_IRQ_NR; i++) + set_irq_chip_and_handler_name(SE7722_FPGA_IRQ_BASE + i, + &se7722_irq_chip, + handle_level_irq, "level"); + + set_irq_chained_handler(IRQ0_IRQ, se7722_irq_demux); + set_irq_type(IRQ0_IRQ, IRQ_TYPE_LEVEL_LOW); + + set_irq_chained_handler(IRQ1_IRQ, se7722_irq_demux); + set_irq_type(IRQ1_IRQ, IRQ_TYPE_LEVEL_LOW); } --- 0001/arch/sh/boards/se/7722/setup.c +++ work/arch/sh/boards/se/7722/setup.c 2007-07-17 16:32:09.000000000 +0900 @@ -77,6 +77,7 @@ static struct resource cf_ide_resources[ }, [2] = { .start = MRSHPC_IRQ0, + .end = MRSHPC_IRQ0, .flags = IORESOURCE_IRQ, }, }; @@ -140,8 +141,6 @@ static void __init se7722_setup(char **c static struct sh_machine_vector mv_se7722 __initmv = { .mv_name = "Solution Engine 7722" , .mv_setup = se7722_setup , - .mv_nr_irqs = 109 , + .mv_nr_irqs = SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_NR, .mv_init_irq = init_se7722_IRQ, - .mv_irq_demux = se7722_irq_demux, - }; --- 0003/arch/sh/configs/se7722_defconfig +++ work/arch/sh/configs/se7722_defconfig 2007-07-17 16:55:09.000000000 +0900 @@ -200,7 +200,7 @@ CONFIG_CPU_LITTLE_ENDIAN=y CONFIG_SH_DSP=y CONFIG_SH_STORE_QUEUES=y CONFIG_CPU_HAS_INTEVT=y -CONFIG_CPU_HAS_IPR_IRQ=y +CONFIG_CPU_HAS_INTC_IRQ=y CONFIG_CPU_HAS_SR_RB=y CONFIG_CPU_HAS_PTEA=y --- 0001/include/asm-sh/se7722.h +++ work/include/asm-sh/se7722.h 2007-07-17 16:32:09.000000000 +0900 @@ -81,36 +81,32 @@ /* IRQ */ #define IRQ0_IRQ 32 #define IRQ1_IRQ 33 -#define INTC_ICR0 0xA4140000UL -#define INTC_ICR1 0xA414001CUL - -#define INTMSK0 0xa4140044 -#define INTMSKCLR0 0xa4140064 -#define INTC_INTPRI0 0xa4140010 #define IRQ01_MODE 0xb1800000 #define IRQ01_STS 0xb1800004 #define IRQ01_MASK 0xb1800008 -#define EXT_BIT (0x3fc0) /* SH IRQ1 */ -#define MRSHPC_BIT0 (0x0004) /* SH IRQ1 */ -#define MRSHPC_BIT1 (0x0008) /* SH IRQ1 */ -#define MRSHPC_BIT2 (0x0010) /* SH IRQ1 */ -#define MRSHPC_BIT3 (0x0020) /* SH IRQ1 */ -#define SMC_BIT (0x0002) /* SH IRQ0 */ -#define USB_BIT (0x0001) /* SH IRQ0 */ - -#define MRSHPC_IRQ3 11 -#define MRSHPC_IRQ2 12 -#define MRSHPC_IRQ1 13 -#define MRSHPC_IRQ0 14 -#define SMC_IRQ 10 -#define EXT_IRQ 5 -#define USB_IRQ 6 +/* Bits in IRQ01_* registers */ + +#define SE7722_FPGA_IRQ_USB 0 /* IRQ0 */ +#define SE7722_FPGA_IRQ_SMC 1 /* IRQ0 */ +#define SE7722_FPGA_IRQ_MRSHPC0 2 /* IRQ1 */ +#define SE7722_FPGA_IRQ_MRSHPC1 3 /* IRQ1 */ +#define SE7722_FPGA_IRQ_MRSHPC2 4 /* IRQ1 */ +#define SE7722_FPGA_IRQ_MRSHPC3 5 /* IRQ1 */ + +#define SE7722_FPGA_IRQ_NR 6 +#define SE7722_FPGA_IRQ_BASE 110 + +#define MRSHPC_IRQ3 (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_MRSHPC3) +#define MRSHPC_IRQ2 (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_MRSHPC2) +#define MRSHPC_IRQ1 (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_MRSHPC1) +#define MRSHPC_IRQ0 (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_MRSHPC0) +#define SMC_IRQ (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_SMC) +#define USB_IRQ (SE7722_FPGA_IRQ_BASE + SE7722_FPGA_IRQ_USB) /* arch/sh/boards/se/7722/irq.c */ void init_se7722_IRQ(void); -int se7722_irq_demux(int); #define __IO_PREFIX se7722 #include <asm/io_generic.h> |
From: Magnus D. <mag...@gm...> - 2007-07-18 01:22:23
|
sh: intc - add support for 7722 processor This patch converts the cpu specific 7722 setup code to use the new intc controller. Many new vectors are added and also support for external interrupt sense configuration. So with this patch it is now possible to configure external interrupt pins as edge or level triggered using set_irq_type(). Signed-off-by: Magnus Damm <da...@ig...> --- Tested on a Solution Engline 7722 Applies to git linux-2.6 a5fcaa210626a79465321e344c91a6a7dc3881fa arch/sh/kernel/cpu/sh4a/setup-sh7722.c | 171 +++++++++++++++++++++++++------- arch/sh/mm/Kconfig | 2 2 files changed, 137 insertions(+), 36 deletions(-) --- 0001/arch/sh/kernel/cpu/sh4a/setup-sh7722.c +++ work/arch/sh/kernel/cpu/sh4a/setup-sh7722.c 2007-07-18 09:22:17.000000000 +0900 @@ -57,45 +57,146 @@ static int __init sh7722_devices_setup(v } __initcall(sh7722_devices_setup); -static struct ipr_data ipr_irq_table[] = { - /* IRQ, IPR-idx, shift, prio */ - { 16, 0, 12, 2 }, /* TMU0 */ - { 17, 0, 8, 2 }, /* TMU1 */ - { 80, 6, 12, 3 }, /* SCIF0 */ - { 81, 6, 8, 3 }, /* SCIF1 */ - { 82, 6, 4, 3 }, /* SCIF2 */ -}; - -static unsigned long ipr_offsets[] = { - 0xa4080000, /* 0: IPRA */ - 0xa4080004, /* 1: IPRB */ - 0xa4080008, /* 2: IPRC */ - 0xa408000c, /* 3: IPRD */ - 0xa4080010, /* 4: IPRE */ - 0xa4080014, /* 5: IPRF */ - 0xa4080018, /* 6: IPRG */ - 0xa408001c, /* 7: IPRH */ - 0xa4080020, /* 8: IPRI */ - 0xa4080024, /* 9: IPRJ */ - 0xa4080028, /* 10: IPRK */ - 0xa408002c, /* 11: IPRL */ -}; - -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-sh7722", - }, +enum { + UNUSED=0, + + /* interrupt sources */ + + IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7, + HUDI, + SIM_ERI, SIM_RXI, SIM_TXI, SIM_TEI, + RTC_ATI, RTC_PRI, RTC_CUI, + DMAC0, DMAC1, DMAC2, DMAC3, + VIO_CEUI, VIO_BEUI, VIO_VEUI, VOU, + VPU, TPU, + USB_USBI0, USB_USBI1, + DMAC4, DMAC5, DMAC_DADERR, + KEYSC, + SCIF0, SCIF1, SCIF2, SIOF0, SIOF1, SIO, + FLCTL_FLSTEI, FLCTL_FLENDI, FLCTL_FLTREQ0I, FLCTL_FLTREQ1I, + I2C_ALI, I2C_TACKI, I2C_WAITI, I2C_DTEI, + SDHI0, SDHI1, SDHI2, SDHI3, + CMT, TSIF, SIU, _2DG, + TMU0, TMU1, TMU2, + IRDA, JPU, LCDC, + + /* interrupt groups */ + + SIM, RTC, DMAC0123, VIOVOU, USB, DMAC45, FLCTL, I2C, SDHI, +}; + +static struct intc_vect vectors[] = { + INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620), + INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660), + INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0), + INTC_VECT(IRQ6, 0x6c0), INTC_VECT(IRQ7, 0x6e0), + INTC_VECT(SIM_ERI, 0x700), INTC_VECT(SIM_RXI, 0x720), + INTC_VECT(SIM_TXI, 0x740), INTC_VECT(SIM_TEI, 0x760), + INTC_VECT(RTC_ATI, 0x780), INTC_VECT(RTC_PRI, 0x7a0), + INTC_VECT(RTC_CUI, 0x7c0), + INTC_VECT(DMAC0, 0x800), INTC_VECT(DMAC1, 0x820), + INTC_VECT(DMAC2, 0x840), INTC_VECT(DMAC3, 0x860), + INTC_VECT(VIO_CEUI, 0x880), INTC_VECT(VIO_BEUI, 0x8a0), + INTC_VECT(VIO_VEUI, 0x8c0), INTC_VECT(VOU, 0x8e0), + INTC_VECT(VPU, 0x980), INTC_VECT(TPU, 0x9a0), + INTC_VECT(USB_USBI0, 0xa20), INTC_VECT(USB_USBI1, 0xa40), + INTC_VECT(DMAC4, 0xb80), INTC_VECT(DMAC5, 0xba0), + INTC_VECT(DMAC_DADERR, 0xbc0), INTC_VECT(KEYSC, 0xbe0), + INTC_VECT(SCIF0, 0xc00), INTC_VECT(SCIF1, 0xc20), + INTC_VECT(SCIF2, 0xc40), INTC_VECT(SIOF0, 0xc80), + INTC_VECT(SIOF1, 0xca0), INTC_VECT(SIO, 0xd00), + INTC_VECT(FLCTL_FLSTEI, 0xd80), INTC_VECT(FLCTL_FLENDI, 0xda0), + INTC_VECT(FLCTL_FLTREQ0I, 0xdc0), INTC_VECT(FLCTL_FLTREQ1I, 0xde0), + INTC_VECT(I2C_ALI, 0xe00), INTC_VECT(I2C_TACKI, 0xe20), + INTC_VECT(I2C_WAITI, 0xe40), INTC_VECT(I2C_DTEI, 0xe60), + INTC_VECT(SDHI0, 0xe80), INTC_VECT(SDHI1, 0xea0), + INTC_VECT(SDHI2, 0xec0), INTC_VECT(SDHI3, 0xee0), + INTC_VECT(CMT, 0xf00), INTC_VECT(TSIF, 0xf20), + INTC_VECT(SIU, 0xf80), INTC_VECT(_2DG, 0xfa0), + INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420), + INTC_VECT(TMU2, 0x440), INTC_VECT(IRDA, 0x480), + INTC_VECT(JPU, 0x560), INTC_VECT(LCDC, 0x580), +}; + +static struct intc_group groups[] = { + INTC_GROUP(SIM, SIM_ERI, SIM_RXI, SIM_TXI, SIM_TEI), + INTC_GROUP(RTC, RTC_ATI, RTC_PRI, RTC_CUI), + INTC_GROUP(DMAC0123, DMAC0, DMAC1, DMAC2, DMAC3), + INTC_GROUP(VIOVOU, VIO_CEUI, VIO_BEUI, VIO_VEUI, VOU), + INTC_GROUP(USB, USB_USBI0, USB_USBI1), + INTC_GROUP(DMAC45, DMAC4, DMAC5, DMAC_DADERR), + INTC_GROUP(FLCTL, FLCTL_FLSTEI, FLCTL_FLENDI, + FLCTL_FLTREQ0I, FLCTL_FLTREQ1I), + INTC_GROUP(I2C, I2C_ALI, I2C_TACKI, I2C_WAITI, I2C_DTEI), + INTC_GROUP(SDHI, SDHI0, SDHI1, SDHI2, SDHI3), }; +static struct intc_prio priorities[] = { + INTC_PRIO(SCIF0, 3), + INTC_PRIO(SCIF1, 3), + INTC_PRIO(SCIF2, 3), + INTC_PRIO(TMU0, 2), + INTC_PRIO(TMU1, 2), +}; + +static struct intc_mask_reg mask_registers[] = { + { 0xa4080080, 0xa40800c0, 8, /* IMR0 / IMCR0 */ + { } }, + { 0xa4080084, 0xa40800c4, 8, /* IMR1 / IMCR1 */ + { VOU, VIO_VEUI, VIO_BEUI, VIO_CEUI, DMAC3, DMAC2, DMAC1, DMAC0 } }, + { 0xa4080088, 0xa40800c8, 8, /* IMR2 / IMCR2 */ + { 0, 0, 0, VPU, } }, + { 0xa408008c, 0xa40800cc, 8, /* IMR3 / IMCR3 */ + { SIM_TEI, SIM_TXI, SIM_RXI, SIM_ERI, 0, 0, 0, IRDA } }, + { 0xa4080090, 0xa40800d0, 8, /* IMR4 / IMCR4 */ + { 0, TMU2, TMU1, TMU0, JPU, 0, 0, LCDC } }, + { 0xa4080094, 0xa40800d4, 8, /* IMR5 / IMCR5 */ + { KEYSC, DMAC_DADERR, DMAC5, DMAC4, 0, SCIF2, SCIF1, SCIF0 } }, + { 0xa4080098, 0xa40800d8, 8, /* IMR6 / IMCR6 */ + { 0, 0, 0, SIO, 0, 0, SIOF1, SIOF0 } }, + { 0xa408009c, 0xa40800dc, 8, /* IMR7 / IMCR7 */ + { I2C_DTEI, I2C_WAITI, I2C_TACKI, I2C_ALI, + FLCTL_FLTREQ1I, FLCTL_FLTREQ0I, FLCTL_FLENDI, FLCTL_FLSTEI } }, + { 0xa40800a0, 0xa40800e0, 8, /* IMR8 / IMCR8 */ + { SDHI3, SDHI2, SDHI1, SDHI0, 0, 0, _2DG, SIU } }, + { 0xa40800a4, 0xa40800e4, 8, /* IMR9 / IMCR9 */ + { 0, 0, 0, CMT, 0, USB_USBI1, USB_USBI0, } }, + { 0xa40800a8, 0xa40800e8, 8, /* IMR10 / IMCR10 */ + { } }, + { 0xa40800ac, 0xa40800ec, 8, /* IMR11 / IMCR11 */ + { 0, RTC_CUI, RTC_PRI, RTC_ATI, 0, TPU, 0, TSIF } }, + { 0xa4140044, 0xa4140064, 8, /* INTMSK00 / INTMSKCLR00 */ + { IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7 } }, +}; + +static struct intc_prio_reg prio_registers[] = { + { 0xa4080000, 16, 4, /* IPRA */ { TMU0, TMU1, TMU2, IRDA } }, + { 0xa4080004, 16, 4, /* IPRB */ { JPU, LCDC, SIM } }, + { 0xa4080008, 16, 4, /* IPRC */ { } }, + { 0xa408000c, 16, 4, /* IPRD */ { } }, + { 0xa4080010, 16, 4, /* IPRE */ { DMAC0123, VIOVOU, 0, VPU } }, + { 0xa4080014, 16, 4, /* IPRF */ { KEYSC, DMAC45, USB, CMT } }, + { 0xa4080018, 16, 4, /* IPRG */ { SCIF0, SCIF1, SCIF2 } }, + { 0xa408001c, 16, 4, /* IPRH */ { SIOF0, SIOF1, FLCTL, I2C } }, + { 0xa4080020, 16, 4, /* IPRI */ { SIO, 0, TSIF, RTC } }, + { 0xa4080024, 16, 4, /* IPRJ */ { 0, 0, SIU } }, + { 0xa4080028, 16, 4, /* IPRK */ { 0, 0, 0, SDHI } }, + { 0xa408002c, 16, 4, /* IPRL */ { _2DG, 0, TPU } }, + { 0xa4140010, 32, 4, /* INTPRI00 */ + { IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7 } }, +}; + +static struct intc_sense_reg sense_registers[] = { + { 0xa414001c, 16, 2, /* ICR1 */ + { IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7 } }, +}; + +DECLARE_INTC_DESC(intc_desc, "sh7722", vectors, groups, priorities, + mask_registers, prio_registers, sense_registers); + void __init init_IRQ_ipr(void) { - register_ipr_controller(&ipr_irq_desc); + register_intc_controller(&intc_desc); } void __init plat_mem_setup(void) --- 0001/arch/sh/mm/Kconfig +++ work/arch/sh/mm/Kconfig 2007-07-18 09:18:54.000000000 +0900 @@ -217,7 +217,7 @@ config CPU_SUBTYPE_SH7722 bool "Support SH7722 processor" select CPU_SH4AL_DSP select CPU_SHX2 - select CPU_HAS_IPR_IRQ + select CPU_HAS_INTC_IRQ select ARCH_SPARSEMEM_ENABLE select SYS_SUPPORTS_NUMA |
From: Magnus D. <mag...@gm...> - 2007-07-18 01:21:30
|
sh: intc - shared IPR and INTC2 controller This patch implements a shared interrupt controller for the sh architecture. The thee main advantages with this controller over the exisitng ones are: - Both priority (ipr) and bitmap (intc2) registers are supported - External pin sense configuration is supported, ie edge vs level triggered - CPU/Board specific code maps 1:1 with datasheet for easy verification This controller can easily coexist with the current IPR and INTC2 controllers, but the idea is that CPU:s/Boards should be moved over to this controller over time so we have a single code base to maintain. Signed-off-by: Magnus Damm <da...@ig...> --- Tested on a Solution Engline 7722 Applies to git sh-2.6 a927beaf01291e299d8fda858e6c8837f2e9a14c arch/sh/Kconfig | 3 arch/sh/kernel/cpu/irq/Makefile | 1 arch/sh/kernel/cpu/irq/intc.c | 348 +++++++++++++++++++++++++++++++++++++++ include/asm-sh/hw_irq.h | 68 +++++++ 4 files changed, 420 insertions(+) --- 0001/arch/sh/Kconfig +++ work/arch/sh/Kconfig 2007-07-17 16:32:03.000000000 +0900 @@ -178,6 +178,9 @@ config CPU_HAS_PINT_IRQ config CPU_HAS_MASKREG_IRQ bool +config CPU_HAS_INTC_IRQ + bool + config CPU_HAS_INTC2_IRQ bool --- 0001/arch/sh/kernel/cpu/irq/Makefile +++ work/arch/sh/kernel/cpu/irq/Makefile 2007-07-17 16:32:03.000000000 +0900 @@ -6,4 +6,5 @@ obj-y += imask.o obj-$(CONFIG_CPU_HAS_IPR_IRQ) += ipr.o obj-$(CONFIG_CPU_HAS_PINT_IRQ) += pint.o obj-$(CONFIG_CPU_HAS_MASKREG_IRQ) += maskreg.o +obj-$(CONFIG_CPU_HAS_INTC_IRQ) += intc.o obj-$(CONFIG_CPU_HAS_INTC2_IRQ) += intc2.o --- /dev/null +++ work/arch/sh/kernel/cpu/irq/intc.c 2007-07-17 17:15:10.000000000 +0900 @@ -0,0 +1,348 @@ +/* + * Shared interrupt handling code for IPR and INT2C types of IRQs. + * + * Copyright (C) 2007 Magnus Damm + * + * Based on intc2.c and ipr.c + * + * Copyright (C) 1999 Niibe Yutaka & Takeshi Yaegashi + * Copyright (C) 2000 Kazumoto Kojima + * Copyright (C) 2001 David J. Mckay (dav...@st...) + * Copyright (C) 2003 Takashi Kusuda <kus...@hi...> + * Copyright (C) 2005, 2006 Paul Mundt + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + */ +#include <linux/init.h> +#include <linux/irq.h> +#include <linux/module.h> +#include <linux/io.h> +#include <linux/interrupt.h> + +#define _INTC_MK(fn, idx, bit, value) \ + ((fn) << 24 | ((value) << 16) | ((idx) << 8) | (bit)) +#define _INTC_FN(h) (h >> 24) +#define _INTC_VALUE(h) ((h >> 16) & 0xff) +#define _INTC_IDX(h) ((h >> 8) & 0xff) +#define _INTC_BIT(h) (h & 0xff) + +#define _INTC_PTR(desc, member, data) \ + (desc->member + _INTC_IDX(data)) + +static inline struct intc_desc *get_intc_desc(unsigned int irq) +{ + struct irq_chip *chip = get_irq_chip(irq); + return (void *)((char *)chip - offsetof(struct intc_desc, chip)); +} + +static inline unsigned int set_field(unsigned int value, + unsigned int field_value, + unsigned int width, + unsigned int shift) +{ + value &= ~(((1 << width) - 1) << shift); + value |= field_value << shift; + return value; +} + +static inline unsigned int set_prio_field(struct intc_desc *desc, + unsigned int value, + unsigned int priority, + unsigned int data) +{ + unsigned int width = _INTC_PTR(desc, prio_regs, data)->field_width; + + return set_field(value, priority, width, _INTC_BIT(data)); +} + +static void disable_prio_16(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, prio_regs, data)->reg; + + ctrl_outw(set_prio_field(desc, ctrl_inw(addr), 0, data), addr); +} + +static void enable_prio_16(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, prio_regs, data)->reg; + unsigned int prio = _INTC_VALUE(data); + + ctrl_outw(set_prio_field(desc, ctrl_inw(addr), prio, data), addr); +} + +static void disable_prio_32(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, prio_regs, data)->reg; + + ctrl_outl(set_prio_field(desc, ctrl_inl(addr), 0, data), addr); +} + +static void enable_prio_32(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, prio_regs, data)->reg; + unsigned int prio = _INTC_VALUE(data); + + ctrl_outl(set_prio_field(desc, ctrl_inl(addr), prio, data), addr); +} + +static void disable_mask_8(struct intc_desc *desc, unsigned int data) +{ + ctrl_outb(1 << _INTC_BIT(data), + _INTC_PTR(desc, mask_regs, data)->set_reg); +} + +static void enable_mask_8(struct intc_desc *desc, unsigned int data) +{ + ctrl_outb(1 << _INTC_BIT(data), + _INTC_PTR(desc, mask_regs, data)->clr_reg); +} + +static void disable_mask_32(struct intc_desc *desc, unsigned int data) +{ + ctrl_outl(1 << _INTC_BIT(data), + _INTC_PTR(desc, mask_regs, data)->set_reg); +} + +static void enable_mask_32(struct intc_desc *desc, unsigned int data) +{ + ctrl_outl(1 << _INTC_BIT(data), + _INTC_PTR(desc, mask_regs, data)->clr_reg); +} + +void (*intc_reg_fns[])(struct intc_desc *, unsigned int) = { + NULL, /* index 0 used as error code */ + enable_mask_8, disable_mask_8, + enable_mask_32, disable_mask_32, + enable_prio_16, disable_prio_16, + enable_prio_32, disable_prio_32, +}; + +static void intc_enable(unsigned int irq) +{ + struct intc_desc *desc = get_intc_desc(irq); + unsigned int data = (unsigned int) get_irq_chip_data(irq); + + intc_reg_fns[_INTC_FN(data)](desc, data); +} + +static void intc_disable(unsigned int irq) +{ + struct intc_desc *desc = get_intc_desc(irq); + unsigned int data = (unsigned int) get_irq_chip_data(irq); + + intc_reg_fns[_INTC_FN(data) + 1](desc, data); +} + +static void set_sense_16(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, sense_regs, data)->reg; + unsigned int width = _INTC_PTR(desc, sense_regs, data)->field_width; + unsigned int bit = _INTC_BIT(data); + unsigned int value = _INTC_VALUE(data); + + ctrl_outw(set_field(ctrl_inw(addr), value, width, bit), addr); +} + +static void set_sense_32(struct intc_desc *desc, unsigned int data) +{ + unsigned long addr = _INTC_PTR(desc, sense_regs, data)->reg; + unsigned int width = _INTC_PTR(desc, sense_regs, data)->field_width; + unsigned int bit = _INTC_BIT(data); + unsigned int value = _INTC_VALUE(data); + + ctrl_outl(set_field(ctrl_inl(addr), value, width, bit), addr); +} + +#define VALID(x) (x | 0x80) + +static unsigned char intc_irq_sense_table[IRQ_TYPE_SENSE_MASK + 1] = { + [IRQ_TYPE_EDGE_FALLING] = VALID(0), + [IRQ_TYPE_EDGE_RISING] = VALID(1), + [IRQ_TYPE_LEVEL_LOW] = VALID(2), + [IRQ_TYPE_LEVEL_HIGH] = VALID(3), +}; + +static int intc_set_sense(unsigned int irq, unsigned int type) +{ + struct intc_desc *desc = get_intc_desc(irq); + unsigned char value = intc_irq_sense_table[type & IRQ_TYPE_SENSE_MASK]; + unsigned int i, j, data, bit; + intc_enum enum_id = 0; + + for (i = 0; i < desc->nr_vectors; i++) { + struct intc_vect *vect = desc->vectors + i; + + if (evt2irq(vect->vect) != irq) + continue; + + enum_id = vect->enum_id; + break; + } + + if (!enum_id || !value) + return -EINVAL; + + value ^= VALID(0); + + for (i = 0; i < desc->nr_sense_regs; i++) { + struct intc_sense_reg *sr = desc->sense_regs + i; + + for (j = 0; j < ARRAY_SIZE(sr->enum_ids); j++) { + if (sr->enum_ids[j] != enum_id) + continue; + + bit = sr->reg_width - ((j + 1) * sr->field_width); + data = _INTC_MK(0, i, bit, value); + + switch(sr->reg_width) { + case 16: set_sense_16(desc, data); return 0; + case 32: set_sense_32(desc, data); return 0; + } + } + } + + return -EINVAL; +} + +static unsigned int __init intc_locate_reg_handler(void *fn) +{ + unsigned int i; + + for (i = 0; i < ARRAY_SIZE(intc_reg_fns); i++) + if (intc_reg_fns[i] == fn) + return i; + BUG(); + return 0; +} + +static unsigned int __init intc_find_mask_handler(unsigned int width) +{ + switch (width) { + case 8: return intc_locate_reg_handler(enable_mask_8); + case 32: return intc_locate_reg_handler(enable_mask_32); + } + + BUG(); + return 0; +} + +static unsigned int __init intc_find_prio_handler(unsigned int width) +{ + switch (width) { + case 16: return intc_locate_reg_handler(enable_prio_16); + case 32: return intc_locate_reg_handler(enable_prio_32); + } + + BUG(); + return 0; +} + +static unsigned int __init intc_prio_value(struct intc_desc *desc, + intc_enum enum_id) +{ + unsigned int i; + + for (i = 0; i < desc->nr_priorities; i++) { + struct intc_prio *p = desc->priorities + i; + + if (p->enum_id != enum_id) + continue; + + return p->priority; + } + + return 1; /* default to the lowest priority if no priority is set */ +} + +static unsigned int __init intc_mask_data(struct intc_desc *desc, + intc_enum enum_id) +{ + unsigned int i, j, fn; + + for (i = 0; i < desc->nr_mask_regs; i++) { + struct intc_mask_reg *mr = desc->mask_regs + i; + + for (j = 0; j < ARRAY_SIZE(mr->enum_ids); j++) { + if (mr->enum_ids[j] != enum_id) + continue; + + fn = intc_find_mask_handler(mr->reg_width); + if (!fn) + return 0; + + return _INTC_MK(fn, i, (mr->reg_width - 1) - j, 0); + } + } + + return 0; +} + +static unsigned int __init intc_prio_data(struct intc_desc *desc, + intc_enum enum_id) +{ + unsigned int i, j, fn, bit, prio; + + for (i = 0; i < desc->nr_prio_regs; i++) { + struct intc_prio_reg *pr = desc->prio_regs + i; + + for (j = 0; j < ARRAY_SIZE(pr->enum_ids); j++) { + if (pr->enum_ids[j] != enum_id) + continue; + + fn = intc_find_prio_handler(pr->reg_width); + if (!fn) + return 0; + + prio = intc_prio_value(desc, enum_id); + bit = pr->reg_width - ((j + 1) * pr->field_width); + + BUG_ON(bit < 0); + + return _INTC_MK(fn, i, bit, prio); + } + } + + return 0; +} + +static void __init intc_register_irq(struct intc_desc *desc, intc_enum enum_id, + unsigned int irq) +{ + unsigned int mask_data = intc_mask_data(desc, enum_id); + unsigned int prio_data = intc_prio_data(desc, enum_id); + unsigned int data = mask_data ? mask_data : prio_data; + + BUG_ON(!data); + + disable_irq_nosync(irq); + set_irq_chip_and_handler_name(irq, &desc->chip, + handle_level_irq, "level"); + set_irq_chip_data(irq, (void *)data); + + /* set priority */ + + if (prio_data) + intc_reg_fns[_INTC_FN(prio_data)](desc, prio_data); + + /* irq should be disabled by default */ + + desc->chip.mask(irq); +} + +void __init register_intc_controller(struct intc_desc *desc) +{ + unsigned int i; + + desc->chip.mask = intc_disable; + desc->chip.unmask = intc_enable; + desc->chip.mask_ack = intc_disable; + desc->chip.set_type = intc_set_sense; + + for (i = 0; i < desc->nr_vectors; i++) { + struct intc_vect *vect = desc->vectors + i; + + intc_register_irq(desc, vect->enum_id, evt2irq(vect->vect)); + } +} --- 0001/include/asm-sh/hw_irq.h +++ work/include/asm-sh/hw_irq.h 2007-07-17 16:32:03.000000000 +0900 @@ -1,6 +1,7 @@ #ifndef __ASM_SH_HW_IRQ_H #define __ASM_SH_HW_IRQ_H +#include <linux/init.h> #include <asm/atomic.h> extern atomic_t irq_err_count; @@ -47,4 +48,71 @@ void init_IRQ_ipr(void); */ void ipr_irq_enable_irlm(void); +typedef unsigned char intc_enum; + +struct intc_vect { + intc_enum enum_id; + unsigned short vect; +}; + +#define INTC_VECT(enum_id, vect) { enum_id, vect } + +struct intc_prio { + intc_enum enum_id; + unsigned char priority; +}; + +#define INTC_PRIO(enum_id, prio) { enum_id, prio } + +struct intc_group { + intc_enum enum_id; + intc_enum *enum_ids; +}; + +#define INTC_GROUP(enum_id, ids...) { enum_id, (intc_enum []) { ids, 0 } } + +struct intc_mask_reg { + unsigned long set_reg, clr_reg, reg_width; + intc_enum enum_ids[32]; +}; + +struct intc_prio_reg { + unsigned long reg, reg_width, field_width; + intc_enum enum_ids[16]; +}; + +struct intc_sense_reg { + unsigned long reg, reg_width, field_width; + intc_enum enum_ids[16]; +}; + +struct intc_desc { + struct intc_vect *vectors; + unsigned int nr_vectors; + struct intc_group *groups; + unsigned int nr_groups; + struct intc_prio *priorities; + unsigned int nr_priorities; + struct intc_mask_reg *mask_regs; + unsigned int nr_mask_regs; + struct intc_prio_reg *prio_regs; + unsigned int nr_prio_regs; + struct intc_sense_reg *sense_regs; + unsigned int nr_sense_regs; + struct irq_chip chip; +}; + +#define _INTC_ARRAY(a) a, sizeof(a)/sizeof(*a) +#define DECLARE_INTC_DESC(symbol, chipname, vectors, groups, \ + priorities, mask_regs, prio_regs, sense_regs) \ +static struct intc_desc symbol = { \ + _INTC_ARRAY(vectors), _INTC_ARRAY(groups), \ + _INTC_ARRAY(priorities), \ + _INTC_ARRAY(mask_regs), _INTC_ARRAY(prio_regs), \ + _INTC_ARRAY(sense_regs), \ + .chip.name = chipname, \ +} + +void __init register_intc_controller(struct intc_desc *desc); + #endif /* __ASM_SH_HW_IRQ_H */ |
From: Paul M. <le...@li...> - 2007-07-17 11:01:50
|
On Tue, Jul 17, 2007 at 06:24:53AM -0400, Jeff Garzik wrote: > It's just reality that there are never enough people to verify every > patch before it goes in. We just support way too much hardware for that > to be remotely feasible. Sure we -try- to keep the driver maintainer > CC'd, but alas we are human. > Try? I've never _once_ received a CC from you regarding a change to pata_platform. The only time I've been CC'ed at all is when someone submitting the patch had the common courtesy to do so. Whereas the number of times I've had to clean up after something merged behind my back has been higher than the number of times I've been CC'ed on any of these changes. > Your thinking is flawed if you think I'm going to hold up every patch > until it's verified on each of 63 ATA controller drivers, when I make a > core change, for example. Not scalable. We scale in another way: > This has nothing to do with core changes that impact every driver, this has to do with isolated changes to a _single_ driver that you're obviously not in a position to test. That's a very different situation. Again, if you can't be bothered to CC people on changes to their drivers that aren't libata-wide, don't apply them in the first place. I would much rather play API catch up with my driver than have to backtrack and figure out what went wrong when suddenly all of my boards stop booting. Your "merge first and hope someone else notices and fixes it later" approach is insane. We've never done kernel development like that, libata isn't special. |
From: Jeff G. <je...@ga...> - 2007-07-17 10:24:58
|
Paul Mundt wrote: > On Tue, Jul 17, 2007 at 05:33:00AM -0400, Jeff Garzik wrote: >> Paul Mundt wrote: >>> It would be great if libata people could actually be bothered to CC >>> driver authors on driver changes so that way these things don't get >>> completely broken in mainline when simple testing on the platforms >>> that actually _rely_ on this driver would have shown that this was >>> broken. >> The patch lived for weeks in -mm along with tons of other git trees >> Andrew pulls. If you want a single point to watch for upcoming stuff, >> test the -mm trees. It's a key part of the development process: I >> merge a patch, -mm tree pulls my tree and others, people test and >> complain and give feedback, ... >> > A key part of the development process is making sure that driver authors > are aware of the changes being made to their drivers, so they're able to > ACK/NACK or at least point out something that's obviously wrong. I test > -mm when time permits, and this happened to slip through. If I had > actually been CC'ed on it, it would not have. > > Your entire process is fundamentally flawed if you're merging the patch > first and expecting people to only find out if it's broken after the > fact. In the best case it leaves -mm broken for a single release, and in > the other case, it happens to make its way to mainline before anyone > notices. It's just reality that there are never enough people to verify every patch before it goes in. We just support way too much hardware for that to be remotely feasible. Sure we -try- to keep the driver maintainer CC'd, but alas we are human. Your thinking is flawed if you think I'm going to hold up every patch until it's verified on each of 63 ATA controller drivers, when I make a core change, for example. Not scalable. We scale in another way: We have the biggest test lab in the world -- the Internet -- and a development process staged so that testing and development occur in parallel. This here is actually an example of the process working: despite my forgetting to CC you, the problem was caught long before it made it into any release kernel. Jeff |
From: Paul M. <le...@li...> - 2007-07-17 09:47:48
|
On Tue, Jul 17, 2007 at 05:33:00AM -0400, Jeff Garzik wrote: > Paul Mundt wrote: > >It would be great if libata people could actually be bothered to CC > >driver authors on driver changes so that way these things don't get > >completely broken in mainline when simple testing on the platforms > >that actually _rely_ on this driver would have shown that this was > >broken. > > The patch lived for weeks in -mm along with tons of other git trees > Andrew pulls. If you want a single point to watch for upcoming stuff, > test the -mm trees. It's a key part of the development process: I > merge a patch, -mm tree pulls my tree and others, people test and > complain and give feedback, ... > A key part of the development process is making sure that driver authors are aware of the changes being made to their drivers, so they're able to ACK/NACK or at least point out something that's obviously wrong. I test -mm when time permits, and this happened to slip through. If I had actually been CC'ed on it, it would not have. Your entire process is fundamentally flawed if you're merging the patch first and expecting people to only find out if it's broken after the fact. In the best case it leaves -mm broken for a single release, and in the other case, it happens to make its way to mainline before anyone notices. > With embedded stuff its tough to judge whether people are knowledgeable > about the impact of the change, and sometimes I judge wrongly. My > apologies. > Another reason to make sure the authors are CC'ed. I really don't see why this is so difficult for you, _everyone_ else manages to do this properly, and shis sort of case illustrates _exactly_ why. > What is your suggestion for moving linux-2.6.git forward? > The patch from Magnus is fine with me for fixing this particular problem, so at least getting that merged quickly will get the sh and ppc platforms fixed again. To avoid having this happen again in the future, I'd appreciate being CC'ed on things that impact pata_platform pre-merge, and again, I don't see this as an extraordinarly unreasonable request. If you can't be bothered doing that, then just stop applying pata_platform patches, and I'll merge them myself. |
From: Jeff G. <je...@ga...> - 2007-07-17 09:33:06
|
Paul Mundt wrote: > On Tue, Jul 17, 2007 at 05:42:52PM +0900, Magnus Damm wrote: >> pata_platform: Fix NULL pointer dereference >> >> The platform-specific structures may leave pdev->dev.platform_data as NULL. >> >> Signed-off-by: Magnus Damm <da...@ig...> > > Looks like the change that broke this came in the libata merge, more > specifically this change: > > commit 5f45bc50976ee1f408f7171af155aec646655a37 > Author: Sonic Zhang <son...@gm...> > Date: Fri Jun 15 17:45:49 2007 +0800 > > Add irq_flags to struct pata_platform_info > > On some embedded platforms, such as blackfin, the gpio interrupt for > IDE interface is designed to be triggered with high voltage. The gpio > port should be configured properly by set_irq_type() when register > the irq. This patch enable the generic pata platform driver to > accept platform irq flags data. > > Signed-off-by: Sonic Zhang <son...@gm...> > Signed-off-by: Jeff Garzik <je...@ga...> > > It would be great if libata people could actually be bothered to CC driver > authors on driver changes so that way these things don't get completely broken > in mainline when simple testing on the platforms that actually _rely_ on this > driver would have shown that this was broken. > > I don't intend to poll the various libata branches on the off chance I'll find > something that's hosed my platforms, and I don't think it's an unreasonable > expectation to at least have to see the patch and sign off on it before it gets > merged. Every other subsystem works this way, I wonder why libata feels that > it's special. > > This is also not the first time changes to pata_platform have caused fallout, > without finding out about it until after the changes were already merged. The patch lived for weeks in -mm along with tons of other git trees Andrew pulls. If you want a single point to watch for upcoming stuff, test the -mm trees. It's a key part of the development process: I merge a patch, -mm tree pulls my tree and others, people test and complain and give feedback, ... With embedded stuff its tough to judge whether people are knowledgeable about the impact of the change, and sometimes I judge wrongly. My apologies. What is your suggestion for moving linux-2.6.git forward? Jeff |
From: Paul M. <le...@li...> - 2007-07-17 09:09:13
|
On Tue, Jul 17, 2007 at 05:43:10PM +0900, Magnus Damm wrote: > sh: Fix irq assignment for uarts on sh7722 > > This patch contains two serial port related fixes for sh7722: > - Make sure the irqs for the first serial port is correct > - Add the second and third serial port to the platform data > > Signed-off-by: Magnus Damm <da...@ig...> Applied, thanks. |
From: Paul M. <le...@li...> - 2007-07-17 09:03:48
|
On Tue, Jul 17, 2007 at 05:42:52PM +0900, Magnus Damm wrote: > pata_platform: Fix NULL pointer dereference > > The platform-specific structures may leave pdev->dev.platform_data as NULL. > > Signed-off-by: Magnus Damm <da...@ig...> Looks like the change that broke this came in the libata merge, more specifically this change: commit 5f45bc50976ee1f408f7171af155aec646655a37 Author: Sonic Zhang <son...@gm...> Date: Fri Jun 15 17:45:49 2007 +0800 Add irq_flags to struct pata_platform_info On some embedded platforms, such as blackfin, the gpio interrupt for IDE interface is designed to be triggered with high voltage. The gpio port should be configured properly by set_irq_type() when register the irq. This patch enable the generic pata platform driver to accept platform irq flags data. Signed-off-by: Sonic Zhang <son...@gm...> Signed-off-by: Jeff Garzik <je...@ga...> It would be great if libata people could actually be bothered to CC driver authors on driver changes so that way these things don't get completely broken in mainline when simple testing on the platforms that actually _rely_ on this driver would have shown that this was broken. I don't intend to poll the various libata branches on the off chance I'll find something that's hosed my platforms, and I don't think it's an unreasonable expectation to at least have to see the patch and sign off on it before it gets merged. Every other subsystem works this way, I wonder why libata feels that it's special. This is also not the first time changes to pata_platform have caused fallout, without finding out about it until after the changes were already merged. |
From: Magnus D. <mag...@gm...> - 2007-07-17 08:43:59
|
sh: Fix irq assignment for uarts on sh7722 This patch contains two serial port related fixes for sh7722: - Make sure the irqs for the first serial port is correct - Add the second and third serial port to the platform data Signed-off-by: Magnus Damm <da...@ig...> --- Tested on a Solution Engline 7722 Applies to git linux-2.6 a5fcaa210626a79465321e344c91a6a7dc3881fa arch/sh/configs/se7722_defconfig | 2 +- arch/sh/kernel/cpu/sh4a/setup-sh7722.c | 25 +++++++++++++++++++------ 2 files changed, 20 insertions(+), 7 deletions(-) --- 0001/arch/sh/configs/se7722_defconfig +++ work/arch/sh/configs/se7722_defconfig 2007-07-13 19:05:22.000000000 +0900 @@ -565,7 +565,7 @@ CONFIG_SERIO_LIBPS2=y # Non-8250 serial port support # CONFIG_SERIAL_SH_SCI=y -CONFIG_SERIAL_SH_SCI_NR_UARTS=2 +CONFIG_SERIAL_SH_SCI_NR_UARTS=3 CONFIG_SERIAL_SH_SCI_CONSOLE=y CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y --- 0001/arch/sh/kernel/cpu/sh4a/setup-sh7722.c +++ work/arch/sh/kernel/cpu/sh4a/setup-sh7722.c 2007-07-11 17:21:20.000000000 +0900 @@ -19,8 +19,21 @@ static struct plat_sci_port sci_platform .mapbase = 0xffe00000, .flags = UPF_BOOT_AUTOCONF, .type = PORT_SCIF, - .irqs = { 80, 81, 83, 82 }, - }, { + .irqs = { 80, 80, 80, 80 }, + }, + { + .mapbase = 0xffe10000, + .flags = UPF_BOOT_AUTOCONF, + .type = PORT_SCIF, + .irqs = { 81, 81, 81, 81 }, + }, + { + .mapbase = 0xffe20000, + .flags = UPF_BOOT_AUTOCONF, + .type = PORT_SCIF, + .irqs = { 82, 82, 82, 82 }, + }, + { .flags = 0, } }; @@ -48,10 +61,10 @@ static struct ipr_data ipr_irq_table[] = /* IRQ, IPR-idx, shift, prio */ { 16, 0, 12, 2 }, /* TMU0 */ { 17, 0, 8, 2 }, /* TMU1 */ - { 80, 6, 12, 3 }, /* SCIF ERI */ - { 81, 6, 12, 3 }, /* SCIF RXI */ - { 82, 6, 12, 3 }, /* SCIF BRI */ - { 83, 6, 12, 3 }, /* SCIF TXI */ + { 80, 6, 12, 3 }, /* SCIF0 */ + { 81, 6, 8, 3 }, /* SCIF1 */ + { 82, 6, 4, 3 }, /* SCIF2 */ + }; static unsigned long ipr_offsets[] = { |
From: Magnus D. <mag...@gm...> - 2007-07-17 08:43:39
|
pata_platform: Fix NULL pointer dereference The platform-specific structures may leave pdev->dev.platform_data as NULL. Signed-off-by: Magnus Damm <da...@ig...> --- Tested on a Solution Engline 7722 Applies to git linux-2.6 a5fcaa210626a79465321e344c91a6a7dc3881fa drivers/ata/pata_platform.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) --- 0001/drivers/ata/pata_platform.c +++ work/drivers/ata/pata_platform.c 2007-07-17 15:01:09.000000000 +0900 @@ -213,8 +213,9 @@ static int __devinit pata_platform_probe pata_platform_setup_port(&ap->ioaddr, pp_info); /* activate */ - return ata_host_activate(host, platform_get_irq(pdev, 0), ata_interrupt, - pp_info->irq_flags, &pata_platform_sht); + return ata_host_activate(host, platform_get_irq(pdev, 0), + ata_interrupt, pp_info ? pp_info->irq_flags + : 0, &pata_platform_sht); } /** |
From: Paul M. <le...@li...> - 2007-07-17 04:55:26
|
On Mon, Jul 16, 2007 at 01:49:03PM -0700, Kristoffer Ericson wrote: > * io.c found in arch/sh/cchips/hd6446x/hd64461/ directory was used to translate PIO -> MMIO. Since we have moved away from PIO this file is useless. > * All io functions are now handled by generic mapping > > signed-off-by: Kristoffer Ericson <Kri...@gm...> > Thanks, I took this a step further and consolidated down to a hd64461.c. Applied and pushed out. |
From: Adrian M. <ad...@ne...> - 2007-07-16 22:28:30
|
More on this... Code seemed to be failing on this: if (atomic_xchg(&channel->busy, 1)) atomic_xchg expands out to this: #define atomic_xchg(v, new) (xchg(&((v)->counter), new)) and in sh xchg expands out to this: #define xchg(ptr,x) \ ((__typeof__(*(ptr)))__xchg((ptr),(unsigned long)(x), sizeof(*(ptr)))) But this has a slightly different format in other archs - eg i386: #define xchg(ptr,v) ((__typeof__(*(ptr)))__xchg((unsigned long)(v),(ptr),sizeof(*(ptr)))) arm - #define xchg(ptr,x) \ ((__typeof__(*(ptr)))__xchg((unsigned long)(x),(ptr),sizeof(*(ptr)))) MIPS #define xchg(ptr,x) ((__typeof__(*(ptr)))__xchg((unsigned long)(x),(ptr),sizeof(*(ptr)))) So I wondered if it was the reversal of the params that was the issue and did this quick and very dirty hack --- #define xchg(ptr,x) \ ((__typeof__(*(ptr)))__xchg((ptr),(unsigned long)(x), sizeof(*(ptr)))) #define xchg_dma(ptr, x) \ ((__typeof__(*(ptr)))__xchg((unsigned long)(x),(ptr),sizeof(*(ptr)))) and changing atomic_chg to this: #define atomic_xchg(v, new) (xchg_dma(&((v)->counter), new)) But, as with most quick and dirty hacks, it didn't work... Linux version 2.6.22-gc2dc1ad5-dirty (adrian@bossclass) (gcc version 3.4.6) #12 PREEMPT Mon Jul 16 23:16:34 BST 2007 console [sercon0] enabled Booting machvec: Sega Dreamcast Node 0: start_pfn = 0xc000, low = 0xd000 Zone PFN ranges: Normal 49152 -> 53248 early_node_map[1] active PFN ranges 0: 49152 -> 53248 Built 1 zonelists in Zone order. Total pages: 4064 Kernel command line: console=ttySC1,115200 panic=3 root=/dev/nfs rw nfsaddrs=192.168.61.55:192.168.61.50:192.168.61.50: earlyprintk=serial PID hash table entries: 64 (order: 6, 256 bytes) Using tmu for system timer Using 12.469 MHz high precision timer. Console: colour dummy device 80x25 Dentry cache hash table entries: 2048 (order: 1, 8192 bytes) Inode-cache hash table entries: 1024 (order: 0, 4096 bytes) Memory: 14104k/16384k available (1499k kernel code, 444k data, 72k init) PVR=040205c1 CVR=00000000 PRR=00000000 I-cache : n_ways=1 n_sets=256 way_incr=8192 I-cache : entry_mask=0x00001fe0 alias_mask=0x00001000 n_aliases=2 D-cache : n_ways=1 n_sets=512 way_incr=16384 D-cache : entry_mask=0x00003fe0 alias_mask=0x00003000 n_aliases=4 Mount-cache hash table entries: 512 CPU: SH7750 NET: Registered protocol family 16 DMA: Registering DMA API. DMA: Registering sh_dmac handler (4 channels). Fault in unaligned fixup: 0000 [#1] Modules linked in: Pid : 1, Comm: swapper PC is at request_dma+0x2e/0x88 PC : 8c10d66a SP : 8c255f30 SR : 400000f1 TEA : 00000001 Not tainted R0 : 00000000 R1 : 00000001 R2 : 8c24c538 R3 : 40000001 R4 : 00000084 R5 : 00000084 R6 : 00000004 R7 : 8c24c400 R8 : 8c24c508 R9 : 00000000 R10 : 8c1e22f0 R11 : 8c1b2fec R12 : 00000000 R13 : 8c1fb370 R14 : 00000000 MACH: 00000000 MACL: 00000108 GBR : 00000000 PR : 8c10d656 Call trace: [<8c1f403a>] pvr2_dma_init+0x12/0x34 [<8c1ea848>] kernel_init+0x90/0x244 [<8c0035e4>] kernel_thread_helper+0x4/0x10 [<8c1ea7b8>] kernel_init+0x0/0x244 [<8c0035e0>] kernel_thread_helper+0x0/0x10 Process: swapper (pid: 1, stack limit = 8c254001) Stack: (0x8c255f30 to 0x8c256000) 5f20: 8c1f403a 00000000 00000000 00000000 5f40: 00000000 8c1ea848 00000000 00000000 00000000 00000000 00000000 00000000 5f60: 00000000 00000000 00000000 00000000 00000001 00000000 00000000 00000000 5f80: 8c0035e4 00000000 00000000 00000000 00000000 00000000 00000000 00000000 5fa0: 00000000 00000000 00000000 00000000 00000000 8c1ea7b8 00000000 00000000 5fc0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 8c255fa0 5fe0: 8c0035e0 00000000 40000000 00000000 00000000 00000000 00000000 00000000 Kernel panic - not syncing: Attempted to kill init! Rebooting in 3 seconds.. |
From: Paul M. <le...@li...> - 2007-07-16 22:05:52
|
On Mon, Jul 16, 2007 at 11:47:40PM -0700, Kristoffer Ericson wrote: > Paul could you just give this a check. Im working on scan_keyb and that should be ready tommorow. > > This patch is based on what andriy made with my additions : > Keymap now uses KEY_X instead of 0x00.. > Fixed for dead keys, so they all work. > Please take this up with Dmitry (added to CC), that's where these things end up going anyways.. > diff --git a/drivers/input/keyboard/hp680_keyb.c b/drivers/input/keyboard/hp680_keyb.c > new file mode 100644 > index 0000000..2890668 > --- /dev/null > +++ b/drivers/input/keyboard/hp680_keyb.c > @@ -0,0 +1,218 @@ > +/* > + * drivers/input/keyboard/hp680_keyb.c > + * > + * HP Jornada 680/690 scan keyboard > + * > + * Copyright (C) 2005 Andriy Skulysh > + * Copyright (C) 2006 Paul Mundt > + * Copyright (C) 2007 Kristoffer Ericson <Kri...@gm...> > + * > + * Splitted from drivers/input/keyboard/hp600_keyb.c > + * > + * Copyright (C) 2000 YAEGASHI Takeshi > + * HP600 keyboard scan routine and translation table > + * Copyright (C) 2000 Niibe Yutaka > + * HP620 keyboard translation table > + */ > +#include <linux/input.h> > +#include <linux/kernel.h> > +#include <linux/module.h> > +#include <linux/init.h> > +#include <asm/delay.h> > +#include <asm/io.h> > +#include "scan_keyb.h" > + > +#define PCCR 0xa4000104 > +#define PDCR 0xa4000106 > +#define PECR 0xa4000108 > +#define PFCR 0xa400010a > +#define PCDR 0xa4000124 > +#define PDDR 0xa4000126 > +#define PEDR 0xa4000128 > +#define PFDR 0xa400012a > +#define PGDR 0xa400012c > +#define PHDR 0xa400012e > +#define PJDR 0xa4000130 > +#define PKDR 0xa4000132 > +#define PLDR 0xa4000134 > + > +/*************************************************************** > +HP Jornada 680(SWEDISH version) keyboard > +[!] indicates Special Characters > +______________________________________________________________________ > +| ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 POWER| > +| 1 2 3 4 5 6 7 8 9 0 + ` BKPSPACE| > +|* Q W E R T Y U I O P ! ^ ENTER| > +| TAB A S D F G H J K L ! ! ' ENTER| > +| SHIFT Z X C V B N M , . - UP SHIFT| > +| CTRL WIN ALT ? =======SPACE======== ALTG DEL LEF DO RI ] > +----------------------------------------------------------------------- > +****************************************************************/ > + > +/**************************************************************** > +HP Jornada 690(Japanese version) keyboard scan matrix > + > + PTC7 PTC6 PTC5 PTC4 PTC3 PTC2 PTC1 PTC0 > +PTD1 REC Escape on/off Han/Zen Hira Eisu > +PTD5 REC Z on/off Enter : / > +PTD7 REC Right Down > +PTE0 REC Windows on/off > +PTE1 REC A on/off ] [ ; > +PTE3 REC Tab on/off ShirtR \ Up > +PTE6 REC Q on/off BS @ P > +PTE7 REC 1 on/off ^ - 0 > + > + PTF7 PTF6 PTF5 PTF4 PTF3 PTF2 PTF1 PTF0 > +PTD1 F5 F4 F6 F7 F8 F3 F2 F1 > +PTD5 N B M , . V C X > +PTD7 Muhen Alt Left > +PTE0 Henkan _ Del Space Ctrl > +PTE1 H G J K L F D S > +PTE3 ShiftL > +PTE6 Y T U I O R E W > +PTE7 6 5 7 8 9 4 3 2 > + > + PTG5 PTG4 PTG3 PTG0 PTH0 > +* REC REW FWW Cover on/off > + > + > + 7 6 5 4 3 2 1 0 > +C: 0xffff 0xdf IP IP IP IP IP IP IP IP > +D: 0x6786 0x59 O I O IP I F O I > +E: 0x5045 0x00 O O F F O F O O > +F: 0xffff 0xff IP IP IP IP IP IP IP IP > +G: 0xaffe 0xfd I I IP IP IP IP IP I > +H: 0x70f2 0x49 O IP F F IP IP F I > +J: 0x0704 0x22 F F O IP F F O F > +K: 0x0100 0x10 F F F O F F F F > +L: 0x0c3c 0x26 F F IP F F IP IP F > + > +****************************************************************/ > + > +static const unsigned char hp680kbd_scancodes[] = { > + /* PTD1 */ > + KEY_CAPSLOCK, KEY_MACRO, KEY_LEFTCTRL, KEY_RESERVED, KEY_ESC, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_F1, KEY_F2, KEY_F3, KEY_F8, KEY_F7, KEY_F2, > + KEY_F4, KEY_F5, > + > + /* PTD5 */ > + KEY_SLASH, KEY_APOSTROPHE, KEY_ENTER, KEY_RESERVED, KEY_Z, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_X, KEY_C, KEY_V, KEY_DOT, KEY_COMMA, > + KEY_M, KEY_B, KEY_N, > + > + /* PTD7 */ > + KEY_KP2, KEY_KP6, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_KP4, > + KEY_RESERVED, KEY_RESERVED, KEY_LEFTALT, KEY_HANJA, > + > + /* PTE0 */ > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_FINANCE, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_LEFTCTRL, KEY_RESERVED, KEY_SPACE, KEY_KPDOT, > + KEY_VOLUMEUP, 249, KEY_RESERVED, KEY_RESERVED, > + > + /* PTE1 */ > + KEY_SEMICOLO, KEY_RIGHTBRACE, KEY_BACKSLASH, KEY_RESERVED, KEY_A, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_S, KEY_D, KEY_F, KEY_L, KEY_K, KEY_J, KEY_G, KEY_H, > + > + /* PTE3 */ > + KEY_KP8, KEY_LEFTMETA, KEY_RIGHTSHIFT, KEY_RESERVED, KEY_TAB, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_LEFTSHIFT, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > + > + /* PTE6 */ > + KEY_P, KEY_LEFTBRACE, KEY_BACKSPACE, KEY_RESERVED, KEY_Q, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_W, KEY_E, KEY_R, KEY_O, KEY_I, KEY_U, KEY_T, KEY_R, > + > + /* PTE7 */ > + KEY_0, KEY_MINUS, KEY_EQUAL, KEY_RESERVED, KEY_1, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_2, KEY_3, KEY_4, KEY_9, KEY_8, KEY_7, KEY_5, KEY_6, > + > + /* **** */ > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, > +}; > + > +static int hp680_japanese_scan_kbd(unsigned char *s) > +{ > + int i; > + unsigned short ec_static,dc_static; /* = UINT16_t */ > + unsigned char matrix_switch[] = { > + 0xfd, 0xff, /* PTD1 PD(1) */ > + 0xdf, 0xff, /* PTD5 PD(5) */ > + 0x7f, 0xff, /* PTD7 PD(7) */ > + 0xff, 0xfe, /* PTE0 PE(0) */ > + 0xff, 0xfd, /* PTE1 PE(1) */ > + 0xff, 0xf7, /* PTE3 PE(3) */ > + 0xff, 0xbf, /* PTE6 PE(6) */ > + 0xff, 0x7f, /* PTE7 PE(7) */ > + }, *t=matrix_switch; > + /* PD(x) : > + 1. 0xcc0c & (1~(1 << (2*(x)+1))))) > + 2. (0xf0cf & 0xfffff) */ > + /* PE(x) : > + 1. 0xcc0c & 0xffff > + 2. 0xf0cf & (1~(1 << (2*(x)+1))))) */ > + unsigned short matrix_PDE[] = { > + 0xcc04, 0xf0cf, /* PD(1) */ > + 0xc40c, 0xf0cf, /* PD(5) */ > + 0x4c0c, 0xf0cf, /* PD(7) */ > + 0xcc0c, 0xf0cd, /* PE(0) */ > + 0xcc0c, 0xf0c7, /* PE(1) */ > + 0xcc0c, 0xf04f, /* PE(3) */ > + 0xcc0c, 0xd0cf, /* PE(6) */ > + 0xcc0c, 0x70cf, /* PE(7) */ > + }, *y=matrix_PDE; > + /* Save these control reg bits */ > + dc_static = (ctrl_inw(PDCR) & (~0xcc0c)); > + ec_static = (ctrl_inw(PECR) & (~0xf0cf)); > + > + for (i=0; i<8; i++) { > + /* disable output for all but the one we want to scan */ > + ctrl_outw((dc_static | *y++), PDCR); > + ctrl_outw((ec_static | *y++), PECR); > + udelay(5); > + > + /* Get scanline row */ > + ctrl_outb(*t++, PDDR); > + ctrl_outb(*t++, PEDR); > + udelay(50); > + > + /* Read data */ > + *s++=ctrl_inb(PCDR); > + *s++=ctrl_inb(PFDR); > + } > + /* Scan no lines */ > + ctrl_outb(0xff, PDDR); > + ctrl_outb(0xff, PEDR); > + > + /* Enable all scanlines */ > + ctrl_outw((dc_static | (0x5555 & 0xcc0c)),PDCR); > + ctrl_outw((ec_static | (0x5555 & 0xf0cf)),PECR); > + /* Ignore extra keys and events */ > + *s++=ctrl_inb(PGDR); > + *s++=ctrl_inb(PHDR); > + > + return 0; > +} > + > +static struct scan_keyboard hp680_kbd = { > + .scan = hp680_japanese_scan_kbd, > + .table = hp680_japanese_table, > + .length = 16, > +}; > + > +static int __init hp680_kbd_init_hw(void) > +{ > + printk(KERN_INFO "HP680 matrix scan keyboard registered\n"); > + return register_scan_keyboard(&hp680_kbd); > +} > + > +static void __exit hp680_kbd_exit_hw(void) > +{ > + unregister_scan_keyboard(&hp680_kbd); > +} > + > +module_init(hp680_kbd_init_hw); > +module_exit(hp680_kbd_exit_hw); > +MODULE_LICENSE("GPL"); |
From: Adrian M. <ad...@ne...> - 2007-07-16 21:56:06
|
On Tue, 2007-07-17 at 06:08 +0900, Paul Mundt wrote: > > That's certainly not good. I suppose I'll have to plug in some dummy > DMACs and hash out where things went wrong. I'll take a look at it later > today. > > Should also probably redo the dependencies so we're not able to > artificially change the number of channels (or better yet, let the > platform device take care of it). Finally managed to test this properly with earlyprintk - here is the output - much as with the module insertion: Linux version 2.6.22-gc2dc1ad5 (adrian@bossclass) (gcc version 3.4.6) #10 PREEMPT Mon Jul 16 22:52:32 BST 2007 console [sercon0] enabled Booting machvec: Sega Dreamcast Node 0: start_pfn = 0xc000, low = 0xd000 Zone PFN ranges: Normal 49152 -> 53248 early_node_map[1] active PFN ranges 0: 49152 -> 53248 Built 1 zonelists in Zone order. Total pages: 4064 Kernel command line: console=ttySC1,115200 panic=3 root=/dev/nfs rw nfsaddrs=192.168.61.55:192.168.61.50:192.168.61.50: earlyprintk=serial PID hash table entries: 64 (order: 6, 256 bytes) Using tmu for system timer Using 12.469 MHz high precision timer. Console: colour dummy device 80x25 Dentry cache hash table entries: 2048 (order: 1, 8192 bytes) Inode-cache hash table entries: 1024 (order: 0, 4096 bytes) Memory: 14104k/16384k available (1499k kernel code, 444k data, 72k init) PVR=040205c1 CVR=00000000 PRR=00000000 I-cache : n_ways=1 n_sets=256 way_incr=8192 I-cache : entry_mask=0x00001fe0 alias_mask=0x00001000 n_aliases=2 D-cache : n_ways=1 n_sets=512 way_incr=16384 D-cache : entry_mask=0x00003fe0 alias_mask=0x00003000 n_aliases=4 Mount-cache hash table entries: 512 CPU: SH7750 NET: Registered protocol family 16 DMA: Registering DMA API. DMA: Registering sh_dmac handler (4 channels). DMA: Registering pvr2_dmac handler (1 channel). DMA: Registering g2_dmac handler (4 channels). Autoconfig PCI channel 0x8c1e23f0 Scanning bus 00, I/O 0x01001600:0x01003600, Mem 0x01840000:0x01848000 00:00.0 Class 0200: 11db:1234 (rev 10) I/O at 0x01001600 [size=0x100] Mem at 0x01840000 [size=0x100] PCI: Fixing up device 0000:00:00.0 Time: SuperH clocksource has been installed. NET: Registered protocol family 2 IP route cache hash table entries: 1024 (order: 0, 4096 bytes) TCP established hash table entries: 512 (order: 0, 4096 bytes) TCP bind hash table entries: 512 (order: -1, 2048 bytes) TCP: Hash tables configured (established 512 bind 512) TCP reno registered sq: Registering store queue API. Total HugeTLB memory allocated, 0 io scheduler noop registered io scheduler anticipatory registered (default) io scheduler deadline registered io scheduler cfq registered Fault in unaligned fixup: 0000 [#1] Modules linked in: Pid : 1, Comm: swapper PC is at request_dma+0x2a/0x84 PC : 8c10d666 SP : 8c255e70 SR : 400000f1 TEA : 0000001a Not tainted R0 : 00000000 R1 : 00000001 R2 : 8c1e2210 R3 : 8c1e2210 R4 : 00000004 R5 : 8c1b0394 R6 : 000000c6 R7 : 8c247ee8 R8 : ffffffea R9 : 00000000 R10 : 00000000 R11 : 8c1b0394 R12 : ffffffed R13 : 8c1fb468 R14 : 00000000 MACH: 00000000 MACL: 00000005 GBR : 00000000 PR : 8c10d656 Call trace: [<8c1f26e8>] pvr2fb_dc_init+0x9c/0x108 [<8c1f298a>] pvr2fb_init+0x236/0x26c [<8c063018>] ifind+0x14/0x98 [<8c0127f4>] acquire_console_sem+0x0/0xb4 [<8c087884>] sysfs_ilookup_test+0x0/0xa [<8c06310a>] ilookup5_nowait+0x2a/0x44 [<8c0879d8>] sysfs_addrm_finish+0x18/0x248 [<8c0878b8>] sysfs_addrm_start+0x2a/0x9e [<8c086d6e>] sysfs_add_file+0x56/0xc0 [<8c0127f4>] acquire_console_sem+0x0/0xb4 [<8c1f25ae>] fb_console_init+0xae/0x134 [<8c0127f4>] acquire_console_sem+0x0/0xb4 [<8c1ea848>] kernel_init+0x90/0x244 [<8c0035e4>] kernel_thread_helper+0x4/0x10 [<8c1ea7b8>] kernel_init+0x0/0x244 [<8c0035e0>] kernel_thread_helper+0x0/0x10 Process: swapper (pid: 1, stack limit = 8c254001) Stack: (0x8c255e70 to 0x8c256000) 5e60: 8c1f26e8 8c208644 00000000 8c1dd8f4 5e80: 8c1dd90c 8c1f298a 8c205cd4 8c291508 00000002 8c1b0038 00000000 8c1dd8c0 5ea0: 8c254000 8c247998 00000000 8c1afe54 00000000 8c29e4c0 8c1afe54 00000000 5ec0: 8c063018 8c1fb464 8c0127f4 8c2085b4 8c2915b4 8c087884 8c254000 8c06310a 5ee0: 8c0879d8 8c244a00 00000000 8c0878b8 8c086d6e 8c1fb464 8c0127f4 8c2085b4 5f00: 8c2915b4 8c1dd8c0 8c2914e4 8c2915b4 00000000 00000000 8c1f25ae 8c0127f4 5f20: 8c2085b4 8c2085bc 00000000 00000000 8c1ea848 00000000 00000000 00000000 5f40: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 5f60: 00000000 00000000 00000000 00000000 00000001 00000000 00000000 00000000 5f80: 8c0035e4 00000000 00000000 00000000 00000000 00000000 00000000 00000000 5fa0: 00000000 00000000 00000000 00000000 00000000 8c1ea7b8 00000000 00000000 5fc0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 8c255fa0 5fe0: 8c0035e0 00000000 40000000 00000000 00000000 00000000 00000000 00000000 Kernel panic - not syncing: Attempted to kill init! Rebooting in 3 seconds.. |
From: Kristoffer E. <kri...@gm...> - 2007-07-16 21:43:13
|
Greetings, Paul could you just give this a check. Im working on scan_keyb and that should be ready tommorow. This patch is based on what andriy made with my additions : Keymap now uses KEY_X instead of 0x00.. Fixed for dead keys, so they all work. Best wishes Kristoffer diff --git a/drivers/input/keyboard/hp680_keyb.c b/drivers/input/keyboard/hp680_keyb.c new file mode 100644 index 0000000..2890668 --- /dev/null +++ b/drivers/input/keyboard/hp680_keyb.c @@ -0,0 +1,218 @@ +/* + * drivers/input/keyboard/hp680_keyb.c + * + * HP Jornada 680/690 scan keyboard + * + * Copyright (C) 2005 Andriy Skulysh + * Copyright (C) 2006 Paul Mundt + * Copyright (C) 2007 Kristoffer Ericson <Kri...@gm...> + * + * Splitted from drivers/input/keyboard/hp600_keyb.c + * + * Copyright (C) 2000 YAEGASHI Takeshi + * HP600 keyboard scan routine and translation table + * Copyright (C) 2000 Niibe Yutaka + * HP620 keyboard translation table + */ +#include <linux/input.h> +#include <linux/kernel.h> +#include <linux/module.h> +#include <linux/init.h> +#include <asm/delay.h> +#include <asm/io.h> +#include "scan_keyb.h" + +#define PCCR 0xa4000104 +#define PDCR 0xa4000106 +#define PECR 0xa4000108 +#define PFCR 0xa400010a +#define PCDR 0xa4000124 +#define PDDR 0xa4000126 +#define PEDR 0xa4000128 +#define PFDR 0xa400012a +#define PGDR 0xa400012c +#define PHDR 0xa400012e +#define PJDR 0xa4000130 +#define PKDR 0xa4000132 +#define PLDR 0xa4000134 + +/*************************************************************** +HP Jornada 680(SWEDISH version) keyboard +[!] indicates Special Characters +______________________________________________________________________ +| ESC F1 F2 F3 F4 F5 F6 F7 F8 F9 F10 POWER| +| 1 2 3 4 5 6 7 8 9 0 + ` BKPSPACE| +|* Q W E R T Y U I O P ! ^ ENTER| +| TAB A S D F G H J K L ! ! ' ENTER| +| SHIFT Z X C V B N M , . - UP SHIFT| +| CTRL WIN ALT ? =======SPACE======== ALTG DEL LEF DO RI ] +----------------------------------------------------------------------- +****************************************************************/ + +/**************************************************************** +HP Jornada 690(Japanese version) keyboard scan matrix + + PTC7 PTC6 PTC5 PTC4 PTC3 PTC2 PTC1 PTC0 +PTD1 REC Escape on/off Han/Zen Hira Eisu +PTD5 REC Z on/off Enter : / +PTD7 REC Right Down +PTE0 REC Windows on/off +PTE1 REC A on/off ] [ ; +PTE3 REC Tab on/off ShirtR \ Up +PTE6 REC Q on/off BS @ P +PTE7 REC 1 on/off ^ - 0 + + PTF7 PTF6 PTF5 PTF4 PTF3 PTF2 PTF1 PTF0 +PTD1 F5 F4 F6 F7 F8 F3 F2 F1 +PTD5 N B M , . V C X +PTD7 Muhen Alt Left +PTE0 Henkan _ Del Space Ctrl +PTE1 H G J K L F D S +PTE3 ShiftL +PTE6 Y T U I O R E W +PTE7 6 5 7 8 9 4 3 2 + + PTG5 PTG4 PTG3 PTG0 PTH0 +* REC REW FWW Cover on/off + + + 7 6 5 4 3 2 1 0 +C: 0xffff 0xdf IP IP IP IP IP IP IP IP +D: 0x6786 0x59 O I O IP I F O I +E: 0x5045 0x00 O O F F O F O O +F: 0xffff 0xff IP IP IP IP IP IP IP IP +G: 0xaffe 0xfd I I IP IP IP IP IP I +H: 0x70f2 0x49 O IP F F IP IP F I +J: 0x0704 0x22 F F O IP F F O F +K: 0x0100 0x10 F F F O F F F F +L: 0x0c3c 0x26 F F IP F F IP IP F + +****************************************************************/ + +static const unsigned char hp680kbd_scancodes[] = { + /* PTD1 */ + KEY_CAPSLOCK, KEY_MACRO, KEY_LEFTCTRL, KEY_RESERVED, KEY_ESC, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_F1, KEY_F2, KEY_F3, KEY_F8, KEY_F7, KEY_F2, + KEY_F4, KEY_F5, + + /* PTD5 */ + KEY_SLASH, KEY_APOSTROPHE, KEY_ENTER, KEY_RESERVED, KEY_Z, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_X, KEY_C, KEY_V, KEY_DOT, KEY_COMMA, + KEY_M, KEY_B, KEY_N, + + /* PTD7 */ + KEY_KP2, KEY_KP6, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_KP4, + KEY_RESERVED, KEY_RESERVED, KEY_LEFTALT, KEY_HANJA, + + /* PTE0 */ + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_FINANCE, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_LEFTCTRL, KEY_RESERVED, KEY_SPACE, KEY_KPDOT, + KEY_VOLUMEUP, 249, KEY_RESERVED, KEY_RESERVED, + + /* PTE1 */ + KEY_SEMICOLO, KEY_RIGHTBRACE, KEY_BACKSLASH, KEY_RESERVED, KEY_A, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_S, KEY_D, KEY_F, KEY_L, KEY_K, KEY_J, KEY_G, KEY_H, + + /* PTE3 */ + KEY_KP8, KEY_LEFTMETA, KEY_RIGHTSHIFT, KEY_RESERVED, KEY_TAB, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_LEFTSHIFT, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, + + /* PTE6 */ + KEY_P, KEY_LEFTBRACE, KEY_BACKSPACE, KEY_RESERVED, KEY_Q, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_W, KEY_E, KEY_R, KEY_O, KEY_I, KEY_U, KEY_T, KEY_R, + + /* PTE7 */ + KEY_0, KEY_MINUS, KEY_EQUAL, KEY_RESERVED, KEY_1, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_2, KEY_3, KEY_4, KEY_9, KEY_8, KEY_7, KEY_5, KEY_6, + + /* **** */ + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, + KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, KEY_RESERVED, +}; + +static int hp680_japanese_scan_kbd(unsigned char *s) +{ + int i; + unsigned short ec_static,dc_static; /* = UINT16_t */ + unsigned char matrix_switch[] = { + 0xfd, 0xff, /* PTD1 PD(1) */ + 0xdf, 0xff, /* PTD5 PD(5) */ + 0x7f, 0xff, /* PTD7 PD(7) */ + 0xff, 0xfe, /* PTE0 PE(0) */ + 0xff, 0xfd, /* PTE1 PE(1) */ + 0xff, 0xf7, /* PTE3 PE(3) */ + 0xff, 0xbf, /* PTE6 PE(6) */ + 0xff, 0x7f, /* PTE7 PE(7) */ + }, *t=matrix_switch; + /* PD(x) : + 1. 0xcc0c & (1~(1 << (2*(x)+1))))) + 2. (0xf0cf & 0xfffff) */ + /* PE(x) : + 1. 0xcc0c & 0xffff + 2. 0xf0cf & (1~(1 << (2*(x)+1))))) */ + unsigned short matrix_PDE[] = { + 0xcc04, 0xf0cf, /* PD(1) */ + 0xc40c, 0xf0cf, /* PD(5) */ + 0x4c0c, 0xf0cf, /* PD(7) */ + 0xcc0c, 0xf0cd, /* PE(0) */ + 0xcc0c, 0xf0c7, /* PE(1) */ + 0xcc0c, 0xf04f, /* PE(3) */ + 0xcc0c, 0xd0cf, /* PE(6) */ + 0xcc0c, 0x70cf, /* PE(7) */ + }, *y=matrix_PDE; + /* Save these control reg bits */ + dc_static = (ctrl_inw(PDCR) & (~0xcc0c)); + ec_static = (ctrl_inw(PECR) & (~0xf0cf)); + + for (i=0; i<8; i++) { + /* disable output for all but the one we want to scan */ + ctrl_outw((dc_static | *y++), PDCR); + ctrl_outw((ec_static | *y++), PECR); + udelay(5); + + /* Get scanline row */ + ctrl_outb(*t++, PDDR); + ctrl_outb(*t++, PEDR); + udelay(50); + + /* Read data */ + *s++=ctrl_inb(PCDR); + *s++=ctrl_inb(PFDR); + } + /* Scan no lines */ + ctrl_outb(0xff, PDDR); + ctrl_outb(0xff, PEDR); + + /* Enable all scanlines */ + ctrl_outw((dc_static | (0x5555 & 0xcc0c)),PDCR); + ctrl_outw((ec_static | (0x5555 & 0xf0cf)),PECR); + /* Ignore extra keys and events */ + *s++=ctrl_inb(PGDR); + *s++=ctrl_inb(PHDR); + + return 0; +} + +static struct scan_keyboard hp680_kbd = { + .scan = hp680_japanese_scan_kbd, + .table = hp680_japanese_table, + .length = 16, +}; + +static int __init hp680_kbd_init_hw(void) +{ + printk(KERN_INFO "HP680 matrix scan keyboard registered\n"); + return register_scan_keyboard(&hp680_kbd); +} + +static void __exit hp680_kbd_exit_hw(void) +{ + unregister_scan_keyboard(&hp680_kbd); +} + +module_init(hp680_kbd_init_hw); +module_exit(hp680_kbd_exit_hw); +MODULE_LICENSE("GPL"); |
From: Paul M. <le...@li...> - 2007-07-16 21:08:58
|
On Mon, Jul 16, 2007 at 09:40:03PM +0100, Adrian McMenamin wrote: > On Mon, 2007-07-16 at 07:42 +0900, Paul Mundt wrote: > > While there might be some problems in the channel management, you're > > barking up the wrong tree here. This stuff worked fine before, and the > > driver has undergone zero changes in terms of the DMA code since then. > > OK, I've made sure that the modules are compiled and loaded in the right > order, and built pvr2fb as a module - get this now: > > Builds with correct number of channels: > > [ 0.036116] DMA: Registering DMA API. > [ 0.036203] DMA: Registering sh_dmac handler (4 channels). > [ 0.038616] DMA: Registering pvr2_dmac handler (1 channel). > [ 0.039326] DMA: Registering g2_dmac handler (4 channels). > > But oopses on attempt to load module - don't know if this is a toolset > problem or code: > What happens if you have pvr2fb built in, does it simply reboot? > / # modprobe pvr2fb > [ 74.814053] Fault in unaligned fixup: 0000 [#1] > [ 74.817984] Modules linked in: pvr2fb cfbcopyarea cfbimgblt > cfbfillrect > [ 74.824808] > [ 74.826344] Pid : 713, Comm: modprobe > [ 74.831211] PC is at request_dma+0x2a/0x84 > [ 74.835429] PC : 8c10f96e SP : 8c1fbea8 SR : 400080f1 TEA : > c0103be4 Not tainted That's certainly not good. I suppose I'll have to plug in some dummy DMACs and hash out where things went wrong. I'll take a look at it later today. Should also probably redo the dependencies so we're not able to artificially change the number of channels (or better yet, let the platform device take care of it). |
From: Adrian M. <ad...@ne...> - 2007-07-16 20:40:49
|
On Mon, 2007-07-16 at 07:42 +0900, Paul Mundt wrote: > On Sun, Jul 15, 2007 at 07:09:02PM +0100, Adrian McMenamin wrote: > > It appears it is not the sh_dmac code which is to blame, but the > > pvr2_dma code. If I fix the build to exclude pvr2_dma.c, the Dreamcast > > will boot with CONFIG_NR_ONCHIP_DMA_CHANNELS set correctly (ie to 4) > > > CONFIG_NR_ONCHIP_DMA_CHANNELS should be 4 for this, yes. > CONFIG_NR_DMA_CHANNELS should be 9, as per the Kconfig entry. > > > Plainly the pvr code is broken when it tries to take channel 4, not sure > > why though, will have a deeper look. > > > How do you reach that conclusion? The pvr code is requesting the first > channel of the pvr2 DMAC. SH DMAC channels are mapped to virtual channels > 0 - 3, pvr2 at 4, andthe G2 channels above that. It's all ordering > dependent. > > While there might be some problems in the channel management, you're > barking up the wrong tree here. This stuff worked fine before, and the > driver has undergone zero changes in terms of the DMA code since then. OK, I've made sure that the modules are compiled and loaded in the right order, and built pvr2fb as a module - get this now: Builds with correct number of channels: [ 0.036116] DMA: Registering DMA API. [ 0.036203] DMA: Registering sh_dmac handler (4 channels). [ 0.038616] DMA: Registering pvr2_dmac handler (1 channel). [ 0.039326] DMA: Registering g2_dmac handler (4 channels). But oopses on attempt to load module - don't know if this is a toolset problem or code: / # modprobe pvr2fb [ 74.814053] Fault in unaligned fixup: 0000 [#1] [ 74.817984] Modules linked in: pvr2fb cfbcopyarea cfbimgblt cfbfillrect [ 74.824808] [ 74.826344] Pid : 713, Comm: modprobe [ 74.831211] PC is at request_dma+0x2a/0x84 [ 74.835429] PC : 8c10f96e SP : 8c1fbea8 SR : 400080f1 TEA : c0103be4 Not tainted [ 74.843601] R0 : 00000000 R1 : 00000001 R2 : 8c1e20d0 R3 : 8c1e20d0 [ 74.850428] R4 : 00000004 R5 : c010f11c R6 : 00000000 R7 : 8c1fbd98 [ 74.857253] R8 : ffffffea R9 : 00000000 R10 : 00000000 R11 : c010f11c [ 74.864082] R12 : c0110244 R13 : 8cd21998 R14 : c0109000 [ 74.869557] MACH: 00000245 MACL: 00000005 GBR : 00000000 PR : 8c10f95e [ 74.876368] [ 74.876395] Call trace: [ 74.880507] [<c01000b8>] pvr2fb_dc_init+0x9c/0x108 [pvr2fb] [ 74.886261] [<c010018c>] pvr2fb_init+0x68/0xb8 [pvr2fb] [ 74.891644] [<8c02e4be>] sys_init_module+0xfba/0x1090 [ 74.896857] [<8c174ee4>] mutex_unlock+0x0/0x40 [ 74.901438] [<8c174ee4>] mutex_unlock+0x0/0x40 [ 74.906061] [<8c007244>] syscall_call+0xc/0x10 [ 74.910604] [<8c02d504>] sys_init_module+0x0/0x1090 [ 74.915645] [ 74.917161] Process: modprobe (pid: 713, stack limit = 8c1fa001) [ 74.923360] Stack: (0x8c1fbea8 to 0x8c1fc000) [ 74.927840] bea0: c01000b8 ffffffed 00000000 c010fd54 c010fd6c c010018c [ 74.936372] bec0: 8c02e4be c010aa8c 8c174ee4 c011015c c01100a0 8c174ee4 00000000 00000000 [ 74.944905] bee0: 00000000 00000000 004160c8 c010a9e4 8cd1b7c0 c010bbdc 00000011 00000012 [ 74.953438] bf00: 00000000 00000000 00000000 0000000b 00000000 00000007 00000000 00000000 [ 74.961971] bf20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 0000006f [ 74.970505] bf40: 0000006f 00000000 00000001 00000000 00000000 00000000 00000000 00000013 [ 74.979038] bf60: 00000174 00000028 c0109030 c0109030 c0109030 c0109030 000002f8 8c1793e8 [ 74.987571] bf80: 8c007244 7bf5fadc 00418290 295e2490 ffffff0f 00000001 8c1fbff8 8c02d504 [ 74.996104] bfa0: 0000308d 00400ef8 7bf5fadc 00000080 29560000 0000308d 004160c8 004160c8 [ 75.004637] bfc0: 00000000 00000000 00000000 004160b8 295e2490 00418290 7bf5fadc 7bf5fadc [ 75.013170] bfe0: 2959862e 00402b48 00008001 00000000 00000210 07ab98f7 00000054 00000160 Segmentation fault |
From: Kristoffer E. <kri...@gm...> - 2007-07-16 11:44:26
|
(doh!) Shortlog: * io.c found in arch/sh/cchips/hd6446x/hd64461/ directory was used to translate PIO -> MMIO. Since we have moved away from PIO this file is useless. * All io functions are now handled by generic mapping signed-off-by: Kristoffer Ericson <Kri...@gm...> diff --git a/arch/sh/cchips/hd6446x/hd64461/io.c b/arch/sh/cchips/hd6446x/hd64461/io.c deleted file mode 100644 index 7909a1b..0000000 --- a/arch/sh/cchips/hd6446x/hd64461/io.c +++ /dev/null @@ -1,150 +0,0 @@ -/* - * Copyright (C) 2000 YAEGASHI Takeshi - * Typical I/O routines for HD64461 system. - */ - -#include <asm/io.h> -#include <asm/hd64461.h> - -#define MEM_BASE (CONFIG_HD64461_IOBASE - HD64461_STBCR) - -static __inline__ unsigned long PORT2ADDR(unsigned long port) -{ - /* 16550A: HD64461 internal */ - if (0x3f8<=port && port<=0x3ff) - return CONFIG_HD64461_IOBASE + 0x8000 + ((port-0x3f8)<<1); - if (0x2f8<=port && port<=0x2ff) - return CONFIG_HD64461_IOBASE + 0x7000 + ((port-0x2f8)<<1); - -#ifdef CONFIG_HD64461_ENABLER - /* NE2000: HD64461 PCMCIA channel 0 (I/O) */ - if (0x300<=port && port<=0x31f) - return 0xba000000 + port; - - /* ide0: HD64461 PCMCIA channel 1 (memory) */ - /* On HP690, CF in slot 1 is configured as a memory card - device. See CF+ and CompactFlash Specification for the - detail of CF's memory mapped addressing. */ - if (0x1f0<=port && port<=0x1f7) return 0xb5000000 + port; - if (port == 0x3f6) return 0xb50001fe; - if (port == 0x3f7) return 0xb50001ff; - - /* ide1 */ - if (0x170<=port && port<=0x177) return 0xba000000 + port; - if (port == 0x376) return 0xba000376; - if (port == 0x377) return 0xba000377; -#endif - - /* ??? */ - if (port < 0xf000) return 0xa0000000 + port; - /* PCMCIA channel 0, I/O (0xba000000) */ - if (port < 0x10000) return 0xba000000 + port - 0xf000; - - /* HD64461 internal devices (0xb0000000) */ - if (port < 0x20000) return CONFIG_HD64461_IOBASE + port - 0x10000; - - /* PCMCIA channel 0, I/O (0xba000000) */ - if (port < 0x30000) return 0xba000000 + port - 0x20000; - - /* PCMCIA channel 1, memory (0xb5000000) */ - if (port < 0x40000) return 0xb5000000 + port - 0x30000; - - /* Whole physical address space (0xa0000000) */ - return 0xa0000000 + (port & 0x1fffffff); -} - -unsigned char hd64461_inb(unsigned long port) -{ - return *(volatile unsigned char*)PORT2ADDR(port); -} - -unsigned char hd64461_inb_p(unsigned long port) -{ - unsigned long v = *(volatile unsigned char*)PORT2ADDR(port); - ctrl_delay(); - return v; -} - -unsigned short hd64461_inw(unsigned long port) -{ - return *(volatile unsigned short*)PORT2ADDR(port); -} - -unsigned int hd64461_inl(unsigned long port) -{ - return *(volatile unsigned long*)PORT2ADDR(port); -} - -void hd64461_outb(unsigned char b, unsigned long port) -{ - *(volatile unsigned char*)PORT2ADDR(port) = b; -} - -void hd64461_outb_p(unsigned char b, unsigned long port) -{ - *(volatile unsigned char*)PORT2ADDR(port) = b; - ctrl_delay(); -} - -void hd64461_outw(unsigned short b, unsigned long port) -{ - *(volatile unsigned short*)PORT2ADDR(port) = b; -} - -void hd64461_outl(unsigned int b, unsigned long port) -{ - *(volatile unsigned long*)PORT2ADDR(port) = b; -} - -void hd64461_insb(unsigned long port, void *buffer, unsigned long count) -{ - volatile unsigned char* addr=(volatile unsigned char*)PORT2ADDR(port); - unsigned char *buf=buffer; - while(count--) *buf++=*addr; -} - -void hd64461_insw(unsigned long port, void *buffer, unsigned long count) -{ - volatile unsigned short* addr=(volatile unsigned short*)PORT2ADDR(port); - unsigned short *buf=buffer; - while(count--) *buf++=*addr; -} - -void hd64461_insl(unsigned long port, void *buffer, unsigned long count) -{ - volatile unsigned long* addr=(volatile unsigned long*)PORT2ADDR(port); - unsigned long *buf=buffer; - while(count--) *buf++=*addr; -} - -void hd64461_outsb(unsigned long port, const void *buffer, unsigned long count) -{ - volatile unsigned char* addr=(volatile unsigned char*)PORT2ADDR(port); - const unsigned char *buf=buffer; - while(count--) *addr=*buf++; -} - -void hd64461_outsw(unsigned long port, const void *buffer, unsigned long count) -{ - volatile unsigned short* addr=(volatile unsigned short*)PORT2ADDR(port); - const unsigned short *buf=buffer; - while(count--) *addr=*buf++; -} - -void hd64461_outsl(unsigned long port, const void *buffer, unsigned long count) -{ - volatile unsigned long* addr=(volatile unsigned long*)PORT2ADDR(port); - const unsigned long *buf=buffer; - while(count--) *addr=*buf++; -} - -unsigned short hd64461_readw(void __iomem *addr) -{ - return ctrl_inw(MEM_BASE+(unsigned long __force)addr); -} - -void hd64461_writew(unsigned short b, void __iomem *addr) -{ - ctrl_outw(b, MEM_BASE+(unsigned long __force)addr); -} - |
From: Kristoffer E. <kri...@gm...> - 2007-07-16 11:42:56
|
Shortlog: * io.c found in arch/sh/cchips/hd6446x/hd64461/ directory was used to translate PIO -> MMIO. Since we have moved away from PIO this file is useless. * All io functions are now handled by generic signed-off-by: Kristoffer Ericson <Kri...@gm...> |
From: Paul M. <le...@li...> - 2007-07-15 22:43:06
|
On Sun, Jul 15, 2007 at 07:09:02PM +0100, Adrian McMenamin wrote: > It appears it is not the sh_dmac code which is to blame, but the > pvr2_dma code. If I fix the build to exclude pvr2_dma.c, the Dreamcast > will boot with CONFIG_NR_ONCHIP_DMA_CHANNELS set correctly (ie to 4) > CONFIG_NR_ONCHIP_DMA_CHANNELS should be 4 for this, yes. CONFIG_NR_DMA_CHANNELS should be 9, as per the Kconfig entry. > Plainly the pvr code is broken when it tries to take channel 4, not sure > why though, will have a deeper look. > How do you reach that conclusion? The pvr code is requesting the first channel of the pvr2 DMAC. SH DMAC channels are mapped to virtual channels 0 - 3, pvr2 at 4, andthe G2 channels above that. It's all ordering dependent. While there might be some problems in the channel management, you're barking up the wrong tree here. This stuff worked fine before, and the driver has undergone zero changes in terms of the DMA code since then. |
From: Adrian M. <ad...@ne...> - 2007-07-15 22:00:25
|
Attempting to link this in as a module, generates this: / # modprobe pvr2fb [ 286.784908] Fault in unaligned fixup: 0000 [#1] [ 286.788836] Modules linked in: pvr2fb cfbcopyarea cfbimgblt cfbfillrect snd_aica snd_pcm_oss snd_pcm snd_timer snd_page_alloc snd_mixer_oss snd soundcore [ 286.803025] [ 286.804563] Pid : 1218, Comm: modprobe [ 286.809519] PC is at request_dma+0x2a/0x84 [ 286.813736] PC : 8c10f96e SP : 8ca6fea8 SR : 400080f1 TEA : c01330a4 Not tainted [ 286.821908] R0 : 00000000 R1 : 00000001 R2 : 8c1e20d0 R3 : 8c1e20d0 [ 286.828735] R4 : 00000004 R5 : c013211c R6 : 00000000 R7 : 8ca6fd98 [ 286.835561] R8 : ffffffea R9 : 00000000 R10 : 00000000 R11 : c013211c [ 286.842389] R12 : c0133244 R13 : 8c974798 R14 : c012c000 [ 286.847864] MACH: 00000240 MACL: 00000005 GBR : 00000000 PR : 8c10f95e [ 286.854675] [ 286.854701] Call trace: [ 286.858815] [<c01350b8>] pvr2fb_dc_init+0x9c/0x108 [pvr2fb] [ 286.864574] [<c013518c>] pvr2fb_init+0x68/0xb8 [pvr2fb] [ 286.869952] [<8c02e4be>] sys_init_module+0xfba/0x1090 [ 286.875165] [<8c174ee4>] mutex_unlock+0x0/0x40 [ 286.879748] [<8c174ee4>] mutex_unlock+0x0/0x40 [ 286.884408] [<8c007244>] syscall_call+0xc/0x10 [ 286.888917] [<8c02d504>] sys_init_module+0x0/0x1090 [ 286.893974] [ 286.895469] Process: modprobe (pid: 1218, stack limit = 8ca6e001) [ 286.901758] Stack: (0x8ca6fea8 to 0x8ca70000) [ 286.906237] fea0: c01350b8 ffffffed 00000000 c0132d54 c0132d6c c013518c [ 286.914769] fec0: 8c02e4be c012da8c 8c174ee4 c013315c c01330a0 8c174ee4 00000000 00000000 [ 286.923302] fee0: 00000000 00000000 004160c8 c012d9e4 8c92ca60 c012ebdc 00000011 00000012 [ 286.931836] ff00: 00000000 00000000 00000000 0000000b 00000000 00000007 00000000 00000000 [ 286.940369] ff20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 0000006f [ 286.948902] ff40: 0000006f 00000000 00000001 00000000 00000000 00000000 00000000 00000013 [ 286.957435] ff60: 00000174 00000028 c012c030 c012c030 c012c030 c012c030 000002f8 8c1793e8 [ 286.965968] ff80: 8c007244 7bda6adc 00418290 295e2490 ffffff0f 00000001 8ca6fff8 8c02d504 [ 286.974501] ffa0: 0000308d 00400ef8 7bda6adc 00000080 29560000 0000308d 004160c8 004160c8 [ 286.983034] ffc0: 00000000 00000000 00000000 004160b8 295e2490 00418290 7bda6adc 7bda6adc [ 286.991567] ffe0: 2959862e 00402b48 00008001 00000000 00000210 006a3499 00000054 00000160 Segmentation fault (NB my inbound mail server has packed up - temporarily I hope - so I am not receiving emails to this address atm) |