ARM i.MX irq: Compile avic irq code only on SoCs that need it
authorSascha Hauer <s.hauer@pengutronix.de>
Fri, 5 Nov 2010 08:37:22 +0000 (09:37 +0100)
committerSascha Hauer <s.hauer@pengutronix.de>
Wed, 24 Nov 2010 09:08:58 +0000 (10:08 +0100)
This patch adds a Kconfig option for the avic irq controller
and lets the SoCs that need it select this option.
Also, as we have two irq controllers for i.MX, irq.c is not
appropriate anymore, so rename it to avic.c

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
arch/arm/mach-imx/Kconfig
arch/arm/mach-mx3/Kconfig
arch/arm/plat-mxc/Kconfig
arch/arm/plat-mxc/Makefile
arch/arm/plat-mxc/avic.c [new file with mode: 0644]
arch/arm/plat-mxc/irq.c [deleted file]

index 41b6450df810f85a482d9ca90578bdfb40575c8b..8a9de1751b7910cf2ee0b09ba4aca3e89a15adf6 100644 (file)
@@ -6,6 +6,7 @@ config SOC_IMX1
        select CPU_ARM920T
        select IMX_HAVE_DMA_V1
        select IMX_HAVE_IOMUX_V1
+       select MXC_AVIC
 
 config SOC_IMX21
        bool
@@ -13,12 +14,14 @@ config SOC_IMX21
        select ARCH_MXC_AUDMUX_V1
        select IMX_HAVE_DMA_V1
        select IMX_HAVE_IOMUX_V1
+       select MXC_AVIC
 
 config SOC_IMX25
        bool
        select CPU_ARM926T
        select ARCH_MXC_AUDMUX_V2
        select ARCH_MXC_IOMUX_V3
+       select MXC_AVIC
 
 config SOC_IMX27
        bool
@@ -26,6 +29,7 @@ config SOC_IMX27
        select ARCH_MXC_AUDMUX_V1
        select IMX_HAVE_DMA_V1
        select IMX_HAVE_IOMUX_V1
+       select MXC_AVIC
 
 if ARCH_MX1
 
index a682c03a1f94876754debb50a9541136c70e879a..165e7221c500f8d4c2f682620e3ccbe15ec17732 100644 (file)
@@ -15,6 +15,7 @@ config SOC_IMX31
        select IMX_HAVE_PLATFORM_MXC_RNGA
        select ARCH_MXC_AUDMUX_V2
        select ARCH_MX31
+       select MXC_AVIC
 
 config SOC_IMX35
        bool
@@ -22,6 +23,7 @@ config SOC_IMX35
        select ARCH_MXC_AUDMUX_V2
        select HAVE_EPIT
        select ARCH_MX35
+       select MXC_AVIC
 
 comment "MX3 platforms:"
 
index a31fa161bb6d5fa6df0a3bf94683e7745f3f4355..6c66bc0521d81d02f62ce29298b8ced713c665d8 100644 (file)
@@ -70,6 +70,9 @@ config MXC_TZIC
          containing this interrupt controller.
          Say N here only if you are really sure.
 
+config MXC_AVIC
+       bool
+
 config MXC_PWM
        tristate "Enable PWM driver"
        select HAVE_PWM
index 372670952789a0e6d583ec1186721d62ba1c9085..989cb59e67ac648ac8530f702c3481722d8b8b43 100644 (file)
@@ -3,10 +3,11 @@
 #
 
 # Common support
-obj-y := irq.o clock.o gpio.o time.o devices.o cpu.o system.o
+obj-y := clock.o gpio.o time.o devices.o cpu.o system.o
 
-# MX51 uses the TZIC interrupt controller, older platforms use AVIC (irq.o)
+# MX51 uses the TZIC interrupt controller, older platforms use AVIC
 obj-$(CONFIG_MXC_TZIC) += tzic.o
+obj-$(CONFIG_MXC_AVIC) += avic.o
 
 obj-$(CONFIG_IMX_HAVE_IOMUX_V1) += iomux-v1.o
 obj-$(CONFIG_ARCH_MXC_IOMUX_V3) += iomux-v3.o
diff --git a/arch/arm/plat-mxc/avic.c b/arch/arm/plat-mxc/avic.c
new file mode 100644 (file)
index 0000000..7331f2a
--- /dev/null
@@ -0,0 +1,152 @@
+/*
+ * Copyright 2004-2007 Freescale Semiconductor, Inc. All Rights Reserved.
+ * Copyright 2008 Juergen Beisert, kernel@pengutronix.de
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA  02110-1301, USA.
+ */
+
+#include <linux/module.h>
+#include <linux/irq.h>
+#include <linux/io.h>
+#include <mach/common.h>
+#include <asm/mach/irq.h>
+#include <mach/hardware.h>
+
+#define AVIC_INTCNTL           0x00    /* int control reg */
+#define AVIC_NIMASK            0x04    /* int mask reg */
+#define AVIC_INTENNUM          0x08    /* int enable number reg */
+#define AVIC_INTDISNUM         0x0C    /* int disable number reg */
+#define AVIC_INTENABLEH                0x10    /* int enable reg high */
+#define AVIC_INTENABLEL                0x14    /* int enable reg low */
+#define AVIC_INTTYPEH          0x18    /* int type reg high */
+#define AVIC_INTTYPEL          0x1C    /* int type reg low */
+#define AVIC_NIPRIORITY(x)     (0x20 + 4 * (7 - (x))) /* int priority */
+#define AVIC_NIVECSR           0x40    /* norm int vector/status */
+#define AVIC_FIVECSR           0x44    /* fast int vector/status */
+#define AVIC_INTSRCH           0x48    /* int source reg high */
+#define AVIC_INTSRCL           0x4C    /* int source reg low */
+#define AVIC_INTFRCH           0x50    /* int force reg high */
+#define AVIC_INTFRCL           0x54    /* int force reg low */
+#define AVIC_NIPNDH            0x58    /* norm int pending high */
+#define AVIC_NIPNDL            0x5C    /* norm int pending low */
+#define AVIC_FIPNDH            0x60    /* fast int pending high */
+#define AVIC_FIPNDL            0x64    /* fast int pending low */
+
+void __iomem *avic_base;
+
+int imx_irq_set_priority(unsigned char irq, unsigned char prio)
+{
+#ifdef CONFIG_MXC_IRQ_PRIOR
+       unsigned int temp;
+       unsigned int mask = 0x0F << irq % 8 * 4;
+
+       if (irq >= MXC_INTERNAL_IRQS)
+               return -EINVAL;;
+
+       temp = __raw_readl(avic_base + AVIC_NIPRIORITY(irq / 8));
+       temp &= ~mask;
+       temp |= prio & mask;
+
+       __raw_writel(temp, avic_base + AVIC_NIPRIORITY(irq / 8));
+
+       return 0;
+#else
+       return -ENOSYS;
+#endif
+}
+EXPORT_SYMBOL(imx_irq_set_priority);
+
+#ifdef CONFIG_FIQ
+int mxc_set_irq_fiq(unsigned int irq, unsigned int type)
+{
+       unsigned int irqt;
+
+       if (irq >= MXC_INTERNAL_IRQS)
+               return -EINVAL;
+
+       if (irq < MXC_INTERNAL_IRQS / 2) {
+               irqt = __raw_readl(avic_base + AVIC_INTTYPEL) & ~(1 << irq);
+               __raw_writel(irqt | (!!type << irq), avic_base + AVIC_INTTYPEL);
+       } else {
+               irq -= MXC_INTERNAL_IRQS / 2;
+               irqt = __raw_readl(avic_base + AVIC_INTTYPEH) & ~(1 << irq);
+               __raw_writel(irqt | (!!type << irq), avic_base + AVIC_INTTYPEH);
+       }
+
+       return 0;
+}
+EXPORT_SYMBOL(mxc_set_irq_fiq);
+#endif /* CONFIG_FIQ */
+
+/* Disable interrupt number "irq" in the AVIC */
+static void mxc_mask_irq(unsigned int irq)
+{
+       __raw_writel(irq, avic_base + AVIC_INTDISNUM);
+}
+
+/* Enable interrupt number "irq" in the AVIC */
+static void mxc_unmask_irq(unsigned int irq)
+{
+       __raw_writel(irq, avic_base + AVIC_INTENNUM);
+}
+
+static struct irq_chip mxc_avic_chip = {
+       .ack = mxc_mask_irq,
+       .mask = mxc_mask_irq,
+       .unmask = mxc_unmask_irq,
+};
+
+/*
+ * This function initializes the AVIC hardware and disables all the
+ * interrupts. It registers the interrupt enable and disable functions
+ * to the kernel for each interrupt source.
+ */
+void __init mxc_init_irq(void __iomem *irqbase)
+{
+       int i;
+
+       avic_base = irqbase;
+
+       /* put the AVIC into the reset value with
+        * all interrupts disabled
+        */
+       __raw_writel(0, avic_base + AVIC_INTCNTL);
+       __raw_writel(0x1f, avic_base + AVIC_NIMASK);
+
+       /* disable all interrupts */
+       __raw_writel(0, avic_base + AVIC_INTENABLEH);
+       __raw_writel(0, avic_base + AVIC_INTENABLEL);
+
+       /* all IRQ no FIQ */
+       __raw_writel(0, avic_base + AVIC_INTTYPEH);
+       __raw_writel(0, avic_base + AVIC_INTTYPEL);
+       for (i = 0; i < MXC_INTERNAL_IRQS; i++) {
+               set_irq_chip(i, &mxc_avic_chip);
+               set_irq_handler(i, handle_level_irq);
+               set_irq_flags(i, IRQF_VALID);
+       }
+
+       /* Set default priority value (0) for all IRQ's */
+       for (i = 0; i < 8; i++)
+               __raw_writel(0, avic_base + AVIC_NIPRIORITY(i));
+
+#ifdef CONFIG_FIQ
+       /* Initialize FIQ */
+       init_FIQ();
+#endif
+
+       printk(KERN_INFO "MXC IRQ initialized\n");
+}
+
diff --git a/arch/arm/plat-mxc/irq.c b/arch/arm/plat-mxc/irq.c
deleted file mode 100644 (file)
index 7331f2a..0000000
+++ /dev/null
@@ -1,152 +0,0 @@
-/*
- * Copyright 2004-2007 Freescale Semiconductor, Inc. All Rights Reserved.
- * Copyright 2008 Juergen Beisert, kernel@pengutronix.de
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
- * MA  02110-1301, USA.
- */
-
-#include <linux/module.h>
-#include <linux/irq.h>
-#include <linux/io.h>
-#include <mach/common.h>
-#include <asm/mach/irq.h>
-#include <mach/hardware.h>
-
-#define AVIC_INTCNTL           0x00    /* int control reg */
-#define AVIC_NIMASK            0x04    /* int mask reg */
-#define AVIC_INTENNUM          0x08    /* int enable number reg */
-#define AVIC_INTDISNUM         0x0C    /* int disable number reg */
-#define AVIC_INTENABLEH                0x10    /* int enable reg high */
-#define AVIC_INTENABLEL                0x14    /* int enable reg low */
-#define AVIC_INTTYPEH          0x18    /* int type reg high */
-#define AVIC_INTTYPEL          0x1C    /* int type reg low */
-#define AVIC_NIPRIORITY(x)     (0x20 + 4 * (7 - (x))) /* int priority */
-#define AVIC_NIVECSR           0x40    /* norm int vector/status */
-#define AVIC_FIVECSR           0x44    /* fast int vector/status */
-#define AVIC_INTSRCH           0x48    /* int source reg high */
-#define AVIC_INTSRCL           0x4C    /* int source reg low */
-#define AVIC_INTFRCH           0x50    /* int force reg high */
-#define AVIC_INTFRCL           0x54    /* int force reg low */
-#define AVIC_NIPNDH            0x58    /* norm int pending high */
-#define AVIC_NIPNDL            0x5C    /* norm int pending low */
-#define AVIC_FIPNDH            0x60    /* fast int pending high */
-#define AVIC_FIPNDL            0x64    /* fast int pending low */
-
-void __iomem *avic_base;
-
-int imx_irq_set_priority(unsigned char irq, unsigned char prio)
-{
-#ifdef CONFIG_MXC_IRQ_PRIOR
-       unsigned int temp;
-       unsigned int mask = 0x0F << irq % 8 * 4;
-
-       if (irq >= MXC_INTERNAL_IRQS)
-               return -EINVAL;;
-
-       temp = __raw_readl(avic_base + AVIC_NIPRIORITY(irq / 8));
-       temp &= ~mask;
-       temp |= prio & mask;
-
-       __raw_writel(temp, avic_base + AVIC_NIPRIORITY(irq / 8));
-
-       return 0;
-#else
-       return -ENOSYS;
-#endif
-}
-EXPORT_SYMBOL(imx_irq_set_priority);
-
-#ifdef CONFIG_FIQ
-int mxc_set_irq_fiq(unsigned int irq, unsigned int type)
-{
-       unsigned int irqt;
-
-       if (irq >= MXC_INTERNAL_IRQS)
-               return -EINVAL;
-
-       if (irq < MXC_INTERNAL_IRQS / 2) {
-               irqt = __raw_readl(avic_base + AVIC_INTTYPEL) & ~(1 << irq);
-               __raw_writel(irqt | (!!type << irq), avic_base + AVIC_INTTYPEL);
-       } else {
-               irq -= MXC_INTERNAL_IRQS / 2;
-               irqt = __raw_readl(avic_base + AVIC_INTTYPEH) & ~(1 << irq);
-               __raw_writel(irqt | (!!type << irq), avic_base + AVIC_INTTYPEH);
-       }
-
-       return 0;
-}
-EXPORT_SYMBOL(mxc_set_irq_fiq);
-#endif /* CONFIG_FIQ */
-
-/* Disable interrupt number "irq" in the AVIC */
-static void mxc_mask_irq(unsigned int irq)
-{
-       __raw_writel(irq, avic_base + AVIC_INTDISNUM);
-}
-
-/* Enable interrupt number "irq" in the AVIC */
-static void mxc_unmask_irq(unsigned int irq)
-{
-       __raw_writel(irq, avic_base + AVIC_INTENNUM);
-}
-
-static struct irq_chip mxc_avic_chip = {
-       .ack = mxc_mask_irq,
-       .mask = mxc_mask_irq,
-       .unmask = mxc_unmask_irq,
-};
-
-/*
- * This function initializes the AVIC hardware and disables all the
- * interrupts. It registers the interrupt enable and disable functions
- * to the kernel for each interrupt source.
- */
-void __init mxc_init_irq(void __iomem *irqbase)
-{
-       int i;
-
-       avic_base = irqbase;
-
-       /* put the AVIC into the reset value with
-        * all interrupts disabled
-        */
-       __raw_writel(0, avic_base + AVIC_INTCNTL);
-       __raw_writel(0x1f, avic_base + AVIC_NIMASK);
-
-       /* disable all interrupts */
-       __raw_writel(0, avic_base + AVIC_INTENABLEH);
-       __raw_writel(0, avic_base + AVIC_INTENABLEL);
-
-       /* all IRQ no FIQ */
-       __raw_writel(0, avic_base + AVIC_INTTYPEH);
-       __raw_writel(0, avic_base + AVIC_INTTYPEL);
-       for (i = 0; i < MXC_INTERNAL_IRQS; i++) {
-               set_irq_chip(i, &mxc_avic_chip);
-               set_irq_handler(i, handle_level_irq);
-               set_irq_flags(i, IRQF_VALID);
-       }
-
-       /* Set default priority value (0) for all IRQ's */
-       for (i = 0; i < 8; i++)
-               __raw_writel(0, avic_base + AVIC_NIPRIORITY(i));
-
-#ifdef CONFIG_FIQ
-       /* Initialize FIQ */
-       init_FIQ();
-#endif
-
-       printk(KERN_INFO "MXC IRQ initialized\n");
-}
-