[ARM] 3946/1: AT91: at91_arch_reset and at91_extern_irq
The external interrupt sources are different on the various AT91 processors. This patch introduces the global 'at91_extern_irq' variable that contains a bitset of the available external interrupt sources. The processor reset mechanism also differs on the various AT91 processors. This patch also adds a global 'at91_arch_reset' callback (from system.h) into the processor-specific code to perform the reset. Signed-off-by: Andrew Victor <andrew@sanpeople.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
This commit is contained in:
Родитель
20127f6863
Коммит
1f4fd0a0d2
|
@ -14,6 +14,7 @@
|
|||
|
||||
#include <asm/mach/arch.h>
|
||||
#include <asm/mach/map.h>
|
||||
#include <asm/arch/at91rm9200.h>
|
||||
|
||||
#include <asm/hardware.h>
|
||||
#include "generic.h"
|
||||
|
@ -222,6 +223,16 @@ static struct at91_gpio_bank at91rm9200_gpio[] = {
|
|||
}
|
||||
};
|
||||
|
||||
static void at91rm9200_reset(void)
|
||||
{
|
||||
/*
|
||||
* Perform a hardware reset with the use of the Watchdog timer.
|
||||
*/
|
||||
at91_sys_write(AT91_ST_WDMR, AT91_ST_RSTEN | AT91_ST_EXTEN | 1);
|
||||
at91_sys_write(AT91_ST_CR, AT91_ST_WDRST);
|
||||
}
|
||||
|
||||
|
||||
/* --------------------------------------------------------------------
|
||||
* AT91RM9200 processor initialization
|
||||
* -------------------------------------------------------------------- */
|
||||
|
@ -230,6 +241,12 @@ void __init at91rm9200_initialize(unsigned long main_clock, unsigned short banks
|
|||
/* Map peripherals */
|
||||
iotable_init(at91rm9200_io_desc, ARRAY_SIZE(at91rm9200_io_desc));
|
||||
|
||||
at91_arch_reset = at91rm9200_reset;
|
||||
at91_extern_irq = (1 << AT91RM9200_ID_IRQ0) | (1 << AT91RM9200_ID_IRQ1)
|
||||
| (1 << AT91RM9200_ID_IRQ2) | (1 << AT91RM9200_ID_IRQ3)
|
||||
| (1 << AT91RM9200_ID_IRQ4) | (1 << AT91RM9200_ID_IRQ5)
|
||||
| (1 << AT91RM9200_ID_IRQ6);
|
||||
|
||||
/* Init clock subsystem */
|
||||
at91_clock_init(main_clock);
|
||||
|
||||
|
|
|
@ -39,3 +39,6 @@ struct at91_gpio_bank {
|
|||
};
|
||||
extern void __init at91_gpio_init(struct at91_gpio_bank *, int nr_banks);
|
||||
extern void __init at91_gpio_irq_setup(void);
|
||||
|
||||
extern void (*at91_arch_reset)(void);
|
||||
extern int at91_extern_irq;
|
||||
|
|
|
@ -47,6 +47,10 @@ static void at91_aic_unmask_irq(unsigned int irq)
|
|||
at91_sys_write(AT91_AIC_IECR, 1 << irq);
|
||||
}
|
||||
|
||||
unsigned int at91_extern_irq;
|
||||
|
||||
#define is_extern_irq(irq) ((1 << (irq)) & at91_extern_irq)
|
||||
|
||||
static int at91_aic_set_type(unsigned irq, unsigned type)
|
||||
{
|
||||
unsigned int smr, srctype;
|
||||
|
@ -59,14 +63,16 @@ static int at91_aic_set_type(unsigned irq, unsigned type)
|
|||
srctype = AT91_AIC_SRCTYPE_RISING;
|
||||
break;
|
||||
case IRQT_LOW:
|
||||
if ((irq > AT91_ID_FIQ) && (irq < AT91RM9200_ID_IRQ0)) /* only supported on external interrupts */
|
||||
if ((irq == AT91_ID_FIQ) || is_extern_irq(irq)) /* only supported on external interrupts */
|
||||
srctype = AT91_AIC_SRCTYPE_LOW;
|
||||
else
|
||||
return -EINVAL;
|
||||
srctype = AT91_AIC_SRCTYPE_LOW;
|
||||
break;
|
||||
case IRQT_FALLING:
|
||||
if ((irq > AT91_ID_FIQ) && (irq < AT91RM9200_ID_IRQ0)) /* only supported on external interrupts */
|
||||
if ((irq == AT91_ID_FIQ) || is_extern_irq(irq)) /* only supported on external interrupts */
|
||||
srctype = AT91_AIC_SRCTYPE_FALLING;
|
||||
else
|
||||
return -EINVAL;
|
||||
srctype = AT91_AIC_SRCTYPE_FALLING;
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
|
|
|
@ -112,7 +112,6 @@ EXPORT_SYMBOL(at91_suspend_entering_slow_clock);
|
|||
static void (*slow_clock)(void);
|
||||
|
||||
|
||||
|
||||
static int at91_pm_enter(suspend_state_t state)
|
||||
{
|
||||
at91_gpio_suspend();
|
||||
|
@ -123,13 +122,7 @@ static int at91_pm_enter(suspend_state_t state)
|
|||
(at91_sys_read(AT91_PMC_PCSR)
|
||||
| (1 << AT91_ID_FIQ)
|
||||
| (1 << AT91_ID_SYS)
|
||||
| (1 << AT91RM9200_ID_IRQ0)
|
||||
| (1 << AT91RM9200_ID_IRQ1)
|
||||
| (1 << AT91RM9200_ID_IRQ2)
|
||||
| (1 << AT91RM9200_ID_IRQ3)
|
||||
| (1 << AT91RM9200_ID_IRQ4)
|
||||
| (1 << AT91RM9200_ID_IRQ5)
|
||||
| (1 << AT91RM9200_ID_IRQ6))
|
||||
| (at91_extern_irq))
|
||||
& at91_sys_read(AT91_AIC_IMR),
|
||||
state);
|
||||
|
||||
|
|
|
@ -39,13 +39,15 @@ static inline void arch_idle(void)
|
|||
cpu_do_idle();
|
||||
}
|
||||
|
||||
void (*at91_arch_reset)(void);
|
||||
|
||||
static inline void arch_reset(char mode)
|
||||
{
|
||||
/*
|
||||
* Perform a hardware reset with the use of the Watchdog timer.
|
||||
*/
|
||||
at91_sys_write(AT91_ST_WDMR, AT91_ST_RSTEN | AT91_ST_EXTEN | 1);
|
||||
at91_sys_write(AT91_ST_CR, AT91_ST_WDRST);
|
||||
/* call the CPU-specific reset function */
|
||||
if (at91_arch_reset)
|
||||
(at91_arch_reset)();
|
||||
|
||||
for (;;) {} /* wait fovever */
|
||||
}
|
||||
|
||||
#define ARCH_ID_AT91RM9200 0x09200080
|
||||
|
|
Загрузка…
Ссылка в новой задаче