Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1682)

Unified Diff: content/common/file_path_watcher/file_path_watcher_win.cc

Issue 6825063: Patch for bug 74983 (among others) to be applied to M11 696 branch. (Closed) Base URL: svn://svn.chromium.org/chrome/branches/696/src
Patch Set: intentionally disabled mac tests. tested by hand. Created 9 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « content/common/file_path_watcher/file_path_watcher_stub.cc ('k') | content/content_common.gypi » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: content/common/file_path_watcher/file_path_watcher_win.cc
diff --git a/chrome/browser/file_path_watcher/file_path_watcher_win.cc b/content/common/file_path_watcher/file_path_watcher_win.cc
similarity index 82%
rename from chrome/browser/file_path_watcher/file_path_watcher_win.cc
rename to content/common/file_path_watcher/file_path_watcher_win.cc
index c2f49b937ca55a352853e9b79e44a2ffcad28e2e..21d94c98c52f04555392db8cb04b02d5316867c3 100644
--- a/chrome/browser/file_path_watcher/file_path_watcher_win.cc
+++ b/content/common/file_path_watcher/file_path_watcher_win.cc
@@ -1,12 +1,13 @@
-// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include "chrome/browser/file_path_watcher/file_path_watcher.h"
+#include "content/common/file_path_watcher/file_path_watcher.h"
#include "base/file_path.h"
#include "base/file_util.h"
#include "base/logging.h"
+#include "base/message_loop_proxy.h"
#include "base/ref_counted.h"
#include "base/time.h"
#include "base/win/object_watcher.h"
@@ -14,18 +15,26 @@
namespace {
class FilePathWatcherImpl : public FilePathWatcher::PlatformDelegate,
- public base::win::ObjectWatcher::Delegate {
+ public base::win::ObjectWatcher::Delegate,
+ public MessageLoop::DestructionObserver {
public:
FilePathWatcherImpl() : delegate_(NULL), handle_(INVALID_HANDLE_VALUE) {}
- virtual bool Watch(const FilePath& path, FilePathWatcher::Delegate* delegate);
- virtual void Cancel();
+ // FilePathWatcher::PlatformDelegate overrides.
+ virtual bool Watch(const FilePath& path,
+ FilePathWatcher::Delegate* delegate) OVERRIDE;
+ virtual void Cancel() OVERRIDE;
+
+ // Deletion of the FilePathWatcher will call Cancel() to dispose of this
+ // object in the right thread. This also observes destruction of the required
+ // cleanup thread, in case it quits before Cancel() is called.
+ virtual void WillDestroyCurrentMessageLoop() OVERRIDE;
// Callback from MessageLoopForIO.
virtual void OnObjectSignaled(HANDLE object);
private:
- virtual ~FilePathWatcherImpl();
+ virtual ~FilePathWatcherImpl() {}
// Setup a watch handle for directory |dir|. Returns true if no fatal error
// occurs. |handle| will receive the handle value if |dir| is watchable,
@@ -39,6 +48,9 @@ class FilePathWatcherImpl : public FilePathWatcher::PlatformDelegate,
// Destroy the watch handle.
void DestroyWatch();
+ // Cleans up and stops observing the |message_loop_| thread.
+ void CancelOnMessageLoopThread() OVERRIDE;
+
// Delegate to notify upon changes.
scoped_refptr<FilePathWatcher::Delegate> delegate_;
@@ -65,8 +77,11 @@ class FilePathWatcherImpl : public FilePathWatcher::PlatformDelegate,
bool FilePathWatcherImpl::Watch(const FilePath& path,
FilePathWatcher::Delegate* delegate) {
DCHECK(target_.value().empty()); // Can only watch one path.
+
+ set_message_loop(base::MessageLoopProxy::CreateForCurrentThread());
delegate_ = delegate;
target_ = path;
+ MessageLoop::current()->AddDestructionObserver(this);
if (!UpdateWatch())
return false;
@@ -77,15 +92,35 @@ bool FilePathWatcherImpl::Watch(const FilePath& path,
}
void FilePathWatcherImpl::Cancel() {
- // Switch to the file thread if necessary so we can stop |watcher_|.
- if (!BrowserThread::CurrentlyOn(BrowserThread::FILE)) {
- BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
- NewRunnableMethod(this, &FilePathWatcherImpl::Cancel));
+ if (!delegate_) {
+ // Watch was never called, or the |message_loop_| has already quit.
+ set_cancelled();
return;
}
+ // Switch to the file thread if necessary so we can stop |watcher_|.
+ if (!message_loop()->BelongsToCurrentThread()) {
+ message_loop()->PostTask(FROM_HERE,
+ new FilePathWatcher::CancelTask(this));
+ } else {
+ CancelOnMessageLoopThread();
+ }
+}
+
+void FilePathWatcherImpl::CancelOnMessageLoopThread() {
+ set_cancelled();
+
if (handle_ != INVALID_HANDLE_VALUE)
DestroyWatch();
+
+ if (delegate_) {
+ MessageLoop::current()->RemoveDestructionObserver(this);
+ delegate_ = NULL;
+ }
+}
+
+void FilePathWatcherImpl::WillDestroyCurrentMessageLoop() {
+ CancelOnMessageLoopThread();
}
void FilePathWatcherImpl::OnObjectSignaled(HANDLE object) {
@@ -94,7 +129,7 @@ void FilePathWatcherImpl::OnObjectSignaled(HANDLE object) {
scoped_refptr<FilePathWatcherImpl> keep_alive(this);
if (!UpdateWatch()) {
- delegate_->OnError();
+ delegate_->OnFilePathError(target_);
return;
}
@@ -137,11 +172,6 @@ void FilePathWatcherImpl::OnObjectSignaled(HANDLE object) {
watcher_.StartWatching(handle_, this);
}
-FilePathWatcherImpl::~FilePathWatcherImpl() {
- if (handle_ != INVALID_HANDLE_VALUE)
- DestroyWatch();
-}
-
// static
bool FilePathWatcherImpl::SetupWatchHandle(const FilePath& dir,
HANDLE* handle) {
« no previous file with comments | « content/common/file_path_watcher/file_path_watcher_stub.cc ('k') | content/content_common.gypi » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698