OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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_kqueue.h" | 5 #include "base/files/file_path_watcher_kqueue.h" |
6 | 6 |
7 #include <fcntl.h> | 7 #include <fcntl.h> |
8 #include <stddef.h> | 8 #include <stddef.h> |
9 #include <sys/param.h> | 9 #include <sys/param.h> |
10 | 10 |
11 #include "base/bind.h" | 11 #include "base/bind.h" |
12 #include "base/files/file_util.h" | 12 #include "base/files/file_util.h" |
13 #include "base/logging.h" | 13 #include "base/logging.h" |
14 #include "base/strings/stringprintf.h" | 14 #include "base/strings/stringprintf.h" |
15 #include "base/threading/sequenced_task_runner_handle.h" | 15 #include "base/threading/sequenced_task_runner_handle.h" |
16 | 16 |
17 // On some platforms these are not defined. | 17 // On some platforms these are not defined. |
18 #if !defined(EV_RECEIPT) | 18 #if !defined(EV_RECEIPT) |
19 #define EV_RECEIPT 0 | 19 #define EV_RECEIPT 0 |
20 #endif | 20 #endif |
21 #if !defined(O_EVTONLY) | 21 #if !defined(O_EVTONLY) |
22 #define O_EVTONLY O_RDONLY | 22 #define O_EVTONLY O_RDONLY |
23 #endif | 23 #endif |
24 | 24 |
25 namespace base { | 25 namespace base { |
26 | 26 |
27 FilePathWatcherKQueue::FilePathWatcherKQueue() : kqueue_(-1) {} | 27 FilePathWatcherKQueue::FilePathWatcherKQueue() : kqueue_(-1) {} |
28 | 28 |
29 FilePathWatcherKQueue::~FilePathWatcherKQueue() {} | 29 FilePathWatcherKQueue::~FilePathWatcherKQueue() { |
30 DCHECK(!task_runner() || task_runner()->RunsTasksOnCurrentThread()); | |
31 } | |
30 | 32 |
31 void FilePathWatcherKQueue::ReleaseEvent(struct kevent& event) { | 33 void FilePathWatcherKQueue::ReleaseEvent(struct kevent& event) { |
32 CloseFileDescriptor(&event.ident); | 34 CloseFileDescriptor(&event.ident); |
33 EventData* entry = EventDataForKevent(event); | 35 EventData* entry = EventDataForKevent(event); |
34 delete entry; | 36 delete entry; |
35 event.udata = NULL; | 37 event.udata = NULL; |
36 } | 38 } |
37 | 39 |
38 int FilePathWatcherKQueue::EventsForPath(FilePath path, EventVector* events) { | 40 int FilePathWatcherKQueue::EventsForPath(FilePath path, EventVector* events) { |
39 // Make sure that we are working with a clean slate. | 41 // Make sure that we are working with a clean slate. |
(...skipping 218 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
258 &responses[0], last_entry, NULL)); | 260 &responses[0], last_entry, NULL)); |
259 if (!AreKeventValuesValid(&responses[0], count)) { | 261 if (!AreKeventValuesValid(&responses[0], count)) { |
260 // Calling Cancel() here to close any file descriptors that were opened. | 262 // Calling Cancel() here to close any file descriptors that were opened. |
261 // This would happen in the destructor anyways, but FilePathWatchers tend to | 263 // This would happen in the destructor anyways, but FilePathWatchers tend to |
262 // be long lived, and if an error has occurred, there is no reason to waste | 264 // be long lived, and if an error has occurred, there is no reason to waste |
263 // the file descriptors. | 265 // the file descriptors. |
264 Cancel(); | 266 Cancel(); |
265 return false; | 267 return false; |
266 } | 268 } |
267 | 269 |
268 // This creates an ownership cycle (|this| owns |kqueue_watch_controller_| | |
269 // which owns a callback which owns |this|). The cycle is broken when | |
270 // |kqueue_watch_controller_| is reset in Cancel(). | |
271 kqueue_watch_controller_ = FileDescriptorWatcher::WatchReadable( | 270 kqueue_watch_controller_ = FileDescriptorWatcher::WatchReadable( |
272 kqueue_, Bind(&FilePathWatcherKQueue::OnKQueueReadable, this)); | 271 kqueue_, |
272 Bind(&FilePathWatcherKQueue::OnKQueueReadable, Unretained(this))); | |
gab
2017/01/05 21:22:53
Can you add a comment explaining why it's okay to
fdoray
2017/01/05 23:04:11
Done.
| |
273 | |
273 return true; | 274 return true; |
274 } | 275 } |
275 | 276 |
276 void FilePathWatcherKQueue::Cancel() { | 277 void FilePathWatcherKQueue::Cancel() { |
277 if (!task_runner()) { | 278 if (!task_runner()) { |
278 set_cancelled(); | 279 set_cancelled(); |
279 return; | 280 return; |
280 } | 281 } |
281 | 282 |
282 DCHECK(task_runner()->RunsTasksOnCurrentThread()); | 283 DCHECK(task_runner()->RunsTasksOnCurrentThread()); |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
359 Cancel(); | 360 Cancel(); |
360 } | 361 } |
361 } | 362 } |
362 | 363 |
363 if (send_notification) { | 364 if (send_notification) { |
364 callback_.Run(target_, false); | 365 callback_.Run(target_, false); |
365 } | 366 } |
366 } | 367 } |
367 | 368 |
368 } // namespace base | 369 } // namespace base |
OLD | NEW |