1*635a8641SAndroid Build Coastguard WorkerFrom 225f21f660b943ff9ade13b0d114e8ba3b3036d5 Mon Sep 17 00:00:00 2001 2*635a8641SAndroid Build Coastguard WorkerFrom: Luis Hector Chavez <lhchavez@google.com> 3*635a8641SAndroid Build Coastguard WorkerDate: Fri, 20 Jul 2018 09:39:22 -0700 4*635a8641SAndroid Build Coastguard WorkerSubject: [PATCH] Mojo: Add a way to create thread-safe interfaces in Java 5*635a8641SAndroid Build Coastguard Worker 6*635a8641SAndroid Build Coastguard WorkerThis change adds Interface.Manager.buildThreadSafeProxy(), which is 7*635a8641SAndroid Build Coastguard Workerroughly analogous to mojo::ThreadSafeInterfacePtr<T>. Given that Java 8*635a8641SAndroid Build Coastguard Workerdoes not have move-only semantics, the Proxy object that is passed is 9*635a8641SAndroid Build Coastguard Workerunbound and a new object is returned. 10*635a8641SAndroid Build Coastguard Worker 11*635a8641SAndroid Build Coastguard WorkerBug: 810084 12*635a8641SAndroid Build Coastguard WorkerTest: cheets_ContainerSmokeTest in Chrome OS 13*635a8641SAndroid Build Coastguard WorkerChange-Id: I6565f9e526e3fa8f8cb222cb8cd11e95bb57f7d3 14*635a8641SAndroid Build Coastguard WorkerReviewed-on: https://chromium-review.googlesource.com/1147320 15*635a8641SAndroid Build Coastguard WorkerReviewed-by: Ken Rockot <rockot@chromium.org> 16*635a8641SAndroid Build Coastguard WorkerCommit-Queue: Luis Hector Chavez <lhchavez@chromium.org> 17*635a8641SAndroid Build Coastguard WorkerCr-Commit-Position: refs/heads/master@{#577429} 18*635a8641SAndroid Build Coastguard Worker--- 19*635a8641SAndroid Build Coastguard Worker .../org/chromium/mojo/bindings/Interface.java | 88 +++++++++++++++++++ 20*635a8641SAndroid Build Coastguard Worker 1 file changed, 88 insertions(+) 21*635a8641SAndroid Build Coastguard Worker 22*635a8641SAndroid Build Coastguard Workerdiff --git a/mojo/public/java/bindings/src/org/chromium/mojo/bindings/Interface.java b/mojo/public/java/bindings/src/org/chromium/mojo/bindings/Interface.java 23*635a8641SAndroid Build Coastguard Workerindex e3be8b3..f7d3f80 100644 24*635a8641SAndroid Build Coastguard Worker--- a/mojo/public/java/bindings/src/org/chromium/mojo/bindings/Interface.java 25*635a8641SAndroid Build Coastguard Worker+++ b/mojo/public/java/bindings/src/org/chromium/mojo/bindings/Interface.java 26*635a8641SAndroid Build Coastguard Worker@@ -20,6 +20,7 @@ import org.chromium.mojo.system.MojoException; 27*635a8641SAndroid Build Coastguard Worker import org.chromium.mojo.system.Pair; 28*635a8641SAndroid Build Coastguard Worker 29*635a8641SAndroid Build Coastguard Worker import java.io.Closeable; 30*635a8641SAndroid Build Coastguard Worker+import java.util.concurrent.Executor; 31*635a8641SAndroid Build Coastguard Worker 32*635a8641SAndroid Build Coastguard Worker /** 33*635a8641SAndroid Build Coastguard Worker * Base class for mojo generated interfaces. 34*635a8641SAndroid Build Coastguard Worker@@ -317,6 +318,67 @@ public interface Interface extends ConnectionErrorHandler, Closeable { 35*635a8641SAndroid Build Coastguard Worker 36*635a8641SAndroid Build Coastguard Worker } 37*635a8641SAndroid Build Coastguard Worker 38*635a8641SAndroid Build Coastguard Worker+ /** 39*635a8641SAndroid Build Coastguard Worker+ * A {@link MessageReceiverWithResponder} implementation that forwards all calls to the thread 40*635a8641SAndroid Build Coastguard Worker+ * the ThreadSafeForwarder was created. 41*635a8641SAndroid Build Coastguard Worker+ */ 42*635a8641SAndroid Build Coastguard Worker+ class ThreadSafeForwarder implements MessageReceiverWithResponder { 43*635a8641SAndroid Build Coastguard Worker+ 44*635a8641SAndroid Build Coastguard Worker+ /** 45*635a8641SAndroid Build Coastguard Worker+ * The {@link MessageReceiverWithResponder} that will receive a serialized message for 46*635a8641SAndroid Build Coastguard Worker+ * each method call. 47*635a8641SAndroid Build Coastguard Worker+ */ 48*635a8641SAndroid Build Coastguard Worker+ private final MessageReceiverWithResponder mMessageReceiver; 49*635a8641SAndroid Build Coastguard Worker+ 50*635a8641SAndroid Build Coastguard Worker+ /** 51*635a8641SAndroid Build Coastguard Worker+ * The {@link Executor} to forward all tasks to. 52*635a8641SAndroid Build Coastguard Worker+ */ 53*635a8641SAndroid Build Coastguard Worker+ private final Executor mExecutor; 54*635a8641SAndroid Build Coastguard Worker+ 55*635a8641SAndroid Build Coastguard Worker+ /** 56*635a8641SAndroid Build Coastguard Worker+ * Constructor. 57*635a8641SAndroid Build Coastguard Worker+ * 58*635a8641SAndroid Build Coastguard Worker+ * @param core the Core implementation used to create pipes and access the async waiter. 59*635a8641SAndroid Build Coastguard Worker+ * @param messageReceiver the message receiver to send message to. 60*635a8641SAndroid Build Coastguard Worker+ */ 61*635a8641SAndroid Build Coastguard Worker+ public ThreadSafeForwarder(Core core, MessageReceiverWithResponder messageReceiver) { 62*635a8641SAndroid Build Coastguard Worker+ mMessageReceiver = messageReceiver; 63*635a8641SAndroid Build Coastguard Worker+ mExecutor = ExecutorFactory.getExecutorForCurrentThread(core); 64*635a8641SAndroid Build Coastguard Worker+ } 65*635a8641SAndroid Build Coastguard Worker+ 66*635a8641SAndroid Build Coastguard Worker+ /** 67*635a8641SAndroid Build Coastguard Worker+ * @see org.chromium.mojo.bindings.MessageReceiver#close() 68*635a8641SAndroid Build Coastguard Worker+ */ 69*635a8641SAndroid Build Coastguard Worker+ @Override 70*635a8641SAndroid Build Coastguard Worker+ public void close() { 71*635a8641SAndroid Build Coastguard Worker+ mExecutor.execute(() -> { 72*635a8641SAndroid Build Coastguard Worker+ mMessageReceiver.close(); 73*635a8641SAndroid Build Coastguard Worker+ }); 74*635a8641SAndroid Build Coastguard Worker+ } 75*635a8641SAndroid Build Coastguard Worker+ 76*635a8641SAndroid Build Coastguard Worker+ /** 77*635a8641SAndroid Build Coastguard Worker+ * @see org.chromium.mojo.bindings.MessageReceiver#accept() 78*635a8641SAndroid Build Coastguard Worker+ */ 79*635a8641SAndroid Build Coastguard Worker+ @Override 80*635a8641SAndroid Build Coastguard Worker+ public boolean accept(Message message) { 81*635a8641SAndroid Build Coastguard Worker+ mExecutor.execute(() -> { 82*635a8641SAndroid Build Coastguard Worker+ mMessageReceiver.accept(message); 83*635a8641SAndroid Build Coastguard Worker+ }); 84*635a8641SAndroid Build Coastguard Worker+ return true; 85*635a8641SAndroid Build Coastguard Worker+ } 86*635a8641SAndroid Build Coastguard Worker+ 87*635a8641SAndroid Build Coastguard Worker+ /** 88*635a8641SAndroid Build Coastguard Worker+ * @see org.chromium.mojo.bindings.MessageReceiverWithResponder#acceptWithResponder() 89*635a8641SAndroid Build Coastguard Worker+ */ 90*635a8641SAndroid Build Coastguard Worker+ @Override 91*635a8641SAndroid Build Coastguard Worker+ public boolean acceptWithResponder(Message message, MessageReceiver responder) { 92*635a8641SAndroid Build Coastguard Worker+ mExecutor.execute(() -> { 93*635a8641SAndroid Build Coastguard Worker+ mMessageReceiver.acceptWithResponder(message, responder); 94*635a8641SAndroid Build Coastguard Worker+ }); 95*635a8641SAndroid Build Coastguard Worker+ return true; 96*635a8641SAndroid Build Coastguard Worker+ } 97*635a8641SAndroid Build Coastguard Worker+ } 98*635a8641SAndroid Build Coastguard Worker+ 99*635a8641SAndroid Build Coastguard Worker /** 100*635a8641SAndroid Build Coastguard Worker * The |Manager| object enables building of proxies and stubs for a given interface. 101*635a8641SAndroid Build Coastguard Worker * 102*635a8641SAndroid Build Coastguard Worker@@ -385,6 +447,32 @@ public interface Interface extends ConnectionErrorHandler, Closeable { 103*635a8641SAndroid Build Coastguard Worker return new InterfaceRequest<I>(handle); 104*635a8641SAndroid Build Coastguard Worker } 105*635a8641SAndroid Build Coastguard Worker 106*635a8641SAndroid Build Coastguard Worker+ /** 107*635a8641SAndroid Build Coastguard Worker+ * Constructs a thread-safe Proxy forwarding the calls to the given message receiver. 108*635a8641SAndroid Build Coastguard Worker+ * All calls can be performed from any thread and are posted to the {@link Executor} that 109*635a8641SAndroid Build Coastguard Worker+ * is associated with the thread on which this method was called on. 110*635a8641SAndroid Build Coastguard Worker+ * 111*635a8641SAndroid Build Coastguard Worker+ * The original Proxy object is unbound. 112*635a8641SAndroid Build Coastguard Worker+ */ 113*635a8641SAndroid Build Coastguard Worker+ public final P buildThreadSafeProxy(P proxy) { 114*635a8641SAndroid Build Coastguard Worker+ HandlerImpl handlerImpl = (HandlerImpl) proxy.getProxyHandler(); 115*635a8641SAndroid Build Coastguard Worker+ Core core = handlerImpl.getCore(); 116*635a8641SAndroid Build Coastguard Worker+ int version = handlerImpl.getVersion(); 117*635a8641SAndroid Build Coastguard Worker+ 118*635a8641SAndroid Build Coastguard Worker+ Router router = new RouterImpl(handlerImpl.passHandle()); 119*635a8641SAndroid Build Coastguard Worker+ // Close the original proxy now that its handle has been passed. 120*635a8641SAndroid Build Coastguard Worker+ proxy.close(); 121*635a8641SAndroid Build Coastguard Worker+ 122*635a8641SAndroid Build Coastguard Worker+ proxy = buildProxy( 123*635a8641SAndroid Build Coastguard Worker+ core, new ThreadSafeForwarder(core, new AutoCloseableRouter(core, router))); 124*635a8641SAndroid Build Coastguard Worker+ DelegatingConnectionErrorHandler handlers = new DelegatingConnectionErrorHandler(); 125*635a8641SAndroid Build Coastguard Worker+ handlers.addConnectionErrorHandler(proxy); 126*635a8641SAndroid Build Coastguard Worker+ router.setErrorHandler(handlers); 127*635a8641SAndroid Build Coastguard Worker+ router.start(); 128*635a8641SAndroid Build Coastguard Worker+ ((HandlerImpl) proxy.getProxyHandler()).setVersion(version); 129*635a8641SAndroid Build Coastguard Worker+ return proxy; 130*635a8641SAndroid Build Coastguard Worker+ } 131*635a8641SAndroid Build Coastguard Worker+ 132*635a8641SAndroid Build Coastguard Worker /** 133*635a8641SAndroid Build Coastguard Worker * Binds the implementation to the given |router|. 134*635a8641SAndroid Build Coastguard Worker */ 135*635a8641SAndroid Build Coastguard Worker-- 136*635a8641SAndroid Build Coastguard Worker2.19.0.605.g01d371f741-goog 137*635a8641SAndroid Build Coastguard Worker 138