diff options
author | bajones@chromium.org <bajones@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-08-06 20:23:48 +0000 |
---|---|---|
committer | bajones@chromium.org <bajones@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-08-06 20:23:48 +0000 |
commit | 21e2490fa8fce98fdebab07ca9e357b06cbbee5d (patch) | |
tree | 9ba444828d74446d0f884439036237a01e68a50e /content/gpu | |
parent | ab9793449fc2cdca1249193232e7357f19eaafcc (diff) | |
download | chromium_src-21e2490fa8fce98fdebab07ca9e357b06cbbee5d.zip chromium_src-21e2490fa8fce98fdebab07ca9e357b06cbbee5d.tar.gz chromium_src-21e2490fa8fce98fdebab07ca9e357b06cbbee5d.tar.bz2 |
Added suspend/resume detection to the GpuWatchdogThread
The watchdog will be "paused" while the system is suspending/suspended to
prevent false positives that may result from erratic behavior during hibernate.
BUG=258617
Review URL: https://chromiumcodereview.appspot.com/22289002
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@215961 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'content/gpu')
-rw-r--r-- | content/gpu/gpu_main.cc | 3 | ||||
-rw-r--r-- | content/gpu/gpu_watchdog_thread.cc | 50 | ||||
-rw-r--r-- | content/gpu/gpu_watchdog_thread.h | 14 |
3 files changed, 65 insertions, 2 deletions
diff --git a/content/gpu/gpu_main.cc b/content/gpu/gpu_main.cc index 2bcff39..5c35707 100644 --- a/content/gpu/gpu_main.cc +++ b/content/gpu/gpu_main.cc @@ -294,6 +294,9 @@ int GpuMain(const MainFunctionParams& parameters) { gpu_process.set_main_thread(child_thread); + if (watchdog_thread) + watchdog_thread->AddPowerObserver(); + { TRACE_EVENT0("gpu", "Run Message Loop"); main_message_loop.Run(); diff --git a/content/gpu/gpu_watchdog_thread.cc b/content/gpu/gpu_watchdog_thread.cc index e823edd..17889b7 100644 --- a/content/gpu/gpu_watchdog_thread.cc +++ b/content/gpu/gpu_watchdog_thread.cc @@ -12,6 +12,7 @@ #include "base/bind_helpers.h" #include "base/command_line.h" #include "base/compiler_specific.h" +#include "base/power_monitor/power_monitor.h" #include "base/process/process.h" #include "build/build_config.h" #include "content/public/common/content_switches.h" @@ -32,7 +33,8 @@ GpuWatchdogThread::GpuWatchdogThread(int timeout) arm_cpu_time_(), #endif task_observer_(this), - weak_factory_(this) { + weak_factory_(this), + suspended_(false) { DCHECK(timeout >= 0); #if defined(OS_WIN) @@ -104,10 +106,16 @@ GpuWatchdogThread::~GpuWatchdogThread() { CloseHandle(watched_thread_handle_); #endif + base::PowerMonitor* power_monitor = base::PowerMonitor::Get(); + if (power_monitor) + power_monitor->RemoveObserver(this); + watched_message_loop_->RemoveTaskObserver(&task_observer_); } void GpuWatchdogThread::OnAcknowledge() { + CHECK(base::PlatformThread::CurrentId() == thread_id()); + // The check has already been acknowledged and another has already been // scheduled by a previous call to OnAcknowledge. It is normal for a // watched thread to see armed_ being true multiple times before @@ -119,6 +127,9 @@ void GpuWatchdogThread::OnAcknowledge() { weak_factory_.InvalidateWeakPtrs(); armed_ = false; + if (suspended_) + return; + // If it took a long time for the acknowledgement, assume the computer was // recently suspended. bool was_suspended = (base::Time::Now() > suspension_timeout_); @@ -132,7 +143,11 @@ void GpuWatchdogThread::OnAcknowledge() { } void GpuWatchdogThread::OnCheck(bool after_suspend) { - if (armed_) + CHECK(base::PlatformThread::CurrentId() == thread_id()); + + // Do not create any new termination tasks if one has already been created + // or the system is suspended. + if (armed_ || suspended_) return; // Must set armed before posting the task. This task might be the only task @@ -168,6 +183,9 @@ void GpuWatchdogThread::OnCheck(bool after_suspend) { // Use the --disable-gpu-watchdog command line switch to disable this. void GpuWatchdogThread::DeliberatelyTerminateToRecoverFromHang() { + // Should not get here while the system is suspended. + DCHECK(!suspended_); + #if defined(OS_WIN) // Defer termination until a certain amount of CPU time has elapsed on the // watched thread. @@ -214,6 +232,34 @@ void GpuWatchdogThread::DeliberatelyTerminateToRecoverFromHang() { terminated = true; } +void GpuWatchdogThread::AddPowerObserver() { + message_loop()->PostTask( + FROM_HERE, + base::Bind(&GpuWatchdogThread::OnAddPowerObserver, this)); +} + +void GpuWatchdogThread::OnAddPowerObserver() { + base::PowerMonitor* power_monitor = base::PowerMonitor::Get(); + DCHECK(power_monitor); + power_monitor->AddObserver(this); +} + +void GpuWatchdogThread::OnSuspend() { + suspended_ = true; + + // When suspending force an acknowledgement to cancel any pending termination + // tasks. + OnAcknowledge(); +} + +void GpuWatchdogThread::OnResume() { + suspended_ = false; + + // After resuming jump-start the watchdog again. + armed_ = false; + OnCheck(true); +} + #if defined(OS_WIN) base::TimeDelta GpuWatchdogThread::GetWatchedThreadTime() { FILETIME creation_time; diff --git a/content/gpu/gpu_watchdog_thread.h b/content/gpu/gpu_watchdog_thread.h index 1ee079f..8731e41 100644 --- a/content/gpu/gpu_watchdog_thread.h +++ b/content/gpu/gpu_watchdog_thread.h @@ -8,6 +8,7 @@ #include "base/memory/ref_counted.h" #include "base/memory/weak_ptr.h" #include "base/message_loop/message_loop.h" +#include "base/power_monitor/power_observer.h" #include "base/threading/thread.h" #include "base/time/time.h" #include "content/common/gpu/gpu_watchdog.h" @@ -18,6 +19,7 @@ namespace content { // and deliberately crashes if one of them does not respond after a timeout. class GpuWatchdogThread : public base::Thread, public GpuWatchdog, + public base::PowerObserver, public base::RefCountedThreadSafe<GpuWatchdogThread> { public: explicit GpuWatchdogThread(int timeout); @@ -29,6 +31,10 @@ class GpuWatchdogThread : public base::Thread, // Implement GpuWatchdog. virtual void CheckArmed() OVERRIDE; + // Must be called after a PowerMonitor has been created. Can be called from + // any thread. + void AddPowerObserver(); + protected: virtual void Init() OVERRIDE; virtual void CleanUp() OVERRIDE; @@ -58,6 +64,12 @@ class GpuWatchdogThread : public base::Thread, void OnCheck(bool after_suspend); void DeliberatelyTerminateToRecoverFromHang(); + void OnAddPowerObserver(); + + // Implement PowerObserver. + virtual void OnSuspend() OVERRIDE; + virtual void OnResume() OVERRIDE; + #if defined(OS_WIN) base::TimeDelta GetWatchedThreadTime(); #endif @@ -78,6 +90,8 @@ class GpuWatchdogThread : public base::Thread, base::WeakPtrFactory<GpuWatchdogThread> weak_factory_; + bool suspended_; + DISALLOW_COPY_AND_ASSIGN(GpuWatchdogThread); }; |