OLD | NEW |
| (Empty) |
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 | |
3 // found in the LICENSE file. | |
4 | |
5 #include "net/dns/notify_watcher_mac.h" | |
6 | |
7 #include <notify.h> | |
8 | |
9 #include "base/logging.h" | |
10 #include "base/posix/eintr_wrapper.h" | |
11 | |
12 namespace net { | |
13 | |
14 NotifyWatcherMac::NotifyWatcherMac() : notify_fd_(-1), notify_token_(-1) {} | |
15 | |
16 NotifyWatcherMac::~NotifyWatcherMac() { | |
17 Cancel(); | |
18 } | |
19 | |
20 bool NotifyWatcherMac::Watch(const char* key, const CallbackType& callback) { | |
21 DCHECK(key); | |
22 DCHECK(!callback.is_null()); | |
23 Cancel(); | |
24 uint32_t status = notify_register_file_descriptor( | |
25 key, ¬ify_fd_, 0, ¬ify_token_); | |
26 if (status != NOTIFY_STATUS_OK) | |
27 return false; | |
28 DCHECK_GE(notify_fd_, 0); | |
29 if (!base::MessageLoopForIO::current()->WatchFileDescriptor( | |
30 notify_fd_, | |
31 true, | |
32 base::MessageLoopForIO::WATCH_READ, | |
33 &watcher_, | |
34 this)) { | |
35 Cancel(); | |
36 return false; | |
37 } | |
38 callback_ = callback; | |
39 return true; | |
40 } | |
41 | |
42 void NotifyWatcherMac::Cancel() { | |
43 if (notify_fd_ >= 0) { | |
44 notify_cancel(notify_token_); // Also closes |notify_fd_|. | |
45 notify_fd_ = -1; | |
46 callback_.Reset(); | |
47 watcher_.StopWatchingFileDescriptor(); | |
48 } | |
49 } | |
50 | |
51 void NotifyWatcherMac::OnFileCanReadWithoutBlocking(int fd) { | |
52 int token; | |
53 int status = HANDLE_EINTR(read(notify_fd_, &token, sizeof(token))); | |
54 if (status != sizeof(token)) { | |
55 Cancel(); | |
56 callback_.Run(false); | |
57 return; | |
58 } | |
59 // Ignoring |token| value to avoid possible endianness mismatch: | |
60 // http://openradar.appspot.com/8821081 | |
61 callback_.Run(true); | |
62 } | |
63 | |
64 } // namespace net | |
OLD | NEW |