diff --git a/bsp/lpc2478/drivers/board.c b/bsp/lpc2478/drivers/board.c index b29fcc8d7d..1ddc0aaf79 100644 --- a/bsp/lpc2478/drivers/board.c +++ b/bsp/lpc2478/drivers/board.c @@ -27,7 +27,7 @@ extern void rt_hw_serial_init(void); */ /*@{*/ -void rt_timer_handler(int vector) +void rt_timer_handler(int vector, void* param) { T0IR |= 0x01; /* clear interrupt flag */ rt_tick_increase(); @@ -49,7 +49,7 @@ void rt_hw_board_init() T0MCR = 0x03; T0MR0 = (DATA_COUNT); - rt_hw_interrupt_install(TIMER0_INT, rt_timer_handler, RT_NULL); + rt_hw_interrupt_install(TIMER0_INT, rt_timer_handler, RT_NULL, "tick"); rt_hw_interrupt_umask(TIMER0_INT); T0TCR = 0x01; //enable timer0 counter diff --git a/bsp/lpc2478/drivers/serial.c b/bsp/lpc2478/drivers/serial.c index 0eeb94a61e..a5edc3c988 100644 --- a/bsp/lpc2478/drivers/serial.c +++ b/bsp/lpc2478/drivers/serial.c @@ -113,7 +113,7 @@ void rt_hw_uart_isr(struct rt_lpcserial* lpc_serial) } #ifdef RT_USING_UART1 -void rt_hw_uart_isr_1(int irqno) +void rt_hw_uart_isr_1(int irqno, void* param) { /* get lpc serial device */ rt_hw_uart_isr(&serial1); @@ -121,7 +121,7 @@ void rt_hw_uart_isr_1(int irqno) #endif #ifdef RT_USING_UART2 -void rt_hw_uart_isr_2(int irqno) +void rt_hw_uart_isr_2(int irqno, void* param) { /* get lpc serial device */ rt_hw_uart_isr(&serial2); @@ -153,13 +153,13 @@ static rt_err_t rt_serial_open(rt_device_t dev, rt_uint16_t oflag) if (lpc_serial->irqno == UART0_INT) { #ifdef RT_USING_UART1 - rt_hw_interrupt_install(lpc_serial->irqno, rt_hw_uart_isr_1, RT_NULL); + rt_hw_interrupt_install(lpc_serial->irqno, rt_hw_uart_isr_1, RT_NULL, "uart1"); #endif } else { #ifdef RT_USING_UART2 - rt_hw_interrupt_install(lpc_serial->irqno, rt_hw_uart_isr_2, RT_NULL); + rt_hw_interrupt_install(lpc_serial->irqno, rt_hw_uart_isr_2, RT_NULL, "uart2"); #endif } diff --git a/bsp/sam7x/applications/startup.c b/bsp/sam7x/applications/startup.c index abf9b58c51..770573910f 100644 --- a/bsp/sam7x/applications/startup.c +++ b/bsp/sam7x/applications/startup.c @@ -97,7 +97,7 @@ void rtthread_startup(void) #elif __ICCARM__ rt_system_heap_init(__segment_end("HEAP"), (void*)0x00210000); #else - rt_system_heap_init(&__bss_end, 0x00210000); + rt_system_heap_init(&__bss_end, (void*)0x00210000); #endif #endif diff --git a/bsp/sam7x/drivers/board.c b/bsp/sam7x/drivers/board.c index b25c4e5cf1..16dfacb9be 100644 --- a/bsp/sam7x/drivers/board.c +++ b/bsp/sam7x/drivers/board.c @@ -33,7 +33,7 @@ static void rt_hw_board_led_init(void); * This is the timer interrupt service routine. * @param vector the irq number for timer */ -void rt_hw_timer_handler(int vector) +void rt_hw_timer_handler(int vector, void* param) { if (AT91C_BASE_PITC->PITC_PISR & 0x01) { @@ -168,7 +168,7 @@ void rt_hw_board_init() AT91C_BASE_PITC->PITC_PIMR = (1 << 25) | (1 << 24) | PIV; /* install timer handler */ - rt_hw_interrupt_install(AT91C_ID_SYS, rt_hw_timer_handler, RT_NULL); + rt_hw_interrupt_install(AT91C_ID_SYS, rt_hw_timer_handler, RT_NULL, "tick"); AT91C_BASE_AIC->AIC_SMR[AT91C_ID_SYS] = 0; rt_hw_interrupt_umask(AT91C_ID_SYS); } diff --git a/bsp/sam7x/drivers/sam7x_emac.c b/bsp/sam7x/drivers/sam7x_emac.c index b2375d45c6..72c9794599 100644 --- a/bsp/sam7x/drivers/sam7x_emac.c +++ b/bsp/sam7x/drivers/sam7x_emac.c @@ -120,7 +120,7 @@ rt_inline void sam7xether_reset_tx_desc(void) /* interrupt service routing */ -static void sam7xether_isr(int irq) +static void sam7xether_isr(int irq, void* param) { /* Variable definitions can be made now. */ volatile rt_uint32_t isr, rsr; @@ -377,7 +377,7 @@ rt_err_t sam7xether_init(rt_device_t dev) AT91C_BASE_EMAC->EMAC_IER = AT91C_EMAC_RCOMP | AT91C_EMAC_TCOMP; /* setup interrupt */ - rt_hw_interrupt_install(AT91C_ID_EMAC, sam7xether_isr, RT_NULL); + rt_hw_interrupt_install(AT91C_ID_EMAC, sam7xether_isr, RT_NULL, "emac"); *(volatile unsigned int*)(0xFFFFF000 + AT91C_ID_EMAC * 4) = AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL | 5; // AT91C_AIC_SMR(AT91C_ID_EMAC) = AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL | 5; rt_hw_interrupt_umask(AT91C_ID_EMAC); diff --git a/bsp/sam7x/drivers/serial.c b/bsp/sam7x/drivers/serial.c index 0a658e9471..2267ed3c25 100644 --- a/bsp/sam7x/drivers/serial.c +++ b/bsp/sam7x/drivers/serial.c @@ -76,27 +76,12 @@ struct rt_at91serial serial1; struct rt_at91serial serial2; #endif -static void rt_hw_serial_isr(int irqno) +static void rt_hw_serial_isr(int irqno, void* param) { rt_base_t level; struct rt_device* device; - struct rt_at91serial* serial = RT_NULL; + struct rt_at91serial* serial = (struct rt_at91serial*)param; -#ifdef RT_USING_UART1 - if (irqno == AT91C_ID_US0) - { - /* serial 1 */ - serial = &serial1; - } -#endif - -#ifdef RT_USING_UART2 - if (irqno == AT91C_ID_US1) - { - /* serial 2 */ - serial = &serial2; - } -#endif RT_ASSERT(serial != RT_NULL); /* get generic device object */ @@ -202,7 +187,7 @@ static rt_err_t rt_serial_open(rt_device_t dev, rt_uint16_t oflag) //serial->hw_base->US_IMR |= 1 << 0; /* umask RxReady interrupt */ /* install UART handler */ - rt_hw_interrupt_install(serial->peripheral_id, rt_hw_serial_isr, RT_NULL); + rt_hw_interrupt_install(serial->peripheral_id, rt_hw_serial_isr, serial, "uart"); // SAM7X Datasheet 30.5.3: // It is notrecommended to use the USART interrupt line in edge sensitive mode //AT91C_AIC_SMR(serial->peripheral_id) = 5 | (0x01 << 5); diff --git a/libcpu/arm/AT91SAM7X/interrupt.c b/libcpu/arm/AT91SAM7X/interrupt.c index d3cbbcda2e..1aced87b29 100644 --- a/libcpu/arm/AT91SAM7X/interrupt.c +++ b/libcpu/arm/AT91SAM7X/interrupt.c @@ -12,11 +12,14 @@ * 2006-08-23 Bernard first version */ -#include +#include #include "AT91SAM7X256.h" #define MAX_HANDLERS 32 +/* exception and interrupt handler table */ +struct rt_irq_desc irq_desc[MAX_HANDLERS]; + extern rt_uint32_t rt_interrupt_nest; rt_uint32_t rt_interrupt_from_thread, rt_interrupt_to_thread; @@ -39,6 +42,13 @@ void rt_hw_interrupt_init() { rt_base_t index; + /* init exceptions table */ + for(index=0; index < MAX_HANDLERS; index++) + { + irq_desc[index].handler = (rt_isr_handler_t)rt_hw_interrupt_handler; + irq_desc[index].param = RT_NULL; + } + for (index = 0; index < MAX_HANDLERS; index ++) { AT91C_BASE_AIC->AIC_SVR[index] = (rt_uint32_t)rt_hw_interrupt_handler; @@ -76,16 +86,28 @@ void rt_hw_interrupt_umask(int vector) /** * This function will install a interrupt service routine to a interrupt. * @param vector the interrupt number - * @param new_handler the interrupt service routine to be installed - * @param old_handler the old interrupt service routine + * @param handler the interrupt service routine to be installed + * @param param the parameter for interrupt service routine + * @name unused. + * + * @return the old handler */ -void rt_hw_interrupt_install(int vector, rt_isr_handler_t new_handler, rt_isr_handler_t *old_handler) +rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, + void *param, char *name) { + rt_isr_handler_t old_handler = RT_NULL; + if(vector >= 0 && vector < MAX_HANDLERS) { - if (old_handler != RT_NULL) *old_handler = (rt_isr_handler_t)AT91C_BASE_AIC->AIC_SVR[vector]; - if (new_handler != RT_NULL) AT91C_BASE_AIC->AIC_SVR[vector] = (rt_uint32_t)new_handler; + old_handler = irq_desc[vector].handler; + if (handler != RT_NULL) + { + irq_desc[vector].handler = (rt_isr_handler_t)handler; + irq_desc[vector].param = param; + } } + + return old_handler; } /*@}*/ diff --git a/libcpu/arm/AT91SAM7X/trap.c b/libcpu/arm/AT91SAM7X/trap.c index 2e137fc009..4b21f81c1c 100644 --- a/libcpu/arm/AT91SAM7X/trap.c +++ b/libcpu/arm/AT91SAM7X/trap.c @@ -24,9 +24,14 @@ void rt_hw_trap_irq() { - rt_isr_handler_t hander = (rt_isr_handler_t)AT91C_BASE_AIC->AIC_IVR; + int irqno; + extern struct rt_irq_desc irq_desc[]; - hander(AT91C_BASE_AIC->AIC_ISR); + /* get interrupt number */ + irqno = AT91C_BASE_AIC->AIC_ISR; + + /* invoke isr with parameters */ + irq_desc[irqno].handler(irqno, irq_desc[irqno].param); /* end of interrupt */ AT91C_BASE_AIC->AIC_EOICR = 0; diff --git a/libcpu/arm/lpc24xx/interrupt.c b/libcpu/arm/lpc24xx/interrupt.c index b18c1e10ff..6d64d7a07c 100644 --- a/libcpu/arm/lpc24xx/interrupt.c +++ b/libcpu/arm/lpc24xx/interrupt.c @@ -12,24 +12,25 @@ * 2008-12-11 XuXinming first version */ -#include +#include #include "LPC24xx.h" #define MAX_HANDLERS 32 +/* exception and interrupt handler table */ +struct rt_irq_desc irq_desc[MAX_HANDLERS]; + extern rt_uint32_t rt_interrupt_nest; /* exception and interrupt handler table */ rt_uint32_t rt_interrupt_from_thread, rt_interrupt_to_thread; rt_uint32_t rt_thread_switch_interrupt_flag; - /** * @addtogroup LPC2478 */ /*@{*/ - -void rt_hw_interrupt_handle(int vector) +void rt_hw_interrupt_handler(int vector, void *param) { rt_kprintf("Unhandled interrupt %d occured!!!\n", vector); } @@ -45,11 +46,15 @@ void rt_hw_interrupt_init() VICVectAddr = 0; VICIntSelect = 0; - for ( i = 0; i < 32; i++ ) + /* init exceptions table */ + for(i=0; i < MAX_HANDLERS; i++) { - vect_addr = (rt_uint32_t *)(VIC_BASE_ADDR + 0x100 + i*4); - vect_cntl = (rt_uint32_t *)(VIC_BASE_ADDR + 0x200 + i*4); - *vect_addr = 0x0; + irq_desc[i].handler = (rt_isr_handler_t)rt_hw_interrupt_handler; + irq_desc[i].param = RT_NULL; + + vect_addr = (rt_uint32_t *)(VIC_BASE_ADDR + 0x100 + i*4); + vect_cntl = (rt_uint32_t *)(VIC_BASE_ADDR + 0x200 + i*4); + *vect_addr = (rt_uint32_t)&irq_desc[i]; *vect_cntl = 0xF; } @@ -70,20 +75,31 @@ void rt_hw_interrupt_umask(int vector) VICIntEnable = (1 << vector); } -void rt_hw_interrupt_install(int vector, rt_isr_handler_t new_handler, rt_isr_handler_t *old_handler) +/** + * This function will install a interrupt service routine to a interrupt. + * @param vector the interrupt number + * @param handler the interrupt service routine to be installed + * @param param the parameter for interrupt service routine + * @name unused. + * + * @return the old handler + */ +rt_isr_handler_t rt_hw_interrupt_install(int vector, rt_isr_handler_t handler, + void *param, char *name) { - rt_uint32_t *vect_addr; - - if(vector < MAX_HANDLERS) + rt_isr_handler_t old_handler = RT_NULL; + + if(vector >= 0 && vector < MAX_HANDLERS) { - /* find first un-assigned VIC address for the handler */ - vect_addr = (rt_uint32_t *)(VIC_BASE_ADDR + 0x100 + vector*4); - - /* get old handler */ - if (old_handler != RT_NULL) *old_handler = (rt_isr_handler_t)*vect_addr; - - *vect_addr = (rt_uint32_t)new_handler; /* set interrupt vector */ + old_handler = irq_desc[vector].handler; + if (handler != RT_NULL) + { + irq_desc[vector].handler = (rt_isr_handler_t)handler; + irq_desc[vector].param = param; + } } + + return old_handler; } /*@}*/ diff --git a/libcpu/arm/lpc24xx/trap.c b/libcpu/arm/lpc24xx/trap.c index 1aa58bc0d6..53ff13b4eb 100644 --- a/libcpu/arm/lpc24xx/trap.c +++ b/libcpu/arm/lpc24xx/trap.c @@ -128,12 +128,15 @@ void rt_hw_trap_resv(struct rt_hw_register *regs) extern rt_isr_handler_t isr_table[]; void rt_hw_trap_irq() { - rt_isr_handler_t isr_func; - - isr_func = (rt_isr_handler_t) VICVectAddr; + int irqno; + struct rt_irq_desc* irq; + extern struct rt_irq_desc irq_desc[]; - /* fixme, how to get interrupt number */ - isr_func(0); + irq = (struct rt_irq_desc*) VICVectAddr; + irqno = ((rt_uint32_t) irq - (rt_uint32_t) &irq_desc[0])/sizeof(struct rt_irq_desc); + + /* invoke isr */ + irq->handler(irqno, irq->param); } void rt_hw_trap_fiq()