xref: /aosp_15_r20/external/libchrome/ipc/ipc_channel_proxy.h (revision 635a864187cb8b6c713ff48b7e790a6b21769273)
1*635a8641SAndroid Build Coastguard Worker // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2*635a8641SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
3*635a8641SAndroid Build Coastguard Worker // found in the LICENSE file.
4*635a8641SAndroid Build Coastguard Worker 
5*635a8641SAndroid Build Coastguard Worker #ifndef IPC_IPC_CHANNEL_PROXY_H_
6*635a8641SAndroid Build Coastguard Worker #define IPC_IPC_CHANNEL_PROXY_H_
7*635a8641SAndroid Build Coastguard Worker 
8*635a8641SAndroid Build Coastguard Worker #include <stdint.h>
9*635a8641SAndroid Build Coastguard Worker 
10*635a8641SAndroid Build Coastguard Worker #include <map>
11*635a8641SAndroid Build Coastguard Worker #include <memory>
12*635a8641SAndroid Build Coastguard Worker #include <string>
13*635a8641SAndroid Build Coastguard Worker #include <vector>
14*635a8641SAndroid Build Coastguard Worker 
15*635a8641SAndroid Build Coastguard Worker #include "base/callback.h"
16*635a8641SAndroid Build Coastguard Worker #include "base/component_export.h"
17*635a8641SAndroid Build Coastguard Worker #include "base/memory/ref_counted.h"
18*635a8641SAndroid Build Coastguard Worker #include "base/sequence_checker.h"
19*635a8641SAndroid Build Coastguard Worker #include "base/synchronization/lock.h"
20*635a8641SAndroid Build Coastguard Worker #include "build/build_config.h"
21*635a8641SAndroid Build Coastguard Worker #include "ipc/ipc_channel.h"
22*635a8641SAndroid Build Coastguard Worker #include "ipc/ipc_channel_handle.h"
23*635a8641SAndroid Build Coastguard Worker #include "ipc/ipc_listener.h"
24*635a8641SAndroid Build Coastguard Worker #include "ipc/ipc_sender.h"
25*635a8641SAndroid Build Coastguard Worker #include "mojo/public/cpp/bindings/associated_interface_ptr.h"
26*635a8641SAndroid Build Coastguard Worker #include "mojo/public/cpp/bindings/associated_interface_request.h"
27*635a8641SAndroid Build Coastguard Worker #include "mojo/public/cpp/bindings/scoped_interface_endpoint_handle.h"
28*635a8641SAndroid Build Coastguard Worker #include "mojo/public/cpp/bindings/thread_safe_interface_ptr.h"
29*635a8641SAndroid Build Coastguard Worker 
30*635a8641SAndroid Build Coastguard Worker namespace base {
31*635a8641SAndroid Build Coastguard Worker class SingleThreadTaskRunner;
32*635a8641SAndroid Build Coastguard Worker }
33*635a8641SAndroid Build Coastguard Worker 
34*635a8641SAndroid Build Coastguard Worker namespace IPC {
35*635a8641SAndroid Build Coastguard Worker 
36*635a8641SAndroid Build Coastguard Worker class ChannelFactory;
37*635a8641SAndroid Build Coastguard Worker class MessageFilter;
38*635a8641SAndroid Build Coastguard Worker class MessageFilterRouter;
39*635a8641SAndroid Build Coastguard Worker 
40*635a8641SAndroid Build Coastguard Worker //-----------------------------------------------------------------------------
41*635a8641SAndroid Build Coastguard Worker // IPC::ChannelProxy
42*635a8641SAndroid Build Coastguard Worker //
43*635a8641SAndroid Build Coastguard Worker // This class is a helper class that is useful when you wish to run an IPC
44*635a8641SAndroid Build Coastguard Worker // channel on a background thread.  It provides you with the option of either
45*635a8641SAndroid Build Coastguard Worker // handling IPC messages on that background thread or having them dispatched to
46*635a8641SAndroid Build Coastguard Worker // your main thread (the thread on which the IPC::ChannelProxy is created).
47*635a8641SAndroid Build Coastguard Worker //
48*635a8641SAndroid Build Coastguard Worker // The API for an IPC::ChannelProxy is very similar to that of an IPC::Channel.
49*635a8641SAndroid Build Coastguard Worker // When you send a message to an IPC::ChannelProxy, the message is routed to
50*635a8641SAndroid Build Coastguard Worker // the background thread, where it is then passed to the IPC::Channel's Send
51*635a8641SAndroid Build Coastguard Worker // method.  This means that you can send a message from your thread and your
52*635a8641SAndroid Build Coastguard Worker // message will be sent over the IPC channel when possible instead of being
53*635a8641SAndroid Build Coastguard Worker // delayed until your thread returns to its message loop.  (Often IPC messages
54*635a8641SAndroid Build Coastguard Worker // will queue up on the IPC::Channel when there is a lot of traffic, and the
55*635a8641SAndroid Build Coastguard Worker // channel will not get cycles to flush its message queue until the thread, on
56*635a8641SAndroid Build Coastguard Worker // which it is running, returns to its message loop.)
57*635a8641SAndroid Build Coastguard Worker //
58*635a8641SAndroid Build Coastguard Worker // An IPC::ChannelProxy can have a MessageFilter associated with it, which will
59*635a8641SAndroid Build Coastguard Worker // be notified of incoming messages on the IPC::Channel's thread.  This gives
60*635a8641SAndroid Build Coastguard Worker // the consumer of IPC::ChannelProxy the ability to respond to incoming
61*635a8641SAndroid Build Coastguard Worker // messages on this background thread instead of on their own thread, which may
62*635a8641SAndroid Build Coastguard Worker // be bogged down with other processing.  The result can be greatly improved
63*635a8641SAndroid Build Coastguard Worker // latency for messages that can be handled on a background thread.
64*635a8641SAndroid Build Coastguard Worker //
65*635a8641SAndroid Build Coastguard Worker // The consumer of IPC::ChannelProxy is responsible for allocating the Thread
66*635a8641SAndroid Build Coastguard Worker // instance where the IPC::Channel will be created and operated.
67*635a8641SAndroid Build Coastguard Worker //
68*635a8641SAndroid Build Coastguard Worker // Thread-safe send
69*635a8641SAndroid Build Coastguard Worker //
70*635a8641SAndroid Build Coastguard Worker // If a particular |Channel| implementation has a thread-safe |Send()| operation
71*635a8641SAndroid Build Coastguard Worker // then ChannelProxy skips the inter-thread hop and calls |Send()| directly. In
72*635a8641SAndroid Build Coastguard Worker // this case the |channel_| variable is touched by multiple threads so
73*635a8641SAndroid Build Coastguard Worker // |channel_lifetime_lock_| is used to protect it. The locking overhead is only
74*635a8641SAndroid Build Coastguard Worker // paid if the underlying channel supports thread-safe |Send|.
75*635a8641SAndroid Build Coastguard Worker //
COMPONENT_EXPORT(IPC)76*635a8641SAndroid Build Coastguard Worker class COMPONENT_EXPORT(IPC) ChannelProxy : public Sender {
77*635a8641SAndroid Build Coastguard Worker  public:
78*635a8641SAndroid Build Coastguard Worker #if defined(ENABLE_IPC_FUZZER)
79*635a8641SAndroid Build Coastguard Worker   // Interface for a filter to be imposed on outgoing messages which can
80*635a8641SAndroid Build Coastguard Worker   // re-write the message. Used for testing.
81*635a8641SAndroid Build Coastguard Worker   class OutgoingMessageFilter {
82*635a8641SAndroid Build Coastguard Worker    public:
83*635a8641SAndroid Build Coastguard Worker     virtual Message* Rewrite(Message* message) = 0;
84*635a8641SAndroid Build Coastguard Worker   };
85*635a8641SAndroid Build Coastguard Worker #endif
86*635a8641SAndroid Build Coastguard Worker 
87*635a8641SAndroid Build Coastguard Worker   // Initializes a channel proxy.  The channel_handle and mode parameters are
88*635a8641SAndroid Build Coastguard Worker   // passed directly to the underlying IPC::Channel.  The listener is called on
89*635a8641SAndroid Build Coastguard Worker   // the thread that creates the ChannelProxy.  The filter's OnMessageReceived
90*635a8641SAndroid Build Coastguard Worker   // method is called on the thread where the IPC::Channel is running.  The
91*635a8641SAndroid Build Coastguard Worker   // filter may be null if the consumer is not interested in handling messages
92*635a8641SAndroid Build Coastguard Worker   // on the background thread.  Any message not handled by the filter will be
93*635a8641SAndroid Build Coastguard Worker   // dispatched to the listener.  The given task runner correspond to a thread
94*635a8641SAndroid Build Coastguard Worker   // on which IPC::Channel is created and used (e.g. IO thread).
95*635a8641SAndroid Build Coastguard Worker   static std::unique_ptr<ChannelProxy> Create(
96*635a8641SAndroid Build Coastguard Worker       const IPC::ChannelHandle& channel_handle,
97*635a8641SAndroid Build Coastguard Worker       Channel::Mode mode,
98*635a8641SAndroid Build Coastguard Worker       Listener* listener,
99*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner,
100*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& listener_task_runner);
101*635a8641SAndroid Build Coastguard Worker 
102*635a8641SAndroid Build Coastguard Worker   static std::unique_ptr<ChannelProxy> Create(
103*635a8641SAndroid Build Coastguard Worker       std::unique_ptr<ChannelFactory> factory,
104*635a8641SAndroid Build Coastguard Worker       Listener* listener,
105*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner,
106*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& listener_task_runner);
107*635a8641SAndroid Build Coastguard Worker 
108*635a8641SAndroid Build Coastguard Worker   // Constructs a ChannelProxy without initializing it.
109*635a8641SAndroid Build Coastguard Worker   ChannelProxy(
110*635a8641SAndroid Build Coastguard Worker       Listener* listener,
111*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner,
112*635a8641SAndroid Build Coastguard Worker       const scoped_refptr<base::SingleThreadTaskRunner>& listener_task_runner);
113*635a8641SAndroid Build Coastguard Worker 
114*635a8641SAndroid Build Coastguard Worker   ~ChannelProxy() override;
115*635a8641SAndroid Build Coastguard Worker 
116*635a8641SAndroid Build Coastguard Worker   // Initializes the channel proxy. Only call this once to initialize a channel
117*635a8641SAndroid Build Coastguard Worker   // proxy that was not initialized in its constructor. If |create_pipe_now| is
118*635a8641SAndroid Build Coastguard Worker   // true, the pipe is created synchronously. Otherwise it's created on the IO
119*635a8641SAndroid Build Coastguard Worker   // thread.
120*635a8641SAndroid Build Coastguard Worker   void Init(const IPC::ChannelHandle& channel_handle,
121*635a8641SAndroid Build Coastguard Worker             Channel::Mode mode,
122*635a8641SAndroid Build Coastguard Worker             bool create_pipe_now);
123*635a8641SAndroid Build Coastguard Worker   void Init(std::unique_ptr<ChannelFactory> factory,
124*635a8641SAndroid Build Coastguard Worker             bool create_pipe_now);
125*635a8641SAndroid Build Coastguard Worker 
126*635a8641SAndroid Build Coastguard Worker   // Pause the channel. Subsequent calls to Send() will be internally queued
127*635a8641SAndroid Build Coastguard Worker   // until Unpause() is called. Queued messages will not be sent until the
128*635a8641SAndroid Build Coastguard Worker   // channel is flushed.
129*635a8641SAndroid Build Coastguard Worker   void Pause();
130*635a8641SAndroid Build Coastguard Worker 
131*635a8641SAndroid Build Coastguard Worker   // Unpause the channel. If |flush| is true the channel will be flushed as soon
132*635a8641SAndroid Build Coastguard Worker   // as it's unpaused (see Flush() below.) Otherwise you must explicitly call
133*635a8641SAndroid Build Coastguard Worker   // Flush() to flush messages which were queued while the channel was paused.
134*635a8641SAndroid Build Coastguard Worker   void Unpause(bool flush);
135*635a8641SAndroid Build Coastguard Worker 
136*635a8641SAndroid Build Coastguard Worker   // Flush the channel. This sends any messages which were queued before calling
137*635a8641SAndroid Build Coastguard Worker   // Connect. Only useful if Unpause(false) was called previously.
138*635a8641SAndroid Build Coastguard Worker   void Flush();
139*635a8641SAndroid Build Coastguard Worker 
140*635a8641SAndroid Build Coastguard Worker   // Close the IPC::Channel.  This operation completes asynchronously, once the
141*635a8641SAndroid Build Coastguard Worker   // background thread processes the command to close the channel.  It is ok to
142*635a8641SAndroid Build Coastguard Worker   // call this method multiple times.  Redundant calls are ignored.
143*635a8641SAndroid Build Coastguard Worker   //
144*635a8641SAndroid Build Coastguard Worker   // WARNING: MessageFilter objects held by the ChannelProxy is also
145*635a8641SAndroid Build Coastguard Worker   // released asynchronously, and it may in fact have its final reference
146*635a8641SAndroid Build Coastguard Worker   // released on the background thread.  The caller should be careful to deal
147*635a8641SAndroid Build Coastguard Worker   // with / allow for this possibility.
148*635a8641SAndroid Build Coastguard Worker   void Close();
149*635a8641SAndroid Build Coastguard Worker 
150*635a8641SAndroid Build Coastguard Worker   // Send a message asynchronously.  The message is routed to the background
151*635a8641SAndroid Build Coastguard Worker   // thread where it is passed to the IPC::Channel's Send method.
152*635a8641SAndroid Build Coastguard Worker   bool Send(Message* message) override;
153*635a8641SAndroid Build Coastguard Worker 
154*635a8641SAndroid Build Coastguard Worker   // Used to intercept messages as they are received on the background thread.
155*635a8641SAndroid Build Coastguard Worker   //
156*635a8641SAndroid Build Coastguard Worker   // Ordinarily, messages sent to the ChannelProxy are routed to the matching
157*635a8641SAndroid Build Coastguard Worker   // listener on the worker thread.  This API allows code to intercept messages
158*635a8641SAndroid Build Coastguard Worker   // before they are sent to the worker thread.
159*635a8641SAndroid Build Coastguard Worker   // If you call this before the target process is launched, then you're
160*635a8641SAndroid Build Coastguard Worker   // guaranteed to not miss any messages.  But if you call this anytime after,
161*635a8641SAndroid Build Coastguard Worker   // then some messages might be missed since the filter is added internally on
162*635a8641SAndroid Build Coastguard Worker   // the IO thread.
163*635a8641SAndroid Build Coastguard Worker   void AddFilter(MessageFilter* filter);
164*635a8641SAndroid Build Coastguard Worker   void RemoveFilter(MessageFilter* filter);
165*635a8641SAndroid Build Coastguard Worker 
166*635a8641SAndroid Build Coastguard Worker   using GenericAssociatedInterfaceFactory =
167*635a8641SAndroid Build Coastguard Worker       base::Callback<void(mojo::ScopedInterfaceEndpointHandle)>;
168*635a8641SAndroid Build Coastguard Worker 
169*635a8641SAndroid Build Coastguard Worker   // Adds a generic associated interface factory to bind incoming interface
170*635a8641SAndroid Build Coastguard Worker   // requests directly on the IO thread. MUST be called either before Init() or
171*635a8641SAndroid Build Coastguard Worker   // before the remote end of the Channel is able to send messages (e.g. before
172*635a8641SAndroid Build Coastguard Worker   // its process is launched.)
173*635a8641SAndroid Build Coastguard Worker   void AddGenericAssociatedInterfaceForIOThread(
174*635a8641SAndroid Build Coastguard Worker       const std::string& name,
175*635a8641SAndroid Build Coastguard Worker       const GenericAssociatedInterfaceFactory& factory);
176*635a8641SAndroid Build Coastguard Worker 
177*635a8641SAndroid Build Coastguard Worker   template <typename Interface>
178*635a8641SAndroid Build Coastguard Worker   using AssociatedInterfaceFactory =
179*635a8641SAndroid Build Coastguard Worker       base::Callback<void(mojo::AssociatedInterfaceRequest<Interface>)>;
180*635a8641SAndroid Build Coastguard Worker 
181*635a8641SAndroid Build Coastguard Worker   // Helper to bind an IO-thread associated interface factory, inferring the
182*635a8641SAndroid Build Coastguard Worker   // interface name from the callback argument's type. MUST be called before
183*635a8641SAndroid Build Coastguard Worker   // Init().
184*635a8641SAndroid Build Coastguard Worker   template <typename Interface>
185*635a8641SAndroid Build Coastguard Worker   void AddAssociatedInterfaceForIOThread(
186*635a8641SAndroid Build Coastguard Worker       const AssociatedInterfaceFactory<Interface>& factory) {
187*635a8641SAndroid Build Coastguard Worker     AddGenericAssociatedInterfaceForIOThread(
188*635a8641SAndroid Build Coastguard Worker         Interface::Name_,
189*635a8641SAndroid Build Coastguard Worker         base::Bind(&ChannelProxy::BindAssociatedInterfaceRequest<Interface>,
190*635a8641SAndroid Build Coastguard Worker                    factory));
191*635a8641SAndroid Build Coastguard Worker   }
192*635a8641SAndroid Build Coastguard Worker 
193*635a8641SAndroid Build Coastguard Worker   // Requests an associated interface from the remote endpoint.
194*635a8641SAndroid Build Coastguard Worker   void GetGenericRemoteAssociatedInterface(
195*635a8641SAndroid Build Coastguard Worker       const std::string& name,
196*635a8641SAndroid Build Coastguard Worker       mojo::ScopedInterfaceEndpointHandle handle);
197*635a8641SAndroid Build Coastguard Worker 
198*635a8641SAndroid Build Coastguard Worker   // Template helper to request associated interfaces from the remote endpoint.
199*635a8641SAndroid Build Coastguard Worker   template <typename Interface>
200*635a8641SAndroid Build Coastguard Worker   void GetRemoteAssociatedInterface(
201*635a8641SAndroid Build Coastguard Worker       mojo::AssociatedInterfacePtr<Interface>* proxy) {
202*635a8641SAndroid Build Coastguard Worker     auto request = mojo::MakeRequest(proxy);
203*635a8641SAndroid Build Coastguard Worker     GetGenericRemoteAssociatedInterface(Interface::Name_, request.PassHandle());
204*635a8641SAndroid Build Coastguard Worker   }
205*635a8641SAndroid Build Coastguard Worker 
206*635a8641SAndroid Build Coastguard Worker #if defined(ENABLE_IPC_FUZZER)
207*635a8641SAndroid Build Coastguard Worker   void set_outgoing_message_filter(OutgoingMessageFilter* filter) {
208*635a8641SAndroid Build Coastguard Worker     outgoing_message_filter_ = filter;
209*635a8641SAndroid Build Coastguard Worker   }
210*635a8641SAndroid Build Coastguard Worker #endif
211*635a8641SAndroid Build Coastguard Worker 
212*635a8641SAndroid Build Coastguard Worker   // Creates a ThreadSafeAssociatedInterfacePtr for |Interface|. This object
213*635a8641SAndroid Build Coastguard Worker   // may be used to send messages on the interface from any thread and those
214*635a8641SAndroid Build Coastguard Worker   // messages will remain ordered with respect to other messages sent on the
215*635a8641SAndroid Build Coastguard Worker   // same thread over other ThreadSafeAssociatedInterfacePtrs associated with
216*635a8641SAndroid Build Coastguard Worker   // the same Channel.
217*635a8641SAndroid Build Coastguard Worker   template <typename Interface>
218*635a8641SAndroid Build Coastguard Worker   void GetThreadSafeRemoteAssociatedInterface(
219*635a8641SAndroid Build Coastguard Worker       scoped_refptr<mojo::ThreadSafeAssociatedInterfacePtr<Interface>>*
220*635a8641SAndroid Build Coastguard Worker           out_ptr) {
221*635a8641SAndroid Build Coastguard Worker     mojo::AssociatedInterfacePtrInfo<Interface> ptr_info;
222*635a8641SAndroid Build Coastguard Worker     auto request = mojo::MakeRequest(&ptr_info);
223*635a8641SAndroid Build Coastguard Worker     GetGenericRemoteAssociatedInterface(Interface::Name_, request.PassHandle());
224*635a8641SAndroid Build Coastguard Worker     *out_ptr = mojo::ThreadSafeAssociatedInterfacePtr<Interface>::Create(
225*635a8641SAndroid Build Coastguard Worker         std::move(ptr_info), ipc_task_runner());
226*635a8641SAndroid Build Coastguard Worker   }
227*635a8641SAndroid Build Coastguard Worker 
228*635a8641SAndroid Build Coastguard Worker   base::SingleThreadTaskRunner* ipc_task_runner() const {
229*635a8641SAndroid Build Coastguard Worker     return context_->ipc_task_runner();
230*635a8641SAndroid Build Coastguard Worker   }
231*635a8641SAndroid Build Coastguard Worker 
232*635a8641SAndroid Build Coastguard Worker   const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner_refptr()
233*635a8641SAndroid Build Coastguard Worker       const {
234*635a8641SAndroid Build Coastguard Worker     return context_->ipc_task_runner_refptr();
235*635a8641SAndroid Build Coastguard Worker   }
236*635a8641SAndroid Build Coastguard Worker 
237*635a8641SAndroid Build Coastguard Worker   // Called to clear the pointer to the IPC task runner when it's going away.
238*635a8641SAndroid Build Coastguard Worker   void ClearIPCTaskRunner();
239*635a8641SAndroid Build Coastguard Worker 
240*635a8641SAndroid Build Coastguard Worker  protected:
241*635a8641SAndroid Build Coastguard Worker   class Context;
242*635a8641SAndroid Build Coastguard Worker   // A subclass uses this constructor if it needs to add more information
243*635a8641SAndroid Build Coastguard Worker   // to the internal state.
244*635a8641SAndroid Build Coastguard Worker   explicit ChannelProxy(Context* context);
245*635a8641SAndroid Build Coastguard Worker 
246*635a8641SAndroid Build Coastguard Worker   // Used internally to hold state that is referenced on the IPC thread.
247*635a8641SAndroid Build Coastguard Worker   class Context : public base::RefCountedThreadSafe<Context>,
248*635a8641SAndroid Build Coastguard Worker                   public Listener {
249*635a8641SAndroid Build Coastguard Worker    public:
250*635a8641SAndroid Build Coastguard Worker     Context(Listener* listener,
251*635a8641SAndroid Build Coastguard Worker             const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner,
252*635a8641SAndroid Build Coastguard Worker             const scoped_refptr<base::SingleThreadTaskRunner>&
253*635a8641SAndroid Build Coastguard Worker                 listener_task_runner);
254*635a8641SAndroid Build Coastguard Worker     void ClearIPCTaskRunner();
255*635a8641SAndroid Build Coastguard Worker     base::SingleThreadTaskRunner* ipc_task_runner() const {
256*635a8641SAndroid Build Coastguard Worker       return ipc_task_runner_.get();
257*635a8641SAndroid Build Coastguard Worker     }
258*635a8641SAndroid Build Coastguard Worker     const scoped_refptr<base::SingleThreadTaskRunner>& ipc_task_runner_refptr()
259*635a8641SAndroid Build Coastguard Worker         const {
260*635a8641SAndroid Build Coastguard Worker       return ipc_task_runner_;
261*635a8641SAndroid Build Coastguard Worker     }
262*635a8641SAndroid Build Coastguard Worker 
263*635a8641SAndroid Build Coastguard Worker     scoped_refptr<base::SingleThreadTaskRunner> listener_task_runner() {
264*635a8641SAndroid Build Coastguard Worker       return listener_task_runner_;
265*635a8641SAndroid Build Coastguard Worker     }
266*635a8641SAndroid Build Coastguard Worker 
267*635a8641SAndroid Build Coastguard Worker     // Dispatches a message on the listener thread.
268*635a8641SAndroid Build Coastguard Worker     void OnDispatchMessage(const Message& message);
269*635a8641SAndroid Build Coastguard Worker 
270*635a8641SAndroid Build Coastguard Worker     // Sends |message| from appropriate thread.
271*635a8641SAndroid Build Coastguard Worker     void Send(Message* message);
272*635a8641SAndroid Build Coastguard Worker 
273*635a8641SAndroid Build Coastguard Worker    protected:
274*635a8641SAndroid Build Coastguard Worker     friend class base::RefCountedThreadSafe<Context>;
275*635a8641SAndroid Build Coastguard Worker     ~Context() override;
276*635a8641SAndroid Build Coastguard Worker 
277*635a8641SAndroid Build Coastguard Worker     // IPC::Listener methods:
278*635a8641SAndroid Build Coastguard Worker     bool OnMessageReceived(const Message& message) override;
279*635a8641SAndroid Build Coastguard Worker     void OnChannelConnected(int32_t peer_pid) override;
280*635a8641SAndroid Build Coastguard Worker     void OnChannelError() override;
281*635a8641SAndroid Build Coastguard Worker     void OnAssociatedInterfaceRequest(
282*635a8641SAndroid Build Coastguard Worker         const std::string& interface_name,
283*635a8641SAndroid Build Coastguard Worker         mojo::ScopedInterfaceEndpointHandle handle) override;
284*635a8641SAndroid Build Coastguard Worker 
285*635a8641SAndroid Build Coastguard Worker     // Like OnMessageReceived but doesn't try the filters.
286*635a8641SAndroid Build Coastguard Worker     bool OnMessageReceivedNoFilter(const Message& message);
287*635a8641SAndroid Build Coastguard Worker 
288*635a8641SAndroid Build Coastguard Worker     // Gives the filters a chance at processing |message|.
289*635a8641SAndroid Build Coastguard Worker     // Returns true if the message was processed, false otherwise.
290*635a8641SAndroid Build Coastguard Worker     bool TryFilters(const Message& message);
291*635a8641SAndroid Build Coastguard Worker 
292*635a8641SAndroid Build Coastguard Worker     void PauseChannel();
293*635a8641SAndroid Build Coastguard Worker     void UnpauseChannel(bool flush);
294*635a8641SAndroid Build Coastguard Worker     void FlushChannel();
295*635a8641SAndroid Build Coastguard Worker 
296*635a8641SAndroid Build Coastguard Worker     // Like Open and Close, but called on the IPC thread.
297*635a8641SAndroid Build Coastguard Worker     virtual void OnChannelOpened();
298*635a8641SAndroid Build Coastguard Worker     virtual void OnChannelClosed();
299*635a8641SAndroid Build Coastguard Worker 
300*635a8641SAndroid Build Coastguard Worker     // Called on the consumers thread when the ChannelProxy is closed.  At that
301*635a8641SAndroid Build Coastguard Worker     // point the consumer is telling us that they don't want to receive any
302*635a8641SAndroid Build Coastguard Worker     // more messages, so we honor that wish by forgetting them!
303*635a8641SAndroid Build Coastguard Worker     virtual void Clear();
304*635a8641SAndroid Build Coastguard Worker 
305*635a8641SAndroid Build Coastguard Worker    private:
306*635a8641SAndroid Build Coastguard Worker     friend class ChannelProxy;
307*635a8641SAndroid Build Coastguard Worker     friend class IpcSecurityTestUtil;
308*635a8641SAndroid Build Coastguard Worker 
309*635a8641SAndroid Build Coastguard Worker     // Create the Channel
310*635a8641SAndroid Build Coastguard Worker     void CreateChannel(std::unique_ptr<ChannelFactory> factory);
311*635a8641SAndroid Build Coastguard Worker 
312*635a8641SAndroid Build Coastguard Worker     // Methods called on the IO thread.
313*635a8641SAndroid Build Coastguard Worker     void OnSendMessage(std::unique_ptr<Message> message_ptr);
314*635a8641SAndroid Build Coastguard Worker     void OnAddFilter();
315*635a8641SAndroid Build Coastguard Worker     void OnRemoveFilter(MessageFilter* filter);
316*635a8641SAndroid Build Coastguard Worker 
317*635a8641SAndroid Build Coastguard Worker     // Methods called on the listener thread.
318*635a8641SAndroid Build Coastguard Worker     void AddFilter(MessageFilter* filter);
319*635a8641SAndroid Build Coastguard Worker     void OnDispatchConnected();
320*635a8641SAndroid Build Coastguard Worker     void OnDispatchError();
321*635a8641SAndroid Build Coastguard Worker     void OnDispatchBadMessage(const Message& message);
322*635a8641SAndroid Build Coastguard Worker     void OnDispatchAssociatedInterfaceRequest(
323*635a8641SAndroid Build Coastguard Worker         const std::string& interface_name,
324*635a8641SAndroid Build Coastguard Worker         mojo::ScopedInterfaceEndpointHandle handle);
325*635a8641SAndroid Build Coastguard Worker 
326*635a8641SAndroid Build Coastguard Worker     void ClearChannel();
327*635a8641SAndroid Build Coastguard Worker 
328*635a8641SAndroid Build Coastguard Worker     mojom::Channel& thread_safe_channel() {
329*635a8641SAndroid Build Coastguard Worker       return thread_safe_channel_->proxy();
330*635a8641SAndroid Build Coastguard Worker     }
331*635a8641SAndroid Build Coastguard Worker 
332*635a8641SAndroid Build Coastguard Worker     void AddGenericAssociatedInterfaceForIOThread(
333*635a8641SAndroid Build Coastguard Worker         const std::string& name,
334*635a8641SAndroid Build Coastguard Worker         const GenericAssociatedInterfaceFactory& factory);
335*635a8641SAndroid Build Coastguard Worker 
336*635a8641SAndroid Build Coastguard Worker     scoped_refptr<base::SingleThreadTaskRunner> listener_task_runner_;
337*635a8641SAndroid Build Coastguard Worker     Listener* listener_;
338*635a8641SAndroid Build Coastguard Worker 
339*635a8641SAndroid Build Coastguard Worker     // List of filters.  This is only accessed on the IPC thread.
340*635a8641SAndroid Build Coastguard Worker     std::vector<scoped_refptr<MessageFilter> > filters_;
341*635a8641SAndroid Build Coastguard Worker     scoped_refptr<base::SingleThreadTaskRunner> ipc_task_runner_;
342*635a8641SAndroid Build Coastguard Worker 
343*635a8641SAndroid Build Coastguard Worker     // Note, channel_ may be set on the Listener thread or the IPC thread.
344*635a8641SAndroid Build Coastguard Worker     // But once it has been set, it must only be read or cleared on the IPC
345*635a8641SAndroid Build Coastguard Worker     // thread.
346*635a8641SAndroid Build Coastguard Worker     // One exception is the thread-safe send. See the class comment.
347*635a8641SAndroid Build Coastguard Worker     std::unique_ptr<Channel> channel_;
348*635a8641SAndroid Build Coastguard Worker     bool channel_connected_called_;
349*635a8641SAndroid Build Coastguard Worker 
350*635a8641SAndroid Build Coastguard Worker     // Lock for |channel_| value. This is only relevant in the context of
351*635a8641SAndroid Build Coastguard Worker     // thread-safe send.
352*635a8641SAndroid Build Coastguard Worker     base::Lock channel_lifetime_lock_;
353*635a8641SAndroid Build Coastguard Worker 
354*635a8641SAndroid Build Coastguard Worker     // Routes a given message to a proper subset of |filters_|, depending
355*635a8641SAndroid Build Coastguard Worker     // on which message classes a filter might support.
356*635a8641SAndroid Build Coastguard Worker     std::unique_ptr<MessageFilterRouter> message_filter_router_;
357*635a8641SAndroid Build Coastguard Worker 
358*635a8641SAndroid Build Coastguard Worker     // Holds filters between the AddFilter call on the listerner thread and the
359*635a8641SAndroid Build Coastguard Worker     // IPC thread when they're added to filters_.
360*635a8641SAndroid Build Coastguard Worker     std::vector<scoped_refptr<MessageFilter> > pending_filters_;
361*635a8641SAndroid Build Coastguard Worker     // Lock for pending_filters_.
362*635a8641SAndroid Build Coastguard Worker     base::Lock pending_filters_lock_;
363*635a8641SAndroid Build Coastguard Worker 
364*635a8641SAndroid Build Coastguard Worker     // Cached copy of the peer process ID. Set on IPC but read on both IPC and
365*635a8641SAndroid Build Coastguard Worker     // listener threads.
366*635a8641SAndroid Build Coastguard Worker     base::ProcessId peer_pid_;
367*635a8641SAndroid Build Coastguard Worker     base::Lock peer_pid_lock_;
368*635a8641SAndroid Build Coastguard Worker 
369*635a8641SAndroid Build Coastguard Worker     // A thread-safe mojom::Channel interface we use to make remote interface
370*635a8641SAndroid Build Coastguard Worker     // requests from the proxy thread.
371*635a8641SAndroid Build Coastguard Worker     std::unique_ptr<mojo::ThreadSafeForwarder<mojom::Channel>>
372*635a8641SAndroid Build Coastguard Worker         thread_safe_channel_;
373*635a8641SAndroid Build Coastguard Worker 
374*635a8641SAndroid Build Coastguard Worker     // Holds associated interface binders added by
375*635a8641SAndroid Build Coastguard Worker     // AddGenericAssociatedInterfaceForIOThread until the underlying channel has
376*635a8641SAndroid Build Coastguard Worker     // been initialized.
377*635a8641SAndroid Build Coastguard Worker     base::Lock pending_io_thread_interfaces_lock_;
378*635a8641SAndroid Build Coastguard Worker     std::vector<std::pair<std::string, GenericAssociatedInterfaceFactory>>
379*635a8641SAndroid Build Coastguard Worker         pending_io_thread_interfaces_;
380*635a8641SAndroid Build Coastguard Worker   };
381*635a8641SAndroid Build Coastguard Worker 
382*635a8641SAndroid Build Coastguard Worker   Context* context() { return context_.get(); }
383*635a8641SAndroid Build Coastguard Worker 
384*635a8641SAndroid Build Coastguard Worker #if defined(ENABLE_IPC_FUZZER)
385*635a8641SAndroid Build Coastguard Worker   OutgoingMessageFilter* outgoing_message_filter() const {
386*635a8641SAndroid Build Coastguard Worker     return outgoing_message_filter_;
387*635a8641SAndroid Build Coastguard Worker   }
388*635a8641SAndroid Build Coastguard Worker #endif
389*635a8641SAndroid Build Coastguard Worker 
390*635a8641SAndroid Build Coastguard Worker   bool did_init() const { return did_init_; }
391*635a8641SAndroid Build Coastguard Worker 
392*635a8641SAndroid Build Coastguard Worker   // A Send() which doesn't DCHECK if the message is synchronous.
393*635a8641SAndroid Build Coastguard Worker   void SendInternal(Message* message);
394*635a8641SAndroid Build Coastguard Worker 
395*635a8641SAndroid Build Coastguard Worker  private:
396*635a8641SAndroid Build Coastguard Worker   friend class IpcSecurityTestUtil;
397*635a8641SAndroid Build Coastguard Worker 
398*635a8641SAndroid Build Coastguard Worker   template <typename Interface>
399*635a8641SAndroid Build Coastguard Worker   static void BindAssociatedInterfaceRequest(
400*635a8641SAndroid Build Coastguard Worker       const AssociatedInterfaceFactory<Interface>& factory,
401*635a8641SAndroid Build Coastguard Worker       mojo::ScopedInterfaceEndpointHandle handle) {
402*635a8641SAndroid Build Coastguard Worker     factory.Run(mojo::AssociatedInterfaceRequest<Interface>(std::move(handle)));
403*635a8641SAndroid Build Coastguard Worker   }
404*635a8641SAndroid Build Coastguard Worker 
405*635a8641SAndroid Build Coastguard Worker   // Always called once immediately after Init.
406*635a8641SAndroid Build Coastguard Worker   virtual void OnChannelInit();
407*635a8641SAndroid Build Coastguard Worker 
408*635a8641SAndroid Build Coastguard Worker   // By maintaining this indirection (ref-counted) to our internal state, we
409*635a8641SAndroid Build Coastguard Worker   // can safely be destroyed while the background thread continues to do stuff
410*635a8641SAndroid Build Coastguard Worker   // that involves this data.
411*635a8641SAndroid Build Coastguard Worker   scoped_refptr<Context> context_;
412*635a8641SAndroid Build Coastguard Worker 
413*635a8641SAndroid Build Coastguard Worker   // Whether the channel has been initialized.
414*635a8641SAndroid Build Coastguard Worker   bool did_init_;
415*635a8641SAndroid Build Coastguard Worker 
416*635a8641SAndroid Build Coastguard Worker #if defined(ENABLE_IPC_FUZZER)
417*635a8641SAndroid Build Coastguard Worker   OutgoingMessageFilter* outgoing_message_filter_;
418*635a8641SAndroid Build Coastguard Worker #endif
419*635a8641SAndroid Build Coastguard Worker 
420*635a8641SAndroid Build Coastguard Worker   SEQUENCE_CHECKER(sequence_checker_);
421*635a8641SAndroid Build Coastguard Worker };
422*635a8641SAndroid Build Coastguard Worker 
423*635a8641SAndroid Build Coastguard Worker }  // namespace IPC
424*635a8641SAndroid Build Coastguard Worker 
425*635a8641SAndroid Build Coastguard Worker #endif  // IPC_IPC_CHANNEL_PROXY_H_
426