OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "base/files/file_path_watcher.h" | 5 #include "base/files/file_path_watcher.h" |
6 | 6 |
7 #include <set> | 7 #include <set> |
8 | 8 |
9 #if defined(OS_WIN) | 9 #if defined(OS_WIN) |
10 #include <windows.h> | 10 #include <windows.h> |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
65 } | 65 } |
66 | 66 |
67 private: | 67 private: |
68 void RecordChange(TestDelegate* delegate) { | 68 void RecordChange(TestDelegate* delegate) { |
69 ASSERT_TRUE(loop_->BelongsToCurrentThread()); | 69 ASSERT_TRUE(loop_->BelongsToCurrentThread()); |
70 ASSERT_TRUE(delegates_.count(delegate)); | 70 ASSERT_TRUE(delegates_.count(delegate)); |
71 signaled_.insert(delegate); | 71 signaled_.insert(delegate); |
72 | 72 |
73 // Check whether all delegates have been signaled. | 73 // Check whether all delegates have been signaled. |
74 if (signaled_ == delegates_) | 74 if (signaled_ == delegates_) |
75 loop_->PostTask(FROM_HERE, new MessageLoop::QuitTask()); | 75 loop_->PostTask(FROM_HERE, MessageLoop::QuitClosure()); |
76 } | 76 } |
77 | 77 |
78 // Set of registered delegates. | 78 // Set of registered delegates. |
79 std::set<TestDelegate*> delegates_; | 79 std::set<TestDelegate*> delegates_; |
80 | 80 |
81 // Set of signaled delegates. | 81 // Set of signaled delegates. |
82 std::set<TestDelegate*> signaled_; | 82 std::set<TestDelegate*> signaled_; |
83 | 83 |
84 // The loop we should break after all delegates signaled. | 84 // The loop we should break after all delegates signaled. |
85 scoped_refptr<base::MessageLoopProxy> loop_; | 85 scoped_refptr<base::MessageLoopProxy> loop_; |
(...skipping 20 matching lines...) Expand all Loading... |
106 virtual void OnFilePathError(const FilePath& path) { | 106 virtual void OnFilePathError(const FilePath& path) { |
107 ADD_FAILURE() << "Error " << path.value(); | 107 ADD_FAILURE() << "Error " << path.value(); |
108 } | 108 } |
109 | 109 |
110 private: | 110 private: |
111 scoped_refptr<NotificationCollector> collector_; | 111 scoped_refptr<NotificationCollector> collector_; |
112 | 112 |
113 DISALLOW_COPY_AND_ASSIGN(TestDelegate); | 113 DISALLOW_COPY_AND_ASSIGN(TestDelegate); |
114 }; | 114 }; |
115 | 115 |
116 // A helper class for setting up watches on the file thread. | 116 void SetupWatchCallback(const FilePath& target, |
117 class SetupWatchTask : public Task { | 117 FilePathWatcher* watcher, |
118 public: | 118 FilePathWatcher::Delegate* delegate, |
119 SetupWatchTask(const FilePath& target, | 119 bool* result, |
120 FilePathWatcher* watcher, | 120 base::WaitableEvent* completion) { |
121 FilePathWatcher::Delegate* delegate, | 121 *result = watcher->Watch(target, delegate); |
122 bool* result, | 122 completion->Signal(); |
123 base::WaitableEvent* completion) | 123 } |
124 : target_(target), | |
125 watcher_(watcher), | |
126 delegate_(delegate), | |
127 result_(result), | |
128 completion_(completion) {} | |
129 | |
130 void Run() { | |
131 *result_ = watcher_->Watch(target_, delegate_); | |
132 completion_->Signal(); | |
133 } | |
134 | |
135 private: | |
136 const FilePath target_; | |
137 FilePathWatcher* watcher_; | |
138 FilePathWatcher::Delegate* delegate_; | |
139 bool* result_; | |
140 base::WaitableEvent* completion_; | |
141 | |
142 DISALLOW_COPY_AND_ASSIGN(SetupWatchTask); | |
143 }; | |
144 | 124 |
145 class FilePathWatcherTest : public testing::Test { | 125 class FilePathWatcherTest : public testing::Test { |
146 public: | 126 public: |
147 FilePathWatcherTest() | 127 FilePathWatcherTest() |
148 : file_thread_("FilePathWatcherTest") {} | 128 : file_thread_("FilePathWatcherTest") {} |
149 | 129 |
150 virtual ~FilePathWatcherTest() {} | 130 virtual ~FilePathWatcherTest() {} |
151 | 131 |
152 protected: | 132 protected: |
153 virtual void SetUp() { | 133 virtual void SetUp() { |
(...skipping 21 matching lines...) Expand all Loading... |
175 int write_size = file_util::WriteFile(file, content.c_str(), | 155 int write_size = file_util::WriteFile(file, content.c_str(), |
176 content.length()); | 156 content.length()); |
177 return write_size == static_cast<int>(content.length()); | 157 return write_size == static_cast<int>(content.length()); |
178 } | 158 } |
179 | 159 |
180 bool SetupWatch(const FilePath& target, | 160 bool SetupWatch(const FilePath& target, |
181 FilePathWatcher* watcher, | 161 FilePathWatcher* watcher, |
182 FilePathWatcher::Delegate* delegate) WARN_UNUSED_RESULT { | 162 FilePathWatcher::Delegate* delegate) WARN_UNUSED_RESULT { |
183 base::WaitableEvent completion(false, false); | 163 base::WaitableEvent completion(false, false); |
184 bool result; | 164 bool result; |
185 file_thread_.message_loop_proxy()->PostTask(FROM_HERE, | 165 file_thread_.message_loop_proxy()->PostTask( |
186 new SetupWatchTask(target, | 166 FROM_HERE, |
187 watcher, | 167 base::Bind(SetupWatchCallback, target, watcher, |
188 delegate, | 168 make_scoped_refptr(delegate), &result, &completion)); |
189 &result, | |
190 &completion)); | |
191 completion.Wait(); | 169 completion.Wait(); |
192 return result; | 170 return result; |
193 } | 171 } |
194 | 172 |
195 bool WaitForEvents() WARN_UNUSED_RESULT { | 173 bool WaitForEvents() WARN_UNUSED_RESULT { |
196 collector_->Reset(); | 174 collector_->Reset(); |
197 loop_.Run(); | 175 loop_.Run(); |
198 return collector_->Success(); | 176 return collector_->Success(); |
199 } | 177 } |
200 | 178 |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
259 // Deletes the FilePathWatcher when it's notified. | 237 // Deletes the FilePathWatcher when it's notified. |
260 class Deleter : public FilePathWatcher::Delegate { | 238 class Deleter : public FilePathWatcher::Delegate { |
261 public: | 239 public: |
262 Deleter(FilePathWatcher* watcher, MessageLoop* loop) | 240 Deleter(FilePathWatcher* watcher, MessageLoop* loop) |
263 : watcher_(watcher), | 241 : watcher_(watcher), |
264 loop_(loop) { | 242 loop_(loop) { |
265 } | 243 } |
266 | 244 |
267 virtual void OnFilePathChanged(const FilePath& path) { | 245 virtual void OnFilePathChanged(const FilePath& path) { |
268 watcher_.reset(); | 246 watcher_.reset(); |
269 loop_->PostTask(FROM_HERE, new MessageLoop::QuitTask()); | 247 loop_->PostTask(FROM_HERE, MessageLoop::QuitClosure()); |
270 } | 248 } |
271 | 249 |
272 scoped_ptr<FilePathWatcher> watcher_; | 250 scoped_ptr<FilePathWatcher> watcher_; |
273 MessageLoop* loop_; | 251 MessageLoop* loop_; |
274 }; | 252 }; |
275 | 253 |
276 // Verify that deleting a watcher during the callback doesn't crash. | 254 // Verify that deleting a watcher during the callback doesn't crash. |
277 TEST_F(FilePathWatcherTest, DeleteDuringNotify) { | 255 TEST_F(FilePathWatcherTest, DeleteDuringNotify) { |
278 FilePathWatcher* watcher = new FilePathWatcher; | 256 FilePathWatcher* watcher = new FilePathWatcher; |
279 // Takes ownership of watcher. | 257 // Takes ownership of watcher. |
(...skipping 491 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
771 ASSERT_TRUE(WriteFile(test_file, "content")); | 749 ASSERT_TRUE(WriteFile(test_file, "content")); |
772 | 750 |
773 FilePathWatcher watcher; | 751 FilePathWatcher watcher; |
774 scoped_refptr<TestDelegate> delegate(new TestDelegate(collector())); | 752 scoped_refptr<TestDelegate> delegate(new TestDelegate(collector())); |
775 ASSERT_TRUE(SetupWatch(test_file, &watcher, delegate.get())); | 753 ASSERT_TRUE(SetupWatch(test_file, &watcher, delegate.get())); |
776 | 754 |
777 // We should not get notified in this case as it hasn't affected our ability | 755 // We should not get notified in this case as it hasn't affected our ability |
778 // to access the file. | 756 // to access the file. |
779 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Read, false)); | 757 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Read, false)); |
780 loop_.PostDelayedTask(FROM_HERE, | 758 loop_.PostDelayedTask(FROM_HERE, |
781 new MessageLoop::QuitTask, | 759 MessageLoop::QuitClosure(), |
782 TestTimeouts::tiny_timeout_ms()); | 760 TestTimeouts::tiny_timeout_ms()); |
783 ASSERT_FALSE(WaitForEvents()); | 761 ASSERT_FALSE(WaitForEvents()); |
784 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Read, true)); | 762 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Read, true)); |
785 | 763 |
786 // We should get notified in this case because filepathwatcher can no | 764 // We should get notified in this case because filepathwatcher can no |
787 // longer access the file | 765 // longer access the file |
788 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Execute, false)); | 766 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Execute, false)); |
789 ASSERT_TRUE(WaitForEvents()); | 767 ASSERT_TRUE(WaitForEvents()); |
790 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Execute, true)); | 768 ASSERT_TRUE(ChangeFilePermissions(test_dir1, Execute, true)); |
791 } | 769 } |
792 | 770 |
793 #endif // OS_MACOSX | 771 #endif // OS_MACOSX |
794 } // namespace | 772 } // namespace |
795 | 773 |
796 } // namespace files | 774 } // namespace files |
797 } // namespace base | 775 } // namespace base |
OLD | NEW |