1 // Copyright 2013 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 #ifndef MOJO_SYSTEM_RAW_CHANNEL_H_ 6 #define MOJO_SYSTEM_RAW_CHANNEL_H_ 7 8 #include <vector> 9 10 #include "base/basictypes.h" 11 #include "mojo/system/constants.h" 12 #include "mojo/system/system_impl_export.h" 13 14 namespace base { 15 class MessageLoop; 16 } 17 18 namespace mojo { 19 namespace system { 20 21 class MessageInTransit; 22 23 // This simply wraps an |int| file descriptor on POSIX and a |HANDLE| on 24 // Windows, but we don't want to impose, e.g., the inclusion of windows.h on 25 // everyone. 26 struct PlatformChannelHandle; 27 28 // |RawChannel| is an interface to objects that wrap an OS "pipe". It presents 29 // the following interface to users: 30 // - Receives and dispatches messages on a thread (running a |MessageLoop|; it 31 // must be a |MessageLoopForIO| in the case of the POSIX libevent 32 // implementation). 33 // - Provides a thread-safe way of writing messages (|WriteMessage()|); 34 // writing/queueing messages will not block and is atomic from the point of 35 // view of the caller. If necessary, messages are queued (to be written on 36 // the aforementioned thread). 37 // 38 // OS-specific implementation subclasses are to be instantiated using the 39 // |Create()| static factory method. 40 // 41 // With the exception of |WriteMessage()|, this class is thread-unsafe (and in 42 // general its methods should only be used on the I/O thread). 43 class MOJO_SYSTEM_IMPL_EXPORT RawChannel { 44 public: 45 virtual ~RawChannel() {} 46 47 // The |Delegate| is only accessed on the same thread as the message loop 48 // (passed in on creation). 49 class MOJO_SYSTEM_IMPL_EXPORT Delegate { 50 public: 51 enum FatalError { 52 FATAL_ERROR_UNKNOWN = 0, 53 FATAL_ERROR_FAILED_READ, 54 FATAL_ERROR_FAILED_WRITE 55 }; 56 57 // Called when a message is read. This may call |Shutdown()| on the 58 // |RawChannel|, but must not destroy it. 59 virtual void OnReadMessage(const MessageInTransit& message) = 0; 60 61 // Called when there's a fatal error, which leads to the channel no longer 62 // being viable. 63 virtual void OnFatalError(FatalError fatal_error) = 0; 64 65 protected: 66 virtual ~Delegate() {} 67 }; 68 69 // Static factory method. Takes ownership of |handle| (i.e., will close it). 70 // Does *not* take ownership of |delegate| and |message_loop|, which must 71 // remain alive while this object does. 72 static RawChannel* Create(const PlatformChannelHandle& handle, 73 Delegate* delegate, 74 base::MessageLoop* message_loop); 75 76 // This must be called (on the I/O thread) before this object is used. Returns 77 // true on success. On failure, |Shutdown()| should *not* be called. 78 virtual bool Init() = 0; 79 80 // This must be called (on the I/O thread) before this object is destroyed. 81 virtual void Shutdown() = 0; 82 83 // This is thread-safe. It takes ownership of |message| (always, even on 84 // failure). Returns true on success. 85 virtual bool WriteMessage(MessageInTransit* message) = 0; 86 87 protected: 88 RawChannel(Delegate* delegate, base::MessageLoop* message_loop) 89 : delegate_(delegate), message_loop_(message_loop) {} 90 91 Delegate* delegate() { return delegate_; } 92 base::MessageLoop* message_loop() { return message_loop_; } 93 94 private: 95 Delegate* const delegate_; 96 base::MessageLoop* const message_loop_; 97 98 DISALLOW_COPY_AND_ASSIGN(RawChannel); 99 }; 100 101 } // namespace system 102 } // namespace mojo 103 104 #endif // MOJO_SYSTEM_RAW_CHANNEL_H_ 105