1 // Copyright 2018 The Chromium Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef BASE_MESSAGE_LOOP_WATCHABLE_IO_MESSAGE_PUMP_POSIX_H_ 6 #define BASE_MESSAGE_LOOP_WATCHABLE_IO_MESSAGE_PUMP_POSIX_H_ 7 8 #include "base/location.h" 9 10 namespace base { 11 12 class WatchableIOMessagePumpPosix { 13 public: 14 // Used with WatchFileDescriptor to asynchronously monitor the I/O readiness 15 // of a file descriptor. 16 class FdWatcher { 17 public: 18 virtual void OnFileCanReadWithoutBlocking(int fd) = 0; 19 virtual void OnFileCanWriteWithoutBlocking(int fd) = 0; 20 21 protected: 22 virtual ~FdWatcher() = default; 23 }; 24 25 class FdWatchControllerInterface { 26 public: 27 explicit FdWatchControllerInterface(const Location& from_here); 28 29 FdWatchControllerInterface(const FdWatchControllerInterface&) = delete; 30 FdWatchControllerInterface& operator=(const FdWatchControllerInterface&) = 31 delete; 32 33 // Subclasses must call StopWatchingFileDescriptor() in their destructor 34 // (this parent class cannot generically do it for them as it must usually 35 // be invoked before they destroy their state which happens before the 36 // parent destructor is invoked). 37 virtual ~FdWatchControllerInterface(); 38 39 // NOTE: This method isn't called StopWatching() to avoid confusion with the 40 // win32 ObjectWatcher class. While this doesn't really need to be virtual 41 // as there's only one impl per platform and users don't use pointers to the 42 // base class. Having this interface forces implementers to share similar 43 // implementations (a problem in the past). 44 45 // Stop watching the FD, always safe to call. No-op if there's nothing to 46 // do. 47 virtual bool StopWatchingFileDescriptor() = 0; 48 created_from_location()49 const Location& created_from_location() const { 50 return created_from_location_; 51 } 52 53 private: 54 const Location created_from_location_; 55 }; 56 57 enum Mode { 58 WATCH_READ = 1 << 0, 59 WATCH_WRITE = 1 << 1, 60 WATCH_READ_WRITE = WATCH_READ | WATCH_WRITE 61 }; 62 63 // Every subclass of WatchableIOMessagePumpPosix must provide a 64 // WatchFileDescriptor() which has the following signature where 65 // |FdWatchController| must be the complete type based on 66 // FdWatchControllerInterface. 67 68 // Registers |delegate| with the current thread's message loop so that its 69 // methods are invoked when file descriptor |fd| becomes ready for reading or 70 // writing (or both) without blocking. |mode| selects ready for reading, for 71 // writing, or both. See "enum Mode" above. |controller| manages the 72 // lifetime of registrations. ("Registrations" are also ambiguously called 73 // "events" in many places, for instance in libevent.) It is an error to use 74 // the same |controller| for different file descriptors; however, the same 75 // controller can be reused to add registrations with a different |mode|. If 76 // |controller| is already attached to one or more registrations, the new 77 // registration is added onto those. If an error occurs while calling this 78 // method, any registration previously attached to |controller| is removed. 79 // Returns true on success. Must be called on the same thread the MessagePump 80 // is running on. 81 // bool WatchFileDescriptor(int fd, 82 // bool persistent, 83 // int mode, 84 // FdWatchController* controller, 85 // FdWatcher* delegate) = 0; 86 }; 87 88 } // namespace base 89 90 #endif // BASE_MESSAGE_LOOP_WATCHABLE_IO_MESSAGE_PUMP_POSIX_H_ 91