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.
5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_LIB_INTERFACE_IMPL_INTERNAL_H_
6 #define MOJO_PUBLIC_CPP_BINDINGS_LIB_INTERFACE_IMPL_INTERNAL_H_
8 #include "mojo/public/cpp/bindings/error_handler.h"
9 #include "mojo/public/cpp/bindings/interface_ptr.h"
10 #include "mojo/public/cpp/bindings/lib/filter_chain.h"
11 #include "mojo/public/cpp/bindings/lib/message_header_validator.h"
12 #include "mojo/public/cpp/environment/environment.h"
13 #include "mojo/public/cpp/environment/logging.h"
14 #include "mojo/public/cpp/system/macros.h"
19 template <typename Interface
>
20 class InterfaceImplBase
: public Interface
{
22 virtual ~InterfaceImplBase() {}
23 virtual void OnConnectionEstablished() = 0;
24 virtual void OnConnectionError() = 0;
27 template <typename Interface
>
28 class InterfaceImplState
: public ErrorHandler
{
30 typedef typename
Interface::Client Client
;
32 explicit InterfaceImplState(InterfaceImplBase
<Interface
>* instance
)
35 instance_bound_to_pipe_(false)
38 deleting_instance_due_to_error_(false)
41 MOJO_DCHECK(instance
);
42 stub_
.set_sink(instance
);
45 virtual ~InterfaceImplState() {
47 MOJO_DCHECK(!instance_bound_to_pipe_
|| deleting_instance_due_to_error_
);
51 router_
->set_error_handler(NULL
);
57 InterfacePtr
<Interface
>* ptr
,
58 bool instance_bound_to_pipe
,
59 const MojoAsyncWaiter
* waiter
= Environment::GetDefaultAsyncWaiter()) {
61 ptr
->Bind(pipe
.handle0
.Pass(), waiter
);
62 Bind(pipe
.handle1
.Pass(), instance_bound_to_pipe
, waiter
);
65 void Bind(ScopedMessagePipeHandle handle
,
66 bool instance_bound_to_pipe
,
67 const MojoAsyncWaiter
* waiter
) {
71 filters
.Append
<MessageHeaderValidator
>();
72 filters
.Append
<typename
Interface::RequestValidator_
>();
73 filters
.Append
<typename
Interface::Client::ResponseValidator_
>();
75 router_
= new Router(handle
.Pass(), filters
.Pass(), waiter
);
76 router_
->set_incoming_receiver(&stub_
);
77 router_
->set_error_handler(this);
79 proxy_
= new typename
Client::Proxy_(router_
);
81 instance_bound_to_pipe_
= instance_bound_to_pipe
;
83 instance()->OnConnectionEstablished();
86 bool WaitForIncomingMethodCall() {
88 return router_
->WaitForIncomingMessage();
91 Router
* router() { return router_
; }
92 Client
* client() { return proxy_
; }
95 InterfaceImplBase
<Interface
>* instance() {
96 return static_cast<InterfaceImplBase
<Interface
>*>(stub_
.sink());
99 virtual void OnConnectionError() MOJO_OVERRIDE
{
100 // If the the instance is not bound to the pipe, the instance might choose
101 // to delete itself in the OnConnectionError handler, which would in turn
102 // delete this. Save the error behavior before invoking the error handler
103 // so we can correctly decide what to do.
104 bool bound
= instance_bound_to_pipe_
;
105 instance()->OnConnectionError();
109 deleting_instance_due_to_error_
= true;
115 typename
Client::Proxy_
* proxy_
;
116 typename
Interface::Stub_ stub_
;
117 bool instance_bound_to_pipe_
;
119 bool deleting_instance_due_to_error_
;
122 MOJO_DISALLOW_COPY_AND_ASSIGN(InterfaceImplState
);
125 } // namespace internal
128 #endif // MOJO_PUBLIC_CPP_BINDINGS_LIB_INTERFACE_IMPL_INTERNAL_H_