OLD | NEW |
| (Empty) |
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 package org.chromium.mojo.bindings; | |
6 | |
7 import org.chromium.mojo.bindings.Callbacks.Callback1; | |
8 import org.chromium.mojo.bindings.Interface.AbstractProxy.HandlerImpl; | |
9 import org.chromium.mojo.system.Core; | |
10 import org.chromium.mojo.system.MessagePipeHandle; | |
11 import org.chromium.mojo.system.MojoException; | |
12 import org.chromium.mojo.system.Pair; | |
13 | |
14 import java.io.Closeable; | |
15 | |
16 /** | |
17 * Base class for mojo generated interfaces. | |
18 */ | |
19 public interface Interface extends ConnectionErrorHandler, Closeable { | |
20 /** | |
21 * If the interface is an implementation, the close method is called when th
e connection to the | |
22 * implementation is closed. | |
23 * <p> | |
24 * If the interface is a proxy, the close method closes the connection to th
e implementation. | |
25 * This method must be called before the proxy is released. | |
26 * | |
27 * @see java.io.Closeable#close() | |
28 */ | |
29 @Override | |
30 public void close(); | |
31 | |
32 /** | |
33 * A proxy to a mojo interface. This is base class for all generated proxies
. It implements the | |
34 * Interface and each time a method is called, the parameters are serialized
and sent to the | |
35 * {@link MessageReceiverWithResponder}, along with the response callback if
needed. | |
36 */ | |
37 public interface Proxy extends Interface { | |
38 /** | |
39 * Class allowing to interact with the proxy itself. | |
40 */ | |
41 public interface Handler extends Closeable { | |
42 /** | |
43 * Sets the {@link ConnectionErrorHandler} that will be notified of
errors. | |
44 */ | |
45 public void setErrorHandler(ConnectionErrorHandler errorHandler); | |
46 | |
47 /** | |
48 * Unbinds the proxy and passes the handle. Can return null if the p
roxy is not bound or | |
49 * if the proxy is not over a message pipe. | |
50 */ | |
51 public MessagePipeHandle passHandle(); | |
52 | |
53 /** | |
54 * Returns the version number of the interface that the remote side
supports. | |
55 */ | |
56 public int getVersion(); | |
57 | |
58 /** | |
59 * Queries the max version that the remote side supports. On complet
ion, the result will | |
60 * be returned as the input of |callback|. The version number of thi
s interface pointer | |
61 * will also be updated. | |
62 */ | |
63 public void queryVersion(Callback1<Integer> callback); | |
64 | |
65 /** | |
66 * If the remote side doesn't support the specified version, it will
close its end of | |
67 * the message pipe asynchronously. The call does nothing if |versio
n| is no greater | |
68 * than getVersion(). | |
69 * <p> | |
70 * If you make a call to requireVersion() with a version number X wh
ich is not supported | |
71 * by the remote side, it is guaranteed that all calls to the interf
ace methods after | |
72 * requireVersion(X) will be ignored. | |
73 */ | |
74 public void requireVersion(int version); | |
75 } | |
76 | |
77 /** | |
78 * Returns the {@link Handler} object allowing to interact with the prox
y itself. | |
79 */ | |
80 public Handler getProxyHandler(); | |
81 } | |
82 | |
83 /** | |
84 * Base implementation of {@link Proxy}. | |
85 */ | |
86 abstract class AbstractProxy implements Proxy { | |
87 /** | |
88 * Implementation of {@link Handler}. | |
89 */ | |
90 protected static class HandlerImpl implements Proxy.Handler, ConnectionE
rrorHandler { | |
91 /** | |
92 * The {@link Core} implementation to use. | |
93 */ | |
94 private final Core mCore; | |
95 | |
96 /** | |
97 * The {@link MessageReceiverWithResponder} that will receive a seri
alized message for | |
98 * each method call. | |
99 */ | |
100 private final MessageReceiverWithResponder mMessageReceiver; | |
101 | |
102 /** | |
103 * The {@link ConnectionErrorHandler} that will be notified of error
s. | |
104 */ | |
105 private ConnectionErrorHandler mErrorHandler = null; | |
106 | |
107 /** | |
108 * The currently known version of the interface. | |
109 */ | |
110 private int mVersion = 0; | |
111 | |
112 /** | |
113 * Constructor. | |
114 * | |
115 * @param core the Core implementation used to create pipes and acce
ss the async waiter. | |
116 * @param messageReceiver the message receiver to send message to. | |
117 */ | |
118 protected HandlerImpl(Core core, MessageReceiverWithResponder messag
eReceiver) { | |
119 this.mCore = core; | |
120 this.mMessageReceiver = messageReceiver; | |
121 } | |
122 | |
123 void setVersion(int version) { | |
124 mVersion = version; | |
125 } | |
126 | |
127 /** | |
128 * Returns the message receiver to send message to. | |
129 */ | |
130 public MessageReceiverWithResponder getMessageReceiver() { | |
131 return mMessageReceiver; | |
132 } | |
133 | |
134 /** | |
135 * Returns the Core implementation. | |
136 */ | |
137 public Core getCore() { | |
138 return mCore; | |
139 } | |
140 | |
141 /** | |
142 * Sets the {@link ConnectionErrorHandler} that will be notified of
errors. | |
143 */ | |
144 @Override | |
145 public void setErrorHandler(ConnectionErrorHandler errorHandler) { | |
146 this.mErrorHandler = errorHandler; | |
147 } | |
148 | |
149 /** | |
150 * @see ConnectionErrorHandler#onConnectionError(MojoException) | |
151 */ | |
152 @Override | |
153 public void onConnectionError(MojoException e) { | |
154 if (mErrorHandler != null) { | |
155 mErrorHandler.onConnectionError(e); | |
156 } | |
157 } | |
158 | |
159 /** | |
160 * @see Closeable#close() | |
161 */ | |
162 @Override | |
163 public void close() { | |
164 mMessageReceiver.close(); | |
165 } | |
166 | |
167 /** | |
168 * @see Interface.Proxy.Handler#passHandle() | |
169 */ | |
170 @Override | |
171 public MessagePipeHandle passHandle() { | |
172 @SuppressWarnings("unchecked") | |
173 HandleOwner<MessagePipeHandle> handleOwner = | |
174 (HandleOwner<MessagePipeHandle>) mMessageReceiver; | |
175 return handleOwner.passHandle(); | |
176 } | |
177 | |
178 /** | |
179 * @see Handler#getVersion() | |
180 */ | |
181 @Override | |
182 public int getVersion() { | |
183 return mVersion; | |
184 } | |
185 | |
186 /** | |
187 * @see Handler#queryVersion(org.chromium.mojo.bindings.Callbacks.Ca
llback1) | |
188 */ | |
189 @Override | |
190 public void queryVersion(final Callback1<Integer> callback) { | |
191 RunMessageParams message = new RunMessageParams(); | |
192 message.reserved0 = 16; | |
193 message.reserved1 = 0; | |
194 message.queryVersion = new QueryVersion(); | |
195 | |
196 InterfaceControlMessagesHelper.sendRunMessage(getCore(), mMessag
eReceiver, message, | |
197 new Callback1<RunResponseMessageParams>() { | |
198 @Override | |
199 public void call(RunResponseMessageParams response)
{ | |
200 mVersion = response.queryVersionResult.version; | |
201 callback.call(mVersion); | |
202 } | |
203 }); | |
204 } | |
205 | |
206 /** | |
207 * @see Handler#requireVersion(int) | |
208 */ | |
209 @Override | |
210 public void requireVersion(int version) { | |
211 if (mVersion >= version) { | |
212 return; | |
213 } | |
214 mVersion = version; | |
215 RunOrClosePipeMessageParams message = new RunOrClosePipeMessageP
arams(); | |
216 message.reserved0 = 16; | |
217 message.reserved1 = 0; | |
218 message.requireVersion = new RequireVersion(); | |
219 message.requireVersion.version = version; | |
220 InterfaceControlMessagesHelper.sendRunOrClosePipeMessage( | |
221 getCore(), mMessageReceiver, message); | |
222 } | |
223 } | |
224 | |
225 /** | |
226 * The handler associated with this proxy. | |
227 */ | |
228 private final HandlerImpl mHandler; | |
229 | |
230 protected AbstractProxy(Core core, MessageReceiverWithResponder messageR
eceiver) { | |
231 mHandler = new HandlerImpl(core, messageReceiver); | |
232 } | |
233 | |
234 /** | |
235 * @see Interface#close() | |
236 */ | |
237 @Override | |
238 public void close() { | |
239 mHandler.close(); | |
240 } | |
241 | |
242 /** | |
243 * @see Proxy#getProxyHandler() | |
244 */ | |
245 @Override | |
246 public HandlerImpl getProxyHandler() { | |
247 return mHandler; | |
248 } | |
249 | |
250 /** | |
251 * @see ConnectionErrorHandler#onConnectionError(org.chromium.mojo.syste
m.MojoException) | |
252 */ | |
253 @Override | |
254 public void onConnectionError(MojoException e) { | |
255 mHandler.onConnectionError(e); | |
256 } | |
257 } | |
258 | |
259 /** | |
260 * Base implementation of Stub. Stubs are message receivers that deserialize
the payload and | |
261 * call the appropriate method in the implementation. If the method returns
result, the stub | |
262 * serializes the response and sends it back. | |
263 * | |
264 * @param <I> the type of the interface to delegate calls to. | |
265 */ | |
266 abstract class Stub<I extends Interface> implements MessageReceiverWithRespo
nder { | |
267 | |
268 /** | |
269 * The {@link Core} implementation to use. | |
270 */ | |
271 private final Core mCore; | |
272 | |
273 /** | |
274 * The implementation to delegate calls to. | |
275 */ | |
276 private final I mImpl; | |
277 | |
278 /** | |
279 * Constructor. | |
280 * | |
281 * @param core the {@link Core} implementation to use. | |
282 * @param impl the implementation to delegate calls to. | |
283 */ | |
284 public Stub(Core core, I impl) { | |
285 mCore = core; | |
286 mImpl = impl; | |
287 } | |
288 | |
289 /** | |
290 * Returns the Core implementation. | |
291 */ | |
292 protected Core getCore() { | |
293 return mCore; | |
294 } | |
295 | |
296 /** | |
297 * Returns the implementation to delegate calls to. | |
298 */ | |
299 protected I getImpl() { | |
300 return mImpl; | |
301 } | |
302 | |
303 /** | |
304 * @see org.chromium.mojo.bindings.MessageReceiver#close() | |
305 */ | |
306 @Override | |
307 public void close() { | |
308 mImpl.close(); | |
309 } | |
310 | |
311 } | |
312 | |
313 /** | |
314 * Enables managing the bindings from an implementation to a message pipe. | |
315 */ | |
316 interface Binding { | |
317 /** | |
318 * Unbinds the implementation from the message pipe. Returns the handle
that will be owned | |
319 * by the caller. | |
320 */ | |
321 public MessagePipeHandle unbind(); | |
322 | |
323 /** | |
324 * Registers an error handler on the binding. It will be called if an er
ror happens on the | |
325 * underlying message pipe. | |
326 */ | |
327 public void registerErrorHandler(ConnectionErrorHandler errorHandler); | |
328 } | |
329 | |
330 /** | |
331 * The |Manager| object enables building of proxies and stubs for a given in
terface. | |
332 * | |
333 * @param <I> the type of the interface the manager can handle. | |
334 * @param <P> the type of the proxy the manager can handle. To be noted, P a
lways extends I. | |
335 */ | |
336 abstract class Manager<I extends Interface, P extends Proxy> { | |
337 | |
338 /** | |
339 * Returns the version of the managed interface. | |
340 */ | |
341 public abstract int getVersion(); | |
342 | |
343 /** | |
344 * Binds the given implementation to the handle. | |
345 */ | |
346 public Binding bind(I impl, MessagePipeHandle handle) { | |
347 // The router (and by consequence the handle) is intentionally leake
d. It will close | |
348 // itself when the connected handle is closed and the proxy receives
the connection | |
349 // error. | |
350 Router router = new RouterImpl(handle); | |
351 Binding result = bind(handle.getCore(), impl, router); | |
352 router.start(); | |
353 return result; | |
354 } | |
355 | |
356 /** | |
357 * Binds the given implementation to the InterfaceRequest. | |
358 */ | |
359 public final Binding bind(I impl, InterfaceRequest<I> request) { | |
360 return bind(impl, request.passHandle()); | |
361 } | |
362 | |
363 /** | |
364 * Returns a Proxy that will send messages to the given |handle|. This i
mplies that the | |
365 * other end of the handle must be bound to an implementation of the int
erface. | |
366 */ | |
367 public final P attachProxy(MessagePipeHandle handle, int version) { | |
368 RouterImpl router = new RouterImpl(handle); | |
369 P proxy = attachProxy(handle.getCore(), router); | |
370 DelegatingConnectionErrorHandler delegatingHandler = | |
371 new DelegatingConnectionErrorHandler(); | |
372 delegatingHandler.addConnectionErrorHandler(proxy); | |
373 router.setErrorHandler(delegatingHandler); | |
374 router.start(); | |
375 ((HandlerImpl) proxy.getProxyHandler()).setVersion(version); | |
376 return proxy; | |
377 } | |
378 | |
379 /** | |
380 * Constructs a new |InterfaceRequest| for the interface. This method re
turns a Pair where | |
381 * the first element is a proxy, and the second element is the request.
The proxy can be | |
382 * used immediately. | |
383 */ | |
384 public final Pair<P, InterfaceRequest<I>> getInterfaceRequest(Core core)
{ | |
385 Pair<MessagePipeHandle, MessagePipeHandle> handles = core.createMess
agePipe(null); | |
386 P proxy = attachProxy(handles.first, 0); | |
387 return Pair.create(proxy, new InterfaceRequest<I>(handles.second)); | |
388 } | |
389 | |
390 public final InterfaceRequest<I> asInterfaceRequest(MessagePipeHandle ha
ndle) { | |
391 return new InterfaceRequest<I>(handle); | |
392 } | |
393 | |
394 /** | |
395 * Binds the implementation to the given |router|. | |
396 */ | |
397 final Binding bind(Core core, I impl, final Router router) { | |
398 final DelegatingConnectionErrorHandler delegatingHandler = | |
399 new DelegatingConnectionErrorHandler(); | |
400 delegatingHandler.addConnectionErrorHandler(impl); | |
401 router.setErrorHandler(delegatingHandler); | |
402 router.setIncomingMessageReceiver(buildStub(core, impl)); | |
403 return new Binding() { | |
404 | |
405 @Override | |
406 public MessagePipeHandle unbind() { | |
407 return router.passHandle(); | |
408 } | |
409 | |
410 @Override | |
411 public void registerErrorHandler(ConnectionErrorHandler errorHan
dler) { | |
412 delegatingHandler.addConnectionErrorHandler(errorHandler); | |
413 } | |
414 }; | |
415 } | |
416 | |
417 /** | |
418 * Returns a Proxy that will send messages to the given |router|. | |
419 */ | |
420 final P attachProxy(Core core, Router router) { | |
421 return buildProxy(core, new AutoCloseableRouter(core, router)); | |
422 } | |
423 | |
424 /** | |
425 * Creates a new array of the given |size|. | |
426 */ | |
427 protected abstract I[] buildArray(int size); | |
428 | |
429 /** | |
430 * Constructs a Stub delegating to the given implementation. | |
431 */ | |
432 protected abstract Stub<I> buildStub(Core core, I impl); | |
433 | |
434 /** | |
435 * Constructs a Proxy forwarding the calls to the given message receiver
. | |
436 */ | |
437 protected abstract P buildProxy(Core core, MessageReceiverWithResponder
messageReceiver); | |
438 | |
439 } | |
440 | |
441 /** | |
442 * The |Manager| object for interfaces having an associated service name in
the bindings. | |
443 */ | |
444 abstract class NamedManager<I extends Interface, P extends Proxy> extends Ma
nager<I, P> { | |
445 /** | |
446 * Returns the name of the service. This is an opaque (but human readabl
e) identifier used | |
447 * by the service provider to identify services. | |
448 */ | |
449 public abstract String getName(); | |
450 } | |
451 } | |
OLD | NEW |