summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHaojian Zhuang <haojian.zhuang@marvell.com>2009-11-02 14:02:21 -0500
committerEric Miao <eric.y.miao@gmail.com>2009-11-03 12:00:56 +0800
commitc482ae4dcf23fd241321595d71bbe8aee33eabf5 (patch)
treefb523d3ec1a368124e3985dedcb9790f2374d84c
parent902805dbdae016653768f7139d7b3ab36a20cc6d (diff)
[ARM] pxa: fix resume failure by saving/restoring IPRx registers
Since interrupt handler is changed to use interrupt priority, we also need to save and restore these interrupt controller registers in suspend/resume routine. Signed-off-by: Haojian Zhuang <haojian.zhuang@marvell.com> Tested-by: Daniel Mack <daniel@caiaq.de> Tested-by: Pavel Machek <pavel@ucw.cz> Tested-by: Robert Jarzmik <robert.jarzmik@free.fr> Acked-by: Pavel Machek <pavel@ucw.cz> Signed-off-by: Eric Miao <eric.y.miao@gmail.com>
-rw-r--r--arch/arm/mach-pxa/irq.c11
1 files changed, 10 insertions, 1 deletions
diff --git a/arch/arm/mach-pxa/irq.c b/arch/arm/mach-pxa/irq.c
index d694ce28966..6112af431fa 100644
--- a/arch/arm/mach-pxa/irq.c
+++ b/arch/arm/mach-pxa/irq.c
@@ -25,6 +25,8 @@
#include "generic.h"
+#define MAX_INTERNAL_IRQS 128
+
#define IRQ_BIT(n) (((n) - PXA_IRQ(0)) & 0x1f)
#define _ICMR(n) (*((((n) - PXA_IRQ(0)) & ~0x1f) ? &ICMR2 : &ICMR))
#define _ICLR(n) (*((((n) - PXA_IRQ(0)) & ~0x1f) ? &ICLR2 : &ICLR))
@@ -122,6 +124,8 @@ void __init pxa_init_irq(int irq_nr, set_wake_t fn)
{
int irq, i;
+ BUG_ON(irq_nr > MAX_INTERNAL_IRQS);
+
pxa_internal_irq_nr = irq_nr;
for (irq = PXA_IRQ(0); irq < PXA_IRQ(irq_nr); irq += 32) {
@@ -149,7 +153,8 @@ void __init pxa_init_irq(int irq_nr, set_wake_t fn)
}
#ifdef CONFIG_PM
-static unsigned long saved_icmr[2];
+static unsigned long saved_icmr[MAX_INTERNAL_IRQS/32];
+static unsigned long saved_ipr[MAX_INTERNAL_IRQS];
static int pxa_irq_suspend(struct sys_device *dev, pm_message_t state)
{
@@ -159,6 +164,8 @@ static int pxa_irq_suspend(struct sys_device *dev, pm_message_t state)
saved_icmr[i] = _ICMR(irq);
_ICMR(irq) = 0;
}
+ for (i = 0; i < pxa_internal_irq_nr; i++)
+ saved_ipr[i] = IPR(i);
return 0;
}
@@ -171,6 +178,8 @@ static int pxa_irq_resume(struct sys_device *dev)
_ICMR(irq) = saved_icmr[i];
_ICLR(irq) = 0;
}
+ for (i = 0; i < pxa_internal_irq_nr; i++)
+ IPR(i) = saved_ipr[i];
ICCR = 1;
return 0;