diff options
author | apatrick@chromium.org <apatrick@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-02-11 23:07:17 +0000 |
---|---|---|
committer | apatrick@chromium.org <apatrick@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-02-11 23:07:17 +0000 |
commit | 995a7f171c7de6077d43c2b797746f04602311be (patch) | |
tree | cf145e59dd8413b08f9503f9ae08466f851d91a9 /chrome/gpu | |
parent | 387b51550046f454ede1939e3de1288bdcd58d9e (diff) | |
download | chromium_src-995a7f171c7de6077d43c2b797746f04602311be.zip chromium_src-995a7f171c7de6077d43c2b797746f04602311be.tar.gz chromium_src-995a7f171c7de6077d43c2b797746f04602311be.tar.bz2 |
Disarm and reset GPU watchdog if it sleeps for an extended period of time.
TEST=simulate sleeping watchdog thread, try
BUG=72697
Review URL: http://codereview.chromium.org/6503007
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@74689 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/gpu')
-rw-r--r-- | chrome/gpu/gpu_main.cc | 6 | ||||
-rw-r--r-- | chrome/gpu/gpu_watchdog_thread.cc | 22 | ||||
-rw-r--r-- | chrome/gpu/gpu_watchdog_thread.h | 5 |
3 files changed, 25 insertions, 8 deletions
diff --git a/chrome/gpu/gpu_main.cc b/chrome/gpu/gpu_main.cc index b06f76e..c59bdde 100644 --- a/chrome/gpu/gpu_main.cc +++ b/chrome/gpu/gpu_main.cc @@ -82,9 +82,9 @@ int GpuMain(const MainFunctionParams& parameters) { // this reason we defer all work related to the GPU until receiving // the GpuMsg_Initialize message from the browser. GpuProcess gpu_process; - GpuThread* gpu_thread = new GpuThread; - gpu_thread->Init(start_time); - + GpuThread* gpu_thread = new GpuThread; + gpu_thread->Init(start_time); + gpu_process.set_main_thread(gpu_thread); main_message_loop.Run(); diff --git a/chrome/gpu/gpu_watchdog_thread.cc b/chrome/gpu/gpu_watchdog_thread.cc index 889e017..6d16b34 100644 --- a/chrome/gpu/gpu_watchdog_thread.cc +++ b/chrome/gpu/gpu_watchdog_thread.cc @@ -25,7 +25,7 @@ GpuWatchdogThread::GpuWatchdogThread(int timeout) armed_(false), #if defined(OS_WIN) watched_thread_handle_(0), - arm_time_(0), + arm_cpu_time_(0), #endif ALLOW_THIS_IN_INITIALIZER_LIST(task_observer_(this)) { DCHECK(timeout >= 0); @@ -172,9 +172,11 @@ void GpuWatchdogThread::OnCheck() { armed_ = true; #if defined(OS_WIN) - arm_time_ = GetWatchedThreadTime(); + arm_cpu_time_ = GetWatchedThreadTime(); #endif + arm_absolute_time_ = base::Time::Now(); + // Post a task to the monitored thread that does nothing but wake up the // TaskObserver. Any other tasks that are pending on the watched thread will // also wake up the observer. This simply ensures there is at least one. @@ -193,8 +195,9 @@ void GpuWatchdogThread::OnCheck() { // Use the --disable-gpu-watchdog command line switch to disable this. void GpuWatchdogThread::OnExit() { #if defined(OS_WIN) - // Defer termination until a certain amount of user time has elapsed. - int64 time_since_arm = GetWatchedThreadTime() - arm_time_; + // Defer termination until a certain amount of CPU time has elapsed on the + // watched thread. + int64 time_since_arm = GetWatchedThreadTime() - arm_cpu_time_; if (time_since_arm < timeout_) { message_loop()->PostDelayedTask( FROM_HERE, @@ -204,6 +207,17 @@ void GpuWatchdogThread::OnExit() { } #endif + // If the watchdog woke up significantly behind schedule, disarm and reset + // the watchdog check. This is to prevent the watchdog thread from terminating + // when a machine wakes up from sleep or hibernation, which would otherwise + // appear to be a hang. + if ((base::Time::Now() - arm_absolute_time_).InMilliseconds() > + timeout_ * 2) { + armed_ = false; + OnCheck(); + return; + } + // Make sure the timeout period is on the stack before crashing. volatile int timeout = timeout_; diff --git a/chrome/gpu/gpu_watchdog_thread.h b/chrome/gpu/gpu_watchdog_thread.h index ed5f17a..925682b 100644 --- a/chrome/gpu/gpu_watchdog_thread.h +++ b/chrome/gpu/gpu_watchdog_thread.h @@ -10,6 +10,7 @@ #include "base/scoped_ptr.h" #include "base/task.h" #include "base/threading/thread.h" +#include "base/time.h" // A thread that intermitently sends tasks to a group of watched message loops // and deliberately crashes if one of them does not respond after a timeout. @@ -59,9 +60,11 @@ class GpuWatchdogThread : public base::Thread, #if defined(OS_WIN) void* watched_thread_handle_; - int64 arm_time_; + int64 arm_cpu_time_; #endif + base::Time arm_absolute_time_; + typedef ScopedRunnableMethodFactory<GpuWatchdogThread> MethodFactory; scoped_ptr<MethodFactory> method_factory_; |