|
@@ -418,19 +418,22 @@ static int watchdog_prepare_cpu(int cpu)
|
|
static int watchdog_enable(int cpu)
|
|
static int watchdog_enable(int cpu)
|
|
{
|
|
{
|
|
struct task_struct *p = per_cpu(softlockup_watchdog, cpu);
|
|
struct task_struct *p = per_cpu(softlockup_watchdog, cpu);
|
|
- int err;
|
|
|
|
|
|
+ int err = 0;
|
|
|
|
|
|
/* enable the perf event */
|
|
/* enable the perf event */
|
|
err = watchdog_nmi_enable(cpu);
|
|
err = watchdog_nmi_enable(cpu);
|
|
- if (err)
|
|
|
|
- return err;
|
|
|
|
|
|
+
|
|
|
|
+ /* Regardless of err above, fall through and start softlockup */
|
|
|
|
|
|
/* create the watchdog thread */
|
|
/* create the watchdog thread */
|
|
if (!p) {
|
|
if (!p) {
|
|
p = kthread_create(watchdog, (void *)(unsigned long)cpu, "watchdog/%d", cpu);
|
|
p = kthread_create(watchdog, (void *)(unsigned long)cpu, "watchdog/%d", cpu);
|
|
if (IS_ERR(p)) {
|
|
if (IS_ERR(p)) {
|
|
printk(KERN_ERR "softlockup watchdog for %i failed\n", cpu);
|
|
printk(KERN_ERR "softlockup watchdog for %i failed\n", cpu);
|
|
- return PTR_ERR(p);
|
|
|
|
|
|
+ if (!err)
|
|
|
|
+ /* if hardlockup hasn't already set this */
|
|
|
|
+ err = PTR_ERR(p);
|
|
|
|
+ goto out;
|
|
}
|
|
}
|
|
kthread_bind(p, cpu);
|
|
kthread_bind(p, cpu);
|
|
per_cpu(watchdog_touch_ts, cpu) = 0;
|
|
per_cpu(watchdog_touch_ts, cpu) = 0;
|
|
@@ -438,7 +441,8 @@ static int watchdog_enable(int cpu)
|
|
wake_up_process(p);
|
|
wake_up_process(p);
|
|
}
|
|
}
|
|
|
|
|
|
- return 0;
|
|
|
|
|
|
+out:
|
|
|
|
+ return err;
|
|
}
|
|
}
|
|
|
|
|
|
static void watchdog_disable(int cpu)
|
|
static void watchdog_disable(int cpu)
|
|
@@ -550,7 +554,13 @@ cpu_callback(struct notifier_block *nfb, unsigned long action, void *hcpu)
|
|
break;
|
|
break;
|
|
#endif /* CONFIG_HOTPLUG_CPU */
|
|
#endif /* CONFIG_HOTPLUG_CPU */
|
|
}
|
|
}
|
|
- return notifier_from_errno(err);
|
|
|
|
|
|
+
|
|
|
|
+ /*
|
|
|
|
+ * hardlockup and softlockup are not important enough
|
|
|
|
+ * to block cpu bring up. Just always succeed and
|
|
|
|
+ * rely on printk output to flag problems.
|
|
|
|
+ */
|
|
|
|
+ return NOTIFY_OK;
|
|
}
|
|
}
|
|
|
|
|
|
static struct notifier_block __cpuinitdata cpu_nfb = {
|
|
static struct notifier_block __cpuinitdata cpu_nfb = {
|