ARM / mach-shmobile: sh73a0 SMP TWD boot regression fix
authorKuninori Morimoto <kuninori.morimoto.gx@renesas.com>
Thu, 10 May 2012 07:26:58 +0000 (00:26 -0700)
committerRafael J. Wysocki <rjw@sisk.pl>
Sat, 12 May 2012 20:13:45 +0000 (22:13 +0200)
Fix SMP TWD boot regression on sh73a0 based platforms caused by:

4200b16 ARM: shmobile: convert to twd_local_timer_register() interface

After the merge of the above commit it has been impossible to boot
sh73a0 based SoCs with SMP enabled and CONFIG_HAVE_ARM_TWD=y. The
kernel crashes at smp_init_cpus() timing which is before the console
has been initialized, so to the user this looks like a kernel lock up
without any particular error message.

This patch fixes the regression on sh73a0 by moving the TWD
registration code from smp_init_cpus() to sys_timer->init() time.

This patch removed shmobile_twd_init() which is no longer needed

Signed-off-by: Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
Signed-off-by: Magnus Damm <damm@opensource.se>
Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl>
arch/arm/mach-shmobile/include/mach/common.h
arch/arm/mach-shmobile/setup-sh73a0.c
arch/arm/mach-shmobile/smp-sh73a0.c
arch/arm/mach-shmobile/timer.c

index 18ac8251a26a4119947c62b9bfdcf61cf67ceade..c85e6ecda606be97b7f951aea269b65630c11852 100644 (file)
@@ -4,7 +4,6 @@
 extern void shmobile_earlytimer_init(void);
 extern struct sys_timer shmobile_timer;
 struct twd_local_timer;
-void shmobile_twd_init(struct twd_local_timer *twd_local_timer);
 extern void shmobile_setup_console(void);
 extern void shmobile_secondary_vector(void);
 extern int shmobile_platform_cpu_kill(unsigned int cpu);
index 5bebffc10455ec88132dab1742da1f86b610bda8..04a0dfe754934c32c17d1d7a565201504bc520c1 100644 (file)
@@ -688,10 +688,14 @@ void __init sh73a0_add_standard_devices(void)
                            ARRAY_SIZE(sh73a0_late_devices));
 }
 
+/* do nothing for !CONFIG_SMP or !CONFIG_HAVE_TWD */
+void __init __weak sh73a0_register_twd(void) { }
+
 static void __init sh73a0_earlytimer_init(void)
 {
        sh73a0_clock_init();
        shmobile_earlytimer_init();
+       sh73a0_register_twd();
 }
 
 void __init sh73a0_add_early_devices(void)
index 14ad8b052f1a0944400d41ec559bc7188b8c5571..e36c41c4ab40f9067352825c7ce8ee30718a7f28 100644 (file)
@@ -42,7 +42,13 @@ static void __iomem *scu_base_addr(void)
 static DEFINE_SPINLOCK(scu_lock);
 static unsigned long tmp;
 
+#ifdef CONFIG_HAVE_ARM_TWD
 static DEFINE_TWD_LOCAL_TIMER(twd_local_timer, 0xf0000600, 29);
+void __init sh73a0_register_twd(void)
+{
+       twd_local_timer_register(&twd_local_timer);
+}
+#endif
 
 static void modify_scu_cpu_psr(unsigned long set, unsigned long clr)
 {
@@ -62,7 +68,6 @@ unsigned int __init sh73a0_get_core_count(void)
 {
        void __iomem *scu_base = scu_base_addr();
 
-       shmobile_twd_init(&twd_local_timer);
        return scu_get_core_count(scu_base);
 }
 
index 2fba5f3d1c8ad705309a2e1f3287af5fbb1aee06..8b79e7917a23149cd56645730fdf47d1a3e31c18 100644 (file)
@@ -46,15 +46,6 @@ static void __init shmobile_timer_init(void)
 {
 }
 
-void __init shmobile_twd_init(struct twd_local_timer *twd_local_timer)
-{
-#ifdef CONFIG_HAVE_ARM_TWD
-       int err = twd_local_timer_register(twd_local_timer);
-       if (err)
-               pr_err("twd_local_timer_register failed %d\n", err);
-#endif
-}
-
 struct sys_timer shmobile_timer = {
        .init           = shmobile_timer_init,
 };