Home | History | Annotate | Download | only in mojo
      1 // Copyright 2014 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 IPC_IPC_CHANNEL_MOJO_H_
      6 #define IPC_IPC_CHANNEL_MOJO_H_
      7 
      8 #include <vector>
      9 
     10 #include "base/memory/scoped_ptr.h"
     11 #include "base/memory/scoped_vector.h"
     12 #include "base/memory/weak_ptr.h"
     13 #include "ipc/ipc_channel.h"
     14 #include "ipc/ipc_channel_factory.h"
     15 #include "ipc/ipc_export.h"
     16 #include "ipc/mojo/ipc_message_pipe_reader.h"
     17 #include "ipc/mojo/ipc_mojo_bootstrap.h"
     18 #include "mojo/public/cpp/system/core.h"
     19 
     20 namespace mojo {
     21 namespace embedder {
     22 struct ChannelInfo;
     23 }
     24 }
     25 
     26 namespace IPC {
     27 
     28 namespace internal {
     29 class ControlReader;
     30 class ServerControlReader;
     31 class ClientControlReader;
     32 class MessageReader;
     33 }
     34 
     35 // Mojo-based IPC::Channel implementation over a platform handle.
     36 //
     37 // ChannelMojo builds Mojo MessagePipe using underlying pipe given by
     38 // "bootstrap" IPC::Channel which creates and owns platform pipe like
     39 // named socket. The bootstrap Channel is used only for establishing
     40 // the underlying connection. ChannelMojo takes its handle over once
     41 // the it is made and puts MessagePipe on it.
     42 //
     43 // ChannelMojo has a couple of MessagePipes:
     44 //
     45 // * The first MessagePipe, which is built on top of bootstrap handle,
     46 //   is the "control" pipe. It is used to communicate out-of-band
     47 //   control messages that aren't visible from IPC::Listener.
     48 //
     49 // * The second MessagePipe, which is created by the server channel
     50 //   and sent to client Channel over the control pipe, is used
     51 //   to send IPC::Messages as an IPC::Sender.
     52 //
     53 // TODO(morrita): Extract handle creation part of IPC::Channel into
     54 //                separate class to clarify what ChannelMojo relies
     55 //                on.
     56 // TODO(morrita): Add APIs to create extra MessagePipes to let
     57 //                Mojo-based objects talk over this Channel.
     58 //
     59 class IPC_MOJO_EXPORT ChannelMojo : public Channel,
     60                                     public MojoBootstrap::Delegate {
     61  public:
     62   class Delegate {
     63    public:
     64     virtual ~Delegate() {}
     65     virtual base::WeakPtr<Delegate> ToWeakPtr() = 0;
     66     virtual scoped_refptr<base::TaskRunner> GetIOTaskRunner() = 0;
     67     virtual void OnChannelCreated(base::WeakPtr<ChannelMojo> channel) = 0;
     68   };
     69 
     70   // Create ChannelMojo. A bootstrap channel is created as well.
     71   // |host| must not be null for server channels.
     72   static scoped_ptr<ChannelMojo> Create(Delegate* delegate,
     73                                         const ChannelHandle& channel_handle,
     74                                         Mode mode,
     75                                         Listener* listener);
     76 
     77   // Create a factory object for ChannelMojo.
     78   // The factory is used to create Mojo-based ChannelProxy family.
     79   // |host| must not be null.
     80   static scoped_ptr<ChannelFactory> CreateServerFactory(
     81       Delegate* delegate,
     82       const ChannelHandle& channel_handle);
     83 
     84   static scoped_ptr<ChannelFactory> CreateClientFactory(
     85       const ChannelHandle& channel_handle);
     86 
     87   virtual ~ChannelMojo();
     88 
     89   // ChannelMojoHost tells the client handle using this API.
     90   void OnClientLaunched(base::ProcessHandle handle);
     91 
     92   // Channel implementation
     93   virtual bool Connect() OVERRIDE;
     94   virtual void Close() OVERRIDE;
     95   virtual bool Send(Message* message) OVERRIDE;
     96   virtual base::ProcessId GetPeerPID() const OVERRIDE;
     97   virtual base::ProcessId GetSelfPID() const OVERRIDE;
     98 
     99 #if defined(OS_POSIX) && !defined(OS_NACL)
    100   virtual int GetClientFileDescriptor() const OVERRIDE;
    101   virtual int TakeClientFileDescriptor() OVERRIDE;
    102 
    103   // These access protected API of IPC::Message, which has ChannelMojo
    104   // as a friend class.
    105   static MojoResult WriteToFileDescriptorSet(
    106       const std::vector<MojoHandle>& handle_buffer,
    107       Message* message);
    108   static MojoResult ReadFromFileDescriptorSet(Message* message,
    109                                               std::vector<MojoHandle>* handles);
    110 
    111 #endif  // defined(OS_POSIX) && !defined(OS_NACL)
    112 
    113   // MojoBootstrapDelegate implementation
    114   virtual void OnPipeAvailable(
    115       mojo::embedder::ScopedPlatformHandle handle) OVERRIDE;
    116   virtual void OnBootstrapError() OVERRIDE;
    117 
    118   // Called from MessagePipeReader implementations
    119   void OnMessageReceived(Message& message);
    120   void OnConnected(mojo::ScopedMessagePipeHandle pipe);
    121   void OnPipeClosed(internal::MessagePipeReader* reader);
    122   void OnPipeError(internal::MessagePipeReader* reader);
    123   void set_peer_pid(base::ProcessId pid) { peer_pid_ = pid; }
    124 
    125  protected:
    126   ChannelMojo(Delegate* delegate,
    127               const ChannelHandle& channel_handle,
    128               Mode mode,
    129               Listener* listener);
    130 
    131  private:
    132   struct ChannelInfoDeleter {
    133     void operator()(mojo::embedder::ChannelInfo* ptr) const;
    134   };
    135 
    136   // ChannelMojo needs to kill its MessagePipeReader in delayed manner
    137   // because the channel wants to kill these readers during the
    138   // notifications invoked by them.
    139   typedef internal::MessagePipeReader::DelayedDeleter ReaderDeleter;
    140 
    141   void InitDelegate(ChannelMojo::Delegate* delegate);
    142   void InitControlReader(mojo::embedder::ScopedPlatformHandle handle);
    143 
    144   scoped_ptr<MojoBootstrap> bootstrap_;
    145   base::WeakPtr<Delegate> delegate_;
    146   Mode mode_;
    147   Listener* listener_;
    148   base::ProcessId peer_pid_;
    149   scoped_ptr<mojo::embedder::ChannelInfo,
    150              ChannelInfoDeleter> channel_info_;
    151 
    152   scoped_ptr<internal::ControlReader, ReaderDeleter> control_reader_;
    153   scoped_ptr<internal::MessageReader, ReaderDeleter> message_reader_;
    154   ScopedVector<Message> pending_messages_;
    155 
    156   base::WeakPtrFactory<ChannelMojo> weak_factory_;
    157 
    158   DISALLOW_COPY_AND_ASSIGN(ChannelMojo);
    159 };
    160 
    161 }  // namespace IPC
    162 
    163 #endif  // IPC_IPC_CHANNEL_MOJO_H_
    164