Commit d8ff1505 authored by Mikael Pettersson's avatar Mikael Pettersson Committed by Linus Torvalds

[PATCH] lapic_nmi_watchdog resume fix

I managed to add a bug to the local APIC NMI watchdog's
resume procedure in the driver model conversion for 2.5.67.
The problem is that the resume procedure simply calls the
enable procedure. If the NMI watchdog has been disabled by
another driver (like oprofile or perfctr), then the NMI
watchdog will incorrectly be re-enabled.

I discovered this when updating the perfctr driver for 2.5.67
and seeing unexpected NMIs after a resume from apm --suspend.

We can fix this by unregistering the NMI watchdog from the
driver model when disabling it (like the code did before the
driver model changes), or by remembering the previous state
at suspend and checking it at resume. The patch below uses
the second, simpler, approach. Tested, please apply.
parent ffc06ab0
...@@ -181,11 +181,13 @@ void enable_lapic_nmi_watchdog(void) ...@@ -181,11 +181,13 @@ void enable_lapic_nmi_watchdog(void)
#ifdef CONFIG_PM #ifdef CONFIG_PM
#include <linux/device.h> #include <linux/device.h>
static int nmi_pm_active; /* nmi_active before suspend */
static int lapic_nmi_suspend(struct device *dev, u32 state, u32 level) static int lapic_nmi_suspend(struct device *dev, u32 state, u32 level)
{ {
if (level != SUSPEND_POWER_DOWN) if (level != SUSPEND_POWER_DOWN)
return 0; return 0;
nmi_pm_active = nmi_active;
disable_lapic_nmi_watchdog(); disable_lapic_nmi_watchdog();
return 0; return 0;
} }
...@@ -194,6 +196,7 @@ static int lapic_nmi_resume(struct device *dev, u32 level) ...@@ -194,6 +196,7 @@ static int lapic_nmi_resume(struct device *dev, u32 level)
{ {
if (level != RESUME_POWER_ON) if (level != RESUME_POWER_ON)
return 0; return 0;
if (nmi_pm_active > 0)
enable_lapic_nmi_watchdog(); enable_lapic_nmi_watchdog();
return 0; return 0;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment