summaryrefslogtreecommitdiffstats
path: root/chrome/chrome_watcher
diff options
context:
space:
mode:
authorsiggi <siggi@chromium.org>2015-02-11 13:02:40 -0800
committerCommit bot <commit-bot@chromium.org>2015-02-11 21:03:23 +0000
commitc855c8079492d78efdabf1e93586acf4dda8726f (patch)
tree83737dc51a829acbcad6bfaeb2df4ab559ba4596 /chrome/chrome_watcher
parent2dbb7e87a8cd907e4d782cff5212dc6f61626e7d (diff)
downloadchromium_src-c855c8079492d78efdabf1e93586acf4dda8726f.zip
chromium_src-c855c8079492d78efdabf1e93586acf4dda8726f.tar.gz
chromium_src-c855c8079492d78efdabf1e93586acf4dda8726f.tar.bz2
Stretch watcher's lifetime if it sees WM_ENDSESSION before process exit.
R=erikwright@chromium.org BUG=412384 Review URL: https://codereview.chromium.org/915123003 Cr-Commit-Position: refs/heads/master@{#315833}
Diffstat (limited to 'chrome/chrome_watcher')
-rw-r--r--chrome/chrome_watcher/chrome_watcher_main.cc33
1 files changed, 20 insertions, 13 deletions
diff --git a/chrome/chrome_watcher/chrome_watcher_main.cc b/chrome/chrome_watcher/chrome_watcher_main.cc
index 4e294dc..c88988f 100644
--- a/chrome/chrome_watcher/chrome_watcher_main.cc
+++ b/chrome/chrome_watcher/chrome_watcher_main.cc
@@ -33,6 +33,9 @@ const GUID kChromeWatcherTraceProviderName = {
0x7fe69228, 0x633e, 0x4f06,
{ 0x80, 0xc1, 0x52, 0x7f, 0xea, 0x23, 0xe3, 0xa7 } };
+// The amount of time we wait around for a WM_ENDSESSION or a process exit.
+const int kDelayTimeSeconds = 30;
+
// Takes care of monitoring a browser. This class watches for a browser's exit
// code, as well as listening for WM_ENDSESSION messages. Events are recorded in
// an exit funnel, for reporting the next time Chrome runs.
@@ -59,9 +62,6 @@ class BrowserMonitor {
// Posted to main thread from Watch when browser exits.
void BrowserExited();
- // True if BrowserExited has run.
- bool browser_exited_;
-
// The funnel used to record events for this browser.
browser_watcher::ExitFunnel exit_funnel_;
@@ -71,6 +71,10 @@ class BrowserMonitor {
// The thread that runs Watch().
base::Thread background_thread_;
+ // Set when the browser has exited, used to stretch the watcher's lifetime
+ // when WM_ENDSESSION occurs before browser exit.
+ base::WaitableEvent browser_exited_;
+
// The run loop for the main thread and its task runner.
base::RunLoop* run_loop_;
scoped_refptr<base::SequencedTaskRunner> main_thread_;
@@ -80,7 +84,7 @@ class BrowserMonitor {
BrowserMonitor::BrowserMonitor(base::RunLoop* run_loop,
const base::char16* registry_path) :
- browser_exited_(false),
+ browser_exited_(true, false), // manual reset, initially non-signalled.
exit_code_watcher_(registry_path),
end_session_watcher_window_(
base::Bind(&BrowserMonitor::OnEndSessionMessage,
@@ -139,9 +143,11 @@ void BrowserMonitor::OnEndSessionMessage(UINT message, LPARAM lparam) {
if (lparam & ~kKnownBits)
exit_funnel_.RecordEvent(L"ES_Other");
- // Belt-and-suspenders; make sure our message loop exits ASAP.
- if (browser_exited_)
- run_loop_->Quit();
+ // If the browser hasn't exited yet, dally for a bit to try and stretch this
+ // process' lifetime to give it some more time to capture the browser exit.
+ browser_exited_.TimedWait(base::TimeDelta::FromSeconds(kDelayTimeSeconds));
+
+ run_loop_->Quit();
}
void BrowserMonitor::Watch(base::win::ScopedHandle on_initialized_event) {
@@ -156,6 +162,9 @@ void BrowserMonitor::Watch(base::win::ScopedHandle on_initialized_event) {
exit_code_watcher_.WaitForExit();
exit_funnel_.RecordEvent(L"BrowserExit");
+ // Note that the browser has exited.
+ browser_exited_.Signal();
+
main_thread_->PostTask(FROM_HERE,
base::Bind(&BrowserMonitor::BrowserExited, base::Unretained(this)));
}
@@ -164,9 +173,6 @@ void BrowserMonitor::BrowserExited() {
// This runs in the main thread.
DCHECK_EQ(main_thread_, base::MessageLoopProxy::current());
- // Note that the browser has exited.
- browser_exited_ = true;
-
// Our background thread has served it's purpose.
background_thread_.Stop();
@@ -178,9 +184,10 @@ void BrowserMonitor::BrowserExited() {
} else {
// The browser exited abnormally, wait around for a little bit to see
// whether this instance will get a logoff message.
- main_thread_->PostDelayedTask(FROM_HERE,
- run_loop_->QuitClosure(),
- base::TimeDelta::FromSeconds(30));
+ main_thread_->PostDelayedTask(
+ FROM_HERE,
+ run_loop_->QuitClosure(),
+ base::TimeDelta::FromSeconds(kDelayTimeSeconds));
}
}