OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ | 5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ |
6 #define MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ | 6 #define MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ |
7 | 7 |
| 8 #include "mojo/public/cpp/bindings/binding.h" |
8 #include "mojo/public/cpp/bindings/interface_request.h" | 9 #include "mojo/public/cpp/bindings/interface_request.h" |
9 #include "mojo/public/cpp/bindings/lib/interface_impl_internal.h" | |
10 #include "mojo/public/cpp/environment/environment.h" | 10 #include "mojo/public/cpp/environment/environment.h" |
11 #include "mojo/public/cpp/system/macros.h" | 11 #include "mojo/public/cpp/system/macros.h" |
12 | 12 |
13 namespace mojo { | 13 namespace mojo { |
14 | 14 |
| 15 // DEPRECATED! Please use mojo::Binding instead of InterfaceImpl<> in new code. |
| 16 // |
15 // InterfaceImpl<..> is designed to be the base class of an interface | 17 // InterfaceImpl<..> is designed to be the base class of an interface |
16 // implementation. It may be bound to a pipe or a proxy, see BindToPipe and | 18 // implementation. It may be bound to a pipe or a proxy, see BindToPipe and |
17 // BindToProxy. | 19 // BindToProxy. |
18 template <typename Interface> | 20 template <typename Interface> |
19 class InterfaceImpl : public internal::InterfaceImplBase<Interface> { | 21 class InterfaceImpl : public Interface, public ErrorHandler { |
20 public: | 22 public: |
21 typedef typename Interface::Client Client; | 23 using ImplementedInterface = Interface; |
22 typedef Interface ImplementedInterface; | 24 using Client = typename Interface::Client; |
23 | 25 |
24 InterfaceImpl() : internal_state_(this) {} | 26 InterfaceImpl() : binding_(this), error_handler_impl_(this) { |
| 27 binding_.set_error_handler(&error_handler_impl_); |
| 28 } |
25 virtual ~InterfaceImpl() {} | 29 virtual ~InterfaceImpl() {} |
26 | 30 |
27 // Returns a proxy to the client interface. This is null upon construction, | 31 void BindToHandle( |
28 // and becomes non-null after OnClientConnected. NOTE: It remains non-null | 32 ScopedMessagePipeHandle handle, |
29 // until this instance is deleted. | 33 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
30 Client* client() { return internal_state_.client(); } | 34 binding_.Bind(handle.Pass(), waiter); |
31 | |
32 // Blocks the current thread for the first incoming method call, i.e., either | |
33 // a call to a method or a client callback method. Returns |true| if a method | |
34 // has been called, |false| in case of error. It must only be called on a | |
35 // bound object. | |
36 bool WaitForIncomingMethodCall() { | |
37 return internal_state_.WaitForIncomingMethodCall(); | |
38 } | 35 } |
39 | 36 |
40 // Called when the client has connected to this instance. | 37 bool WaitForIncomingMethodCall() { |
41 virtual void OnConnectionEstablished() {} | 38 return binding_.WaitForIncomingMethodCall(); |
| 39 } |
| 40 |
| 41 Client* client() { return binding_.client(); } |
| 42 internal::Router* internal_router() { return binding_.internal_router(); } |
42 | 43 |
43 // Called when the client is no longer connected to this instance. NOTE: The | 44 // Called when the client is no longer connected to this instance. NOTE: The |
44 // client() method continues to return a non-null pointer after this method | 45 // client() method continues to return a non-null pointer after this method |
45 // is called. After this method is called, any method calls made on client() | 46 // is called. After this method is called, any method calls made on client() |
46 // will be silently ignored. | 47 // will be silently ignored. |
47 virtual void OnConnectionError() {} | 48 virtual void OnConnectionError() {} |
48 | 49 |
49 // DO NOT USE. Exposed only for internal use and for testing. | 50 void set_delete_on_error(bool delete_on_error) { |
50 internal::InterfaceImplState<Interface>* internal_state() { | 51 error_handler_impl_.set_delete_on_error(delete_on_error); |
51 return &internal_state_; | |
52 } | 52 } |
53 | 53 |
54 private: | 54 private: |
55 internal::InterfaceImplState<Interface> internal_state_; | 55 class ErrorHandlerImpl : public ErrorHandler { |
| 56 public: |
| 57 explicit ErrorHandlerImpl(InterfaceImpl* impl) : impl_(impl) {} |
| 58 ~ErrorHandlerImpl() override {} |
| 59 |
| 60 // ErrorHandler implementation: |
| 61 void OnConnectionError() override { |
| 62 // If the the instance is not bound to the pipe, the instance might choose |
| 63 // to delete the binding in the OnConnectionError handler, which would in |
| 64 // turn delete |this|. Save the error behavior before invoking the error |
| 65 // handler so we can correctly decide what to do. |
| 66 bool delete_on_error = delete_on_error_; |
| 67 impl_->OnConnectionError(); |
| 68 if (delete_on_error) |
| 69 delete impl_; |
| 70 } |
| 71 |
| 72 void set_delete_on_error(bool delete_on_error) { |
| 73 delete_on_error_ = delete_on_error; |
| 74 } |
| 75 |
| 76 private: |
| 77 InterfaceImpl* impl_; |
| 78 bool delete_on_error_ = false; |
| 79 |
| 80 MOJO_DISALLOW_COPY_AND_ASSIGN(ErrorHandlerImpl); |
| 81 }; |
| 82 |
| 83 Binding<Interface> binding_; |
| 84 ErrorHandlerImpl error_handler_impl_; |
| 85 |
56 MOJO_DISALLOW_COPY_AND_ASSIGN(InterfaceImpl); | 86 MOJO_DISALLOW_COPY_AND_ASSIGN(InterfaceImpl); |
57 }; | 87 }; |
58 | 88 |
59 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given | 89 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given |
60 // MessagePipe. The instance is returned for convenience in member initializer | 90 // MessagePipe. The instance is returned for convenience in member initializer |
61 // lists, etc. | 91 // lists, etc. |
62 // | 92 // |
63 // If the pipe is closed, the instance's OnConnectionError method will be called | 93 // If the pipe is closed, the instance's OnConnectionError method will be called |
64 // and then the instance will be deleted. | 94 // and then the instance will be deleted. |
65 // | 95 // |
66 // The instance is also bound to the current thread. Its methods will only be | 96 // The instance is also bound to the current thread. Its methods will only be |
67 // called on the current thread, and if the current thread exits, then the end | 97 // called on the current thread, and if the current thread exits, then the end |
68 // point of the pipe will be closed and the error handler's OnConnectionError | 98 // point of the pipe will be closed and the error handler's OnConnectionError |
69 // method will be called. | 99 // method will be called. |
70 // | |
71 // Before returning, the instance's OnConnectionEstablished method is called. | |
72 template <typename Impl> | 100 template <typename Impl> |
73 Impl* BindToPipe( | 101 Impl* BindToPipe( |
74 Impl* instance, | 102 Impl* instance, |
75 ScopedMessagePipeHandle handle, | 103 ScopedMessagePipeHandle handle, |
76 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { | 104 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
77 instance->internal_state()->Bind(handle.Pass(), true, waiter); | 105 instance->set_delete_on_error(true); |
| 106 instance->BindToHandle(handle.Pass(), waiter); |
78 return instance; | 107 return instance; |
79 } | 108 } |
80 | 109 |
81 // Like BindToPipe but does not delete the instance after a channel error. | 110 // Like BindToPipe but does not delete the instance after a channel error. |
82 template <typename Impl> | 111 template <typename Impl> |
83 Impl* WeakBindToPipe( | 112 Impl* WeakBindToPipe( |
84 Impl* instance, | 113 Impl* instance, |
85 ScopedMessagePipeHandle handle, | 114 ScopedMessagePipeHandle handle, |
86 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { | 115 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
87 instance->internal_state()->Bind(handle.Pass(), false, waiter); | 116 instance->BindToHandle(handle.Pass(), waiter); |
88 return instance; | 117 return instance; |
89 } | 118 } |
90 | 119 |
91 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given | 120 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given |
92 // InterfacePtr<..>. The instance is returned for convenience in member | 121 // InterfacePtr<..>. The instance is returned for convenience in member |
93 // initializer lists, etc. If the pipe is closed, the instance's | 122 // initializer lists, etc. If the pipe is closed, the instance's |
94 // OnConnectionError method will be called and then the instance will be | 123 // OnConnectionError method will be called and then the instance will be |
95 // deleted. | 124 // deleted. |
96 // | 125 // |
97 // The instance is also bound to the current thread. Its methods will only be | 126 // The instance is also bound to the current thread. Its methods will only be |
98 // called on the current thread, and if the current thread exits, then it will | 127 // called on the current thread, and if the current thread exits, then it will |
99 // also be deleted, and along with it, its end point of the pipe will be closed. | 128 // also be deleted, and along with it, its end point of the pipe will be closed. |
100 // | |
101 // Before returning, the instance's OnConnectionEstablished method is called. | |
102 template <typename Impl, typename Interface> | 129 template <typename Impl, typename Interface> |
103 Impl* BindToProxy( | 130 Impl* BindToProxy( |
104 Impl* instance, | 131 Impl* instance, |
105 InterfacePtr<Interface>* ptr, | 132 InterfacePtr<Interface>* ptr, |
106 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { | 133 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
107 instance->internal_state()->BindProxy(ptr, true, waiter); | 134 instance->set_delete_on_error(true); |
| 135 WeakBindToProxy(instance, ptr, waiter); |
108 return instance; | 136 return instance; |
109 } | 137 } |
110 | 138 |
111 // Like BindToProxy but does not delete the instance after a channel error. | 139 // Like BindToProxy but does not delete the instance after a channel error. |
112 template <typename Impl, typename Interface> | 140 template <typename Impl, typename Interface> |
113 Impl* WeakBindToProxy( | 141 Impl* WeakBindToProxy( |
114 Impl* instance, | 142 Impl* instance, |
115 InterfacePtr<Interface>* ptr, | 143 InterfacePtr<Interface>* ptr, |
116 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { | 144 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
117 instance->internal_state()->BindProxy(ptr, false, waiter); | 145 MessagePipe pipe; |
| 146 ptr->Bind(pipe.handle0.Pass(), waiter); |
| 147 instance->BindToHandle(pipe.handle1.Pass(), waiter); |
118 return instance; | 148 return instance; |
119 } | 149 } |
120 | 150 |
121 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given | 151 // Takes an instance of an InterfaceImpl<..> subclass and binds it to the given |
122 // InterfaceRequest<..>. The instance is returned for convenience in member | 152 // InterfaceRequest<..>. The instance is returned for convenience in member |
123 // initializer lists, etc. If the pipe is closed, the instance's | 153 // initializer lists, etc. If the pipe is closed, the instance's |
124 // OnConnectionError method will be called and then the instance will be | 154 // OnConnectionError method will be called and then the instance will be |
125 // deleted. | 155 // deleted. |
126 // | 156 // |
127 // The instance is also bound to the current thread. Its methods will only be | 157 // The instance is also bound to the current thread. Its methods will only be |
(...skipping 15 matching lines...) Expand all Loading... |
143 Impl* WeakBindToRequest( | 173 Impl* WeakBindToRequest( |
144 Impl* instance, | 174 Impl* instance, |
145 InterfaceRequest<Interface>* request, | 175 InterfaceRequest<Interface>* request, |
146 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { | 176 const MojoAsyncWaiter* waiter = Environment::GetDefaultAsyncWaiter()) { |
147 return WeakBindToPipe(instance, request->PassMessagePipe(), waiter); | 177 return WeakBindToPipe(instance, request->PassMessagePipe(), waiter); |
148 } | 178 } |
149 | 179 |
150 } // namespace mojo | 180 } // namespace mojo |
151 | 181 |
152 #endif // MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ | 182 #endif // MOJO_PUBLIC_CPP_BINDINGS_INTERFACE_IMPL_H_ |
OLD | NEW |