All the calls to gic_secondary_init() pass 0 as the first argument.
Since this function is called on each CPU when starting, it can be done
in a platform-independent way via a CPU notifier registered by the GIC
code.
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>
Acked-by: Stephen Warren <swarren@nvidia.com>
Acked-by: Viresh Kumar <viresh.kumar@linaro.org>
Acked-by: Santosh Shilimkar <santosh.shilimkar@ti.com>
Acked-by: Rob Herring <rob.herring@calxeda.com>
Acked-by: Simon Horman <horms+renesas@verge.net.au>
Tested-by: Simon Horman <horms+renesas@verge.net.au>
Acked-by: Srinidhi Kasagar <srinidhi.kasagar@stericsson.com>
Tested-by: Dinh Nguyen <dinguyen@altera.com>
Acked-by: Nicolas Pitre <nico@linaro.org>
Tested-by: Marc Zyngier <marc.zyngier@arm.com>
Cc: Russell King <linux@arm.linux.org.uk>
Cc: Thomas Gleixner <tglx@linutronix.de>
Cc: Kukjin Kim <kgene.kim@samsung.com>
Cc: Sascha Hauer <kernel@pengutronix.de>
Cc: David Brown <davidb@codeaurora.org>
Cc: Bryan Huntsman <bryanh@codeaurora.org>
Cc: Tony Lindgren <tony@atomide.com>
Cc: Magnus Damm <magnus.damm@gmail.com>
Cc: Shiraz Hashim <shiraz.hashim@st.com>
Cc: Linus Walleij <linus.walleij@linaro.org>
Cc: Will Deacon <will.deacon@arm.com>
Cc: Kukjin Kim <kgene.kim@samsung.com>
Cc: Barry Song <baohua.song@csr.com>
 #include <linux/jiffies.h>
 #include <linux/smp.h>
 #include <linux/io.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/cacheflush.h>
 #include <asm/smp_plat.h>
 
 static void __cpuinit exynos_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
 #include <linux/init.h>
 #include <linux/smp.h>
 #include <linux/io.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/smp_scu.h>
 
 
 extern void secondary_startup(void);
 
-static void __cpuinit highbank_secondary_init(unsigned int cpu)
-{
-       gic_secondary_init(0);
-}
-
 static int __cpuinit highbank_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        highbank_set_cpu_jump(cpu, secondary_startup);
 struct smp_operations highbank_smp_ops __initdata = {
        .smp_init_cpus          = highbank_smp_init_cpus,
        .smp_prepare_cpus       = highbank_smp_prepare_cpus,
-       .smp_secondary_init     = highbank_secondary_init,
        .smp_boot_secondary     = highbank_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_die                = highbank_cpu_die,
 
 
 #include <linux/init.h>
 #include <linux/smp.h>
-#include <linux/irqchip/arm-gic.h>
 #include <asm/page.h>
 #include <asm/smp_scu.h>
 #include <asm/mach/map.h>
        writel_relaxed(val, scu_base);
 }
 
-static void __cpuinit imx_secondary_init(unsigned int cpu)
-{
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-}
-
 static int __cpuinit imx_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        imx_set_cpu_jump(cpu, v7_secondary_startup);
 struct smp_operations  imx_smp_ops __initdata = {
        .smp_init_cpus          = imx_smp_init_cpus,
        .smp_prepare_cpus       = imx_smp_prepare_cpus,
-       .smp_secondary_init     = imx_secondary_init,
        .smp_boot_secondary     = imx_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_die                = imx_cpu_die,
 
 #include <linux/jiffies.h>
 #include <linux/smp.h>
 #include <linux/io.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/cacheflush.h>
 #include <asm/cputype.h>
 
 static void __cpuinit msm_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
                omap_secure_dispatcher(OMAP4_PPA_CPU_ACTRL_SMP_INDEX,
                                                        4, 0, 0, 0, 0, 0);
 
-       /*
-        * If any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * Synchronise with the boot thread.
         */
 
 #include <linux/delay.h>
 #include <linux/of.h>
 #include <linux/of_address.h>
-#include <linux/irqchip/arm-gic.h>
 #include <asm/page.h>
 #include <asm/mach/map.h>
 #include <asm/smp_plat.h>
 
 static void __cpuinit sirfsoc_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
 #include <linux/spinlock.h>
 #include <linux/io.h>
 #include <linux/delay.h>
-#include <linux/irqchip/arm-gic.h>
 #include <mach/common.h>
 #include <mach/emev2.h>
 #include <asm/smp_plat.h>
 }
 
 
-static void __cpuinit emev2_secondary_init(unsigned int cpu)
-{
-       gic_secondary_init(0);
-}
-
 static int __cpuinit emev2_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        cpu = cpu_logical_map(cpu);
 struct smp_operations emev2_smp_ops __initdata = {
        .smp_init_cpus          = emev2_smp_init_cpus,
        .smp_prepare_cpus       = emev2_smp_prepare_cpus,
-       .smp_secondary_init     = emev2_secondary_init,
        .smp_boot_secondary     = emev2_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_kill               = emev2_cpu_kill,
 
 #include <linux/spinlock.h>
 #include <linux/io.h>
 #include <linux/delay.h>
-#include <linux/irqchip/arm-gic.h>
 #include <mach/common.h>
 #include <mach/r8a7779.h>
 #include <asm/smp_plat.h>
 }
 
 
-static void __cpuinit r8a7779_secondary_init(unsigned int cpu)
-{
-       gic_secondary_init(0);
-}
-
 static int __cpuinit r8a7779_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        struct r8a7779_pm_ch *ch = NULL;
 struct smp_operations r8a7779_smp_ops  __initdata = {
        .smp_init_cpus          = r8a7779_smp_init_cpus,
        .smp_prepare_cpus       = r8a7779_smp_prepare_cpus,
-       .smp_secondary_init     = r8a7779_secondary_init,
        .smp_boot_secondary     = r8a7779_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_kill               = r8a7779_cpu_kill,
 
 #include <linux/spinlock.h>
 #include <linux/io.h>
 #include <linux/delay.h>
-#include <linux/irqchip/arm-gic.h>
 #include <mach/common.h>
 #include <asm/cacheflush.h>
 #include <asm/smp_plat.h>
        return scu_get_core_count(scu_base);
 }
 
-static void __cpuinit sh73a0_secondary_init(unsigned int cpu)
-{
-       gic_secondary_init(0);
-}
-
 static int __cpuinit sh73a0_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        cpu = cpu_logical_map(cpu);
 struct smp_operations sh73a0_smp_ops __initdata = {
        .smp_init_cpus          = sh73a0_smp_init_cpus,
        .smp_prepare_cpus       = sh73a0_smp_prepare_cpus,
-       .smp_secondary_init     = sh73a0_secondary_init,
        .smp_boot_secondary     = sh73a0_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_kill               = sh73a0_cpu_kill,
 
 #include <linux/io.h>
 #include <linux/of.h>
 #include <linux/of_address.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/cacheflush.h>
 #include <asm/smp_scu.h>
 extern void __iomem *sys_manager_base_addr;
 extern void __iomem *rst_manager_base_addr;
 
-static void __cpuinit socfpga_secondary_init(unsigned int cpu)
-{
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-}
-
 static int __cpuinit socfpga_boot_secondary(unsigned int cpu, struct task_struct *idle)
 {
        int trampoline_size = &secondary_trampoline_end - &secondary_trampoline;
 struct smp_operations socfpga_smp_ops __initdata = {
        .smp_init_cpus          = socfpga_smp_init_cpus,
        .smp_prepare_cpus       = socfpga_smp_prepare_cpus,
-       .smp_secondary_init     = socfpga_secondary_init,
        .smp_boot_secondary     = socfpga_boot_secondary,
 #ifdef CONFIG_HOTPLUG_CPU
        .cpu_die                = socfpga_cpu_die,
 
 #include <linux/jiffies.h>
 #include <linux/io.h>
 #include <linux/smp.h>
-#include <linux/irqchip/arm-gic.h>
 #include <asm/cacheflush.h>
 #include <asm/smp_scu.h>
 #include <mach/spear.h>
 
 static void __cpuinit spear13xx_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
 #include <linux/jiffies.h>
 #include <linux/smp.h>
 #include <linux/io.h>
-#include <linux/irqchip/arm-gic.h>
 #include <linux/clk/tegra.h>
 
 #include <asm/cacheflush.h>
 
 static void __cpuinit tegra_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        cpumask_set_cpu(cpu, &tegra_cpu_init_mask);
 }
 
 
 #include <linux/device.h>
 #include <linux/smp.h>
 #include <linux/io.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/cacheflush.h>
 #include <asm/smp_plat.h>
 
 static void __cpuinit ux500_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
 #include <linux/smp.h>
 #include <linux/of.h>
 
-#include <linux/irqchip/arm-gic.h>
-
 #include <asm/psci.h>
 #include <asm/smp_plat.h>
 
        return -ENODEV;
 }
 
-static void __cpuinit virt_secondary_init(unsigned int cpu)
-{
-       gic_secondary_init(0);
-}
-
 struct smp_operations __initdata virt_smp_ops = {
        .smp_init_cpus          = virt_smp_init_cpus,
        .smp_prepare_cpus       = virt_smp_prepare_cpus,
-       .smp_secondary_init     = virt_secondary_init,
        .smp_boot_secondary     = virt_boot_secondary,
 };
 
 #include <linux/device.h>
 #include <linux/jiffies.h>
 #include <linux/smp.h>
-#include <linux/irqchip/arm-gic.h>
 
 #include <asm/cacheflush.h>
 #include <asm/smp_plat.h>
 
 void __cpuinit versatile_secondary_init(unsigned int cpu)
 {
-       /*
-        * if any interrupts are already enabled for the primary
-        * core (e.g. timer irq), then they will not have been enabled
-        * for us: do so
-        */
-       gic_secondary_init(0);
-
        /*
         * let the primary processor know we're out of the
         * pen, then head off into the C entry point
 
 #include <linux/module.h>
 #include <linux/list.h>
 #include <linux/smp.h>
+#include <linux/cpu.h>
 #include <linux/cpu_pm.h>
 #include <linux/cpumask.h>
 #include <linux/io.h>
        return 0;
 }
 
+#ifdef CONFIG_SMP
+static int __cpuinit gic_secondary_init(struct notifier_block *nfb,
+                                       unsigned long action, void *hcpu)
+{
+       if (action == CPU_STARTING)
+               gic_cpu_init(&gic_data[0]);
+       return NOTIFY_OK;
+}
+
+/*
+ * Notifier for enabling the GIC CPU interface. Set an arbitrarily high
+ * priority because the GIC needs to be up before the ARM generic timers.
+ */
+static struct notifier_block __cpuinitdata gic_cpu_notifier = {
+       .notifier_call = gic_secondary_init,
+       .priority = 100,
+};
+#endif
+
 const struct irq_domain_ops gic_irq_domain_ops = {
        .map = gic_irq_domain_map,
        .xlate = gic_irq_domain_xlate,
 
 #ifdef CONFIG_SMP
        set_smp_cross_call(gic_raise_softirq);
+       register_cpu_notifier(&gic_cpu_notifier);
 #endif
 
        set_handle_irq(gic_handle_irq);
        gic_pm_init(gic);
 }
 
-void __cpuinit gic_secondary_init(unsigned int gic_nr)
-{
-       BUG_ON(gic_nr >= MAX_GIC_NR);
-
-       gic_cpu_init(&gic_data[gic_nr]);
-}
-
 #ifdef CONFIG_OF
 static int gic_cnt __initdata = 0;
 
 
 
 void gic_init_bases(unsigned int, int, void __iomem *, void __iomem *,
                    u32 offset, struct device_node *);
-void gic_secondary_init(unsigned int);
 void gic_cascade_irq(unsigned int gic_nr, unsigned int irq);
 
 static inline void gic_init(unsigned int nr, int start,