diff options
Diffstat (limited to 'kernel/watchdog.c')
| -rw-r--r-- | kernel/watchdog.c | 20 | 
1 files changed, 15 insertions, 5 deletions
| diff --git a/kernel/watchdog.c b/kernel/watchdog.c index 613bc1f0461..7f9c3c52ecc 100644 --- a/kernel/watchdog.c +++ b/kernel/watchdog.c @@ -122,7 +122,7 @@ static void __touch_watchdog(void)  void touch_softlockup_watchdog(void)  { -	__get_cpu_var(watchdog_touch_ts) = 0; +	__raw_get_cpu_var(watchdog_touch_ts) = 0;  }  EXPORT_SYMBOL(touch_softlockup_watchdog); @@ -142,7 +142,14 @@ void touch_all_softlockup_watchdogs(void)  #ifdef CONFIG_HARDLOCKUP_DETECTOR  void touch_nmi_watchdog(void)  { -	__get_cpu_var(watchdog_nmi_touch) = true; +	if (watchdog_enabled) { +		unsigned cpu; + +		for_each_present_cpu(cpu) { +			if (per_cpu(watchdog_nmi_touch, cpu) != true) +				per_cpu(watchdog_nmi_touch, cpu) = true; +		} +	}  	touch_softlockup_watchdog();  }  EXPORT_SYMBOL(touch_nmi_watchdog); @@ -206,6 +213,9 @@ void watchdog_overflow_callback(struct perf_event *event, int nmi,  		 struct perf_sample_data *data,  		 struct pt_regs *regs)  { +	/* Ensure the watchdog never gets throttled */ +	event->hw.interrupts = 0; +  	if (__get_cpu_var(watchdog_nmi_touch) == true) {  		__get_cpu_var(watchdog_nmi_touch) = false;  		return; @@ -430,6 +440,9 @@ static int watchdog_enable(int cpu)  		wake_up_process(p);  	} +	/* if any cpu succeeds, watchdog is considered enabled for the system */ +	watchdog_enabled = 1; +  	return 0;  } @@ -452,9 +465,6 @@ static void watchdog_disable(int cpu)  		per_cpu(softlockup_watchdog, cpu) = NULL;  		kthread_stop(p);  	} - -	/* if any cpu succeeds, watchdog is considered enabled for the system */ -	watchdog_enabled = 1;  }  static void watchdog_enable_all_cpus(void) | 
