Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(50)

Side by Side Diff: mojo/public/cpp/bindings/lib/interface_endpoint_client.cc

Issue 1823683006: Mojo C++ bindings: sync call support for associated interfaces and master interfaces (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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 #include "mojo/public/cpp/bindings/lib/interface_endpoint_client.h" 5 #include "mojo/public/cpp/bindings/lib/interface_endpoint_client.h"
6 6
7 #include <stdint.h> 7 #include <stdint.h>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
90 90
91 private: 91 private:
92 base::WeakPtr<InterfaceEndpointClient> endpoint_client_; 92 base::WeakPtr<InterfaceEndpointClient> endpoint_client_;
93 bool accept_was_invoked_; 93 bool accept_was_invoked_;
94 scoped_refptr<base::SingleThreadTaskRunner> task_runner_; 94 scoped_refptr<base::SingleThreadTaskRunner> task_runner_;
95 95
96 DISALLOW_COPY_AND_ASSIGN(ResponderThunk); 96 DISALLOW_COPY_AND_ASSIGN(ResponderThunk);
97 }; 97 };
98 98
99 } // namespace 99 } // namespace
100 // ----------------------------------------------------------------------------
101
102 InterfaceEndpointClient::SyncResponseInfo::SyncResponseInfo(
103 bool* in_response_received)
104 : response_received(in_response_received) {}
105
106 InterfaceEndpointClient::SyncResponseInfo::~SyncResponseInfo() {}
100 107
101 // ---------------------------------------------------------------------------- 108 // ----------------------------------------------------------------------------
102 109
103 InterfaceEndpointClient::HandleIncomingMessageThunk::HandleIncomingMessageThunk( 110 InterfaceEndpointClient::HandleIncomingMessageThunk::HandleIncomingMessageThunk(
104 InterfaceEndpointClient* owner) 111 InterfaceEndpointClient* owner)
105 : owner_(owner) {} 112 : owner_(owner) {}
106 113
107 InterfaceEndpointClient::HandleIncomingMessageThunk:: 114 InterfaceEndpointClient::HandleIncomingMessageThunk::
108 ~HandleIncomingMessageThunk() {} 115 ~HandleIncomingMessageThunk() {}
109 116
110 bool InterfaceEndpointClient::HandleIncomingMessageThunk::Accept( 117 bool InterfaceEndpointClient::HandleIncomingMessageThunk::Accept(
111 Message* message) { 118 Message* message) {
112 return owner_->HandleValidatedMessage(message); 119 return owner_->HandleValidatedMessage(message);
113 } 120 }
114 121
115 // ---------------------------------------------------------------------------- 122 // ----------------------------------------------------------------------------
116 123
117 InterfaceEndpointClient::InterfaceEndpointClient( 124 InterfaceEndpointClient::InterfaceEndpointClient(
118 ScopedInterfaceEndpointHandle handle, 125 ScopedInterfaceEndpointHandle handle,
119 MessageReceiverWithResponderStatus* receiver, 126 MessageReceiverWithResponderStatus* receiver,
120 scoped_ptr<MessageFilter> payload_validator) 127 scoped_ptr<MessageFilter> payload_validator,
128 bool expect_sync_requests)
121 : handle_(std::move(handle)), 129 : handle_(std::move(handle)),
122 incoming_receiver_(receiver), 130 incoming_receiver_(receiver),
123 payload_validator_(std::move(payload_validator)), 131 payload_validator_(std::move(payload_validator)),
124 thunk_(this), 132 thunk_(this),
125 next_request_id_(1), 133 next_request_id_(1),
126 encountered_error_(false), 134 encountered_error_(false),
127 weak_ptr_factory_(this) { 135 weak_ptr_factory_(this) {
128 DCHECK(handle_.is_valid()); 136 DCHECK(handle_.is_valid());
129 DCHECK(handle_.is_local()); 137 DCHECK(handle_.is_local());
130 138
131 // TODO(yzshen): the way to use validator (or message filter in general) 139 // TODO(yzshen): the way to use validator (or message filter in general)
132 // directly is a little awkward. 140 // directly is a little awkward.
133 payload_validator_->set_sink(&thunk_); 141 payload_validator_->set_sink(&thunk_);
134 142
135 handle_.router()->AttachEndpointClient(handle_, this); 143 controller_ = handle_.router()->AttachEndpointClient(handle_, this);
144 if (expect_sync_requests)
145 controller_->AllowWokenUpBySyncWatchOnSameThread();
136 } 146 }
137 147
138 InterfaceEndpointClient::~InterfaceEndpointClient() { 148 InterfaceEndpointClient::~InterfaceEndpointClient() {
139 DCHECK(thread_checker_.CalledOnValidThread()); 149 DCHECK(thread_checker_.CalledOnValidThread());
140 150
141 STLDeleteValues(&responders_);
142
143 handle_.router()->DetachEndpointClient(handle_); 151 handle_.router()->DetachEndpointClient(handle_);
144 } 152 }
145 153
146 AssociatedGroup* InterfaceEndpointClient::associated_group() { 154 AssociatedGroup* InterfaceEndpointClient::associated_group() {
147 if (!associated_group_) 155 if (!associated_group_)
148 associated_group_ = handle_.router()->CreateAssociatedGroup(); 156 associated_group_ = handle_.router()->CreateAssociatedGroup();
149 return associated_group_.get(); 157 return associated_group_.get();
150 } 158 }
151 159
152 uint32_t InterfaceEndpointClient::interface_id() const { 160 uint32_t InterfaceEndpointClient::interface_id() const {
153 DCHECK(thread_checker_.CalledOnValidThread()); 161 DCHECK(thread_checker_.CalledOnValidThread());
154 return handle_.id(); 162 return handle_.id();
155 } 163 }
156 164
157 ScopedInterfaceEndpointHandle InterfaceEndpointClient::PassHandle() { 165 ScopedInterfaceEndpointHandle InterfaceEndpointClient::PassHandle() {
158 DCHECK(thread_checker_.CalledOnValidThread()); 166 DCHECK(thread_checker_.CalledOnValidThread());
159 DCHECK(!has_pending_responders()); 167 DCHECK(!has_pending_responders());
160 168
161 if (!handle_.is_valid()) 169 if (!handle_.is_valid())
162 return ScopedInterfaceEndpointHandle(); 170 return ScopedInterfaceEndpointHandle();
163 171
172 controller_ = nullptr;
164 handle_.router()->DetachEndpointClient(handle_); 173 handle_.router()->DetachEndpointClient(handle_);
165 174
166 return std::move(handle_); 175 return std::move(handle_);
167 } 176 }
168 177
169 void InterfaceEndpointClient::RaiseError() { 178 void InterfaceEndpointClient::RaiseError() {
170 DCHECK(thread_checker_.CalledOnValidThread()); 179 DCHECK(thread_checker_.CalledOnValidThread());
171 180
172 handle_.router()->RaiseError(); 181 handle_.router()->RaiseError();
173 } 182 }
174 183
175 bool InterfaceEndpointClient::Accept(Message* message) { 184 bool InterfaceEndpointClient::Accept(Message* message) {
176 DCHECK(thread_checker_.CalledOnValidThread()); 185 DCHECK(thread_checker_.CalledOnValidThread());
186 DCHECK(controller_);
177 DCHECK(!message->has_flag(kMessageExpectsResponse)); 187 DCHECK(!message->has_flag(kMessageExpectsResponse));
178 188
179 if (encountered_error_) 189 if (encountered_error_)
180 return false; 190 return false;
181 191
182 return handle_.router()->SendMessage(handle_, message); 192 return controller_->SendMessage(message);
183 } 193 }
184 194
185 bool InterfaceEndpointClient::AcceptWithResponder(Message* message, 195 bool InterfaceEndpointClient::AcceptWithResponder(Message* message,
186 MessageReceiver* responder) { 196 MessageReceiver* responder) {
187 DCHECK(thread_checker_.CalledOnValidThread()); 197 DCHECK(thread_checker_.CalledOnValidThread());
198 DCHECK(controller_);
188 DCHECK(message->has_flag(kMessageExpectsResponse)); 199 DCHECK(message->has_flag(kMessageExpectsResponse));
189 200
190 // TODO(yzshen): Sync method call using assoicated interfaces or master
191 // interfaces that serve associated interfaces hasn't been supported yet.
192 if (message->has_flag(kMessageIsSync)) {
193 NOTIMPLEMENTED();
194 return false;
195 }
196
197 if (encountered_error_) 201 if (encountered_error_)
198 return false; 202 return false;
199 203
200 // Reserve 0 in case we want it to convey special meaning in the future. 204 // Reserve 0 in case we want it to convey special meaning in the future.
201 uint64_t request_id = next_request_id_++; 205 uint64_t request_id = next_request_id_++;
202 if (request_id == 0) 206 if (request_id == 0)
203 request_id = next_request_id_++; 207 request_id = next_request_id_++;
204 208
205 message->set_request_id(request_id); 209 message->set_request_id(request_id);
206 210
207 if (!handle_.router()->SendMessage(handle_, message)) 211 if (!controller_->SendMessage(message))
208 return false; 212 return false;
209 213
210 // We assume ownership of |responder|. 214 if (!message->has_flag(kMessageIsSync)) {
211 responders_[request_id] = responder; 215 // We assume ownership of |responder|.
216 async_responders_[request_id] = make_scoped_ptr(responder);
217 return true;
218 }
219
220 bool response_received = false;
221 scoped_ptr<MessageReceiver> sync_responder(responder);
222 sync_responses_.insert(std::make_pair(
223 request_id, make_scoped_ptr(new SyncResponseInfo(&response_received))));
224
225 base::WeakPtr<InterfaceEndpointClient> weak_self =
226 weak_ptr_factory_.GetWeakPtr();
227 bool result = controller_->SyncWatch(&response_received);
228 // Make sure that this instance hasn't been destroyed.
229 if (weak_self) {
230 DCHECK(ContainsKey(sync_responses_, request_id));
231 auto iter = sync_responses_.find(request_id);
232 DCHECK_EQ(&response_received, iter->second->response_received);
233 if (result && response_received) {
234 scoped_ptr<Message> response = std::move(iter->second->response);
235 ignore_result(sync_responder->Accept(response.get()));
236 }
237 sync_responses_.erase(iter);
238 }
239
240 // Return true means that we take ownership of |responder|.
212 return true; 241 return true;
213 } 242 }
214 243
215 bool InterfaceEndpointClient::HandleIncomingMessage(Message* message) { 244 bool InterfaceEndpointClient::HandleIncomingMessage(Message* message) {
216 DCHECK(thread_checker_.CalledOnValidThread()); 245 DCHECK(thread_checker_.CalledOnValidThread());
217 246
218 return payload_validator_->Accept(message); 247 return payload_validator_->Accept(message);
219 } 248 }
220 249
221 void InterfaceEndpointClient::NotifyError() { 250 void InterfaceEndpointClient::NotifyError() {
(...skipping 13 matching lines...) Expand all
235 return false; 264 return false;
236 265
237 MessageReceiverWithStatus* responder = 266 MessageReceiverWithStatus* responder =
238 new ResponderThunk(weak_ptr_factory_.GetWeakPtr()); 267 new ResponderThunk(weak_ptr_factory_.GetWeakPtr());
239 bool ok = incoming_receiver_->AcceptWithResponder(message, responder); 268 bool ok = incoming_receiver_->AcceptWithResponder(message, responder);
240 if (!ok) 269 if (!ok)
241 delete responder; 270 delete responder;
242 return ok; 271 return ok;
243 } else if (message->has_flag(kMessageIsResponse)) { 272 } else if (message->has_flag(kMessageIsResponse)) {
244 uint64_t request_id = message->request_id(); 273 uint64_t request_id = message->request_id();
245 ResponderMap::iterator it = responders_.find(request_id); 274
246 if (it == responders_.end()) 275 if (message->has_flag(kMessageIsSync)) {
276 auto it = sync_responses_.find(request_id);
277 if (it == sync_responses_.end())
278 return false;
279 it->second->response.reset(new Message());
280 message->MoveTo(it->second->response.get());
281 *it->second->response_received = true;
282 return true;
283 }
284
285 auto it = async_responders_.find(request_id);
286 if (it == async_responders_.end())
247 return false; 287 return false;
248 MessageReceiver* responder = it->second; 288 scoped_ptr<MessageReceiver> responder = std::move(it->second);
249 responders_.erase(it); 289 async_responders_.erase(it);
250 bool ok = responder->Accept(message); 290 return responder->Accept(message);
251 delete responder;
252 return ok;
253 } else { 291 } else {
254 if (!incoming_receiver_) 292 if (!incoming_receiver_)
255 return false; 293 return false;
256 294
257 return incoming_receiver_->Accept(message); 295 return incoming_receiver_->Accept(message);
258 } 296 }
259 } 297 }
260 298
261 } // namespace internal 299 } // namespace internal
262 } // namespace mojo 300 } // namespace mojo
OLDNEW
« no previous file with comments | « mojo/public/cpp/bindings/lib/interface_endpoint_client.h ('k') | mojo/public/cpp/bindings/lib/interface_ptr_state.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698