Index: ios/web/webui/resources/mojo_api.js |
diff --git a/ios/web/webui/resources/mojo_api.js b/ios/web/webui/resources/mojo_api.js |
new file mode 100644 |
index 0000000000000000000000000000000000000000..9799ea15726f69525afe6033036e7e72c357f289 |
--- /dev/null |
+++ b/ios/web/webui/resources/mojo_api.js |
@@ -0,0 +1,314 @@ |
+// Copyright 2017 The Chromium Authors. All rights reserved. |
+// Use of this source code is governed by a BSD-style license that can be |
+// found in the LICENSE file. |
+ |
+goog.provide('__crWeb.mojoApi'); |
+ |
+// Note: The API should stay in sync with the IDL definitions in |
+// third_party/WebKit/Source/core/mojo |
+ |
+var Mojo = Mojo || {}; |
+ |
+/** |
+ * MojoResult {number}: Result codes for Mojo operations. |
+ */ |
+Mojo.RESULT_OK = 0; |
+Mojo.RESULT_CANCELLED = 1; |
+Mojo.RESULT_UNKNOWN = 2; |
+Mojo.RESULT_INVALID_ARGUMENT = 3; |
+Mojo.RESULT_DEADLINE_EXCEEDED = 4; |
+Mojo.RESULT_NOT_FOUND = 5; |
+Mojo.RESULT_ALREADY_EXISTS = 6; |
+Mojo.RESULT_PERMISSION_DENIED = 7; |
+Mojo.RESULT_RESOURCE_EXHAUSTED = 8; |
+Mojo.RESULT_FAILED_PRECONDITION = 9; |
+Mojo.RESULT_ABORTED = 10; |
+Mojo.RESULT_OUT_OF_RANGE = 11; |
+Mojo.RESULT_UNIMPLEMENTED = 12; |
+Mojo.RESULT_INTERNAL = 13; |
+Mojo.RESULT_UNAVAILABLE = 14; |
+Mojo.RESULT_DATA_LOSS = 15; |
+Mojo.RESULT_BUSY = 16; |
+Mojo.RESULT_SHOULD_WAIT = 17; |
+ |
+/** |
+ * Creates a message pipe. |
+ * |
+ * @return {result: !MojoResult, handle0: !MojoHandle=, handle1: !MojoHandle=} |
+ * Result code and (on success) the two message pipe handles. |
+ */ |
+Mojo.createMessagePipe = function() { |
+ var result = Mojo.internal.sendMessage({ |
+ name: "Mojo.createMessagePipe", |
+ args: {} |
+ }); |
+ if (result.result == Mojo.RESULT_OK) { |
+ result.handle0 = new MojoHandle(result.handle0); |
+ result.handle1 = new MojoHandle(result.handle1); |
+ } |
+ return result; |
+}; |
+ |
+/** |
+ * Binds to the specified Mojo interface. |
+ * @param {string} interfaceName The interface name to connect. |
+ * @param {!MojoHandle} requestHandle The interface request handle. |
+ */ |
+Mojo.bindInterface = function(interfaceName, requestHandle) { |
+ Mojo.internal.sendMessage({ |
+ name: "Mojo.bindInterface", |
+ args: { |
+ interfaceName: interfaceName, |
+ requestHandle: requestHandle.takeNativeHandle_() |
+ } |
+ }); |
+}; |
+ |
+/** |
+ * @constructor |
+ * @param {?number=} nativeHandle An opaque number representing the underlying |
+ * Mojo system resource. |
+ */ |
+var MojoHandle = function(nativeHandle) { |
+ if (nativeHandle === undefined) |
+ nativeHandle = null; |
+ |
+ /** |
+ * @type {number|null} |
+ */ |
+ this.nativeHandle_ = nativeHandle; |
+}; |
+ |
+/** |
+ * Takes the native handle value. This is not part of the public API. |
+ * @return {?number} |
+ */ |
+MojoHandle.prototype.takeNativeHandle_ = function() { |
+ var nativeHandle = this.nativeHandle_; |
+ this.nativeHandle_ = null; |
+ return nativeHandle; |
+}; |
+ |
+/** |
+ * Closes the handle. |
+ */ |
+MojoHandle.prototype.close = function() { |
+ if (this.nativeHandle_ === null) |
+ return; |
+ |
+ var nativeHandle = this.nativeHandle_; |
+ this.nativeHandle_ = null; |
+ Mojo.internal.sendMessage({ |
+ name: "MojoHandle.close", |
+ args: { |
+ handle: nativeHandle |
+ } |
+ }); |
+}; |
+ |
+/** |
+ * Begins watching the handle for |signals| to be satisfied or unsatisfiable. |
+ * |
+ * @param {readable: boolean=, writable: boolean=, peerClosed: boolean=} signals |
+ * The signals to watch. |
+ * @param {!function(!MojoResult)} calback Called with a result any time |
+ * the watched signals become satisfied or unsatisfiable. |
+ * |
+ * @return {!MojoWatcher} A MojoWatcher instance that could be used to cancel |
+ * the watch. |
+ */ |
+MojoHandle.prototype.watch = function(signals, callback) { |
+ var HANDLE_SIGNAL_NONE = 0; |
+ var HANDLE_SIGNAL_READABLE = 1; |
+ var HANDLE_SIGNAL_WRITABLE = 2; |
+ var HANDLE_SIGNAL_PEER_CLOSED = 4; |
+ |
+ var signalsValue = HANDLE_SIGNAL_NONE; |
+ if (signals.readable) { |
+ signalsValue |= HANDLE_SIGNAL_READABLE; |
+ } |
+ if (signals.writable) { |
+ signalsValue |= HANDLE_SIGNAL_WRITABLE; |
+ } |
+ if (signalsValue.peerClosed) { |
+ signalsValue |= HANDLE_SIGNAL_PEER_CLOSED; |
+ } |
+ |
+ var watchId = Mojo.internal.sendMessage({ |
+ name: "MojoHandle.watch", |
+ args: { |
+ handle: this.nativeHandle_, |
+ signals: signalsValue, |
+ callbackId: Mojo.internal.watchCallbacksHolder.getNextCallbackId() |
+ } |
+ }); |
+ Mojo.internal.watchCallbacksHolder.addWatchCallback(watchId, callback); |
+ |
+ return new MojoWatcher(watchId); |
+}; |
+ |
+/** |
+ * Writes a message to the message pipe. |
+ * |
+ * @param {!ArrayBufferView} buffer The message data. May be empty. |
+ * @param {!Array<!MojoHandle>} handles Any handles to attach. Handles are |
+ * transferred and will no longer be valid. May be empty. |
+ * @return {!MojoResult} Result code. |
+ */ |
+MojoHandle.prototype.writeMessage = function(buffer, handles) { |
+ var nativeHandles = handles.map(function(handle) { |
+ return handle.takeNativeHandle_(); |
+ }); |
+ return Mojo.internal.sendMessage({ |
+ name: "MojoHandle.writeMessage", |
+ args: { |
+ handle: this.nativeHandle_, |
+ buffer: buffer, |
+ handles: nativeHandles, |
+ } |
+ }); |
+}; |
+ |
+/** |
+ * Reads a message from the message pipe. |
+ * |
+ * @return {result: !MojoResult, |
+ * buffer: !ArrayBufferView=, |
+ * handles: !Array<!MojoHandle>=} |
+ * Result code and (on success) the data and handles recevied. |
+ */ |
+MojoHandle.prototype.readMessage = function() { |
+ var result = Mojo.internal.sendMessage({ |
+ name: "MojoHandle.readMessage", |
+ args: { |
+ handle: this.nativeHandle_ |
+ } |
+ }); |
+ |
+ if (result.result == Mojo.RESULT_OK) { |
+ result.buffer = new Uint8Array(result.buffer).buffer; |
+ result.handles = result.handles.map(function(handle) { |
+ return new MojoHandle(handle); |
+ }); |
+ } |
+ return result; |
+}; |
+ |
+/** |
+ * MojoWatcher identifies a watch on a MojoHandle and can be used to cancel the |
+ * watch. |
+ * |
+ * @constructor |
+ * @param {number} An opaque id representing the watch. |
+ */ |
+var MojoWatcher = function(watchId) { |
+ this.watchId_ = watchId; |
+}; |
+ |
+/* |
+ * Cancels a handle watch. |
+ */ |
+MojoWatcher.prototype.cancel = function() { |
+ Mojo.internal.sendMessage({ |
+ name: "MojoWatcher.cancel", |
+ args: { |
+ watchId: this.watchId_ |
+ } |
+ }); |
+ Mojo.internal.watchCallbacksHolder.removeWatchCallback(watchId); |
+}; |
+ |
+// ----------------------------------------------------------------------------- |
+// Mojo API implementation details. It is not part of the public API. |
+ |
+Mojo.internal = Mojo.internal || {}; |
+ |
+/** |
+ * Synchronously sends a message to Mojo backend. |
+ * @param {!Object} message The message to send. |
+ * @return {Object=} Response from Mojo backend. |
+ */ |
+Mojo.internal.sendMessage = function(message) { |
+ var response = window.prompt(__gCrWeb.common.JSONStringify(message)); |
+ return response ? JSON.parse(response) : undefined; |
+}; |
+ |
+/** |
+ * Holds callbacks for all currently active watches. |
+ */ |
+Mojo.internal.watchCallbacksHolder = (function() { |
+ /** |
+ * Next callback id to be used for watch. |
+ * @type{number} |
+ */ |
+ var nextCallbackId = 0; |
+ |
+ /** |
+ * Map where keys are callbacks ids and values are callbacks. |
+ * @type {!Map<number, !function(!MojoResult)>} |
+ */ |
+ var callbacks = new Map(); |
+ |
+ /** |
+ * Map where keys are watch ids and values are callback ids. |
+ * @type {!Map<number, number>} |
+ */ |
+ var callbackIds = new Map(); |
+ |
+ /** |
+ * Calls watch callback. |
+ * |
+ * @param {number} callbackId Callback id previously returned from |
+ {@code getNextCallbackId}. |
+ * @param {!MojoResult} mojoResult The result code to call the callback with. |
+ */ |
+ var callCallback = function(callbackId, mojoResult) { |
+ var callback = callbacks.get(callbackId); |
+ |
+ // Signalling the watch is asynchronous operation and this function may be |
+ // called for already removed watch. |
+ if (callback) |
+ callback(mojoResult); |
+ }; |
+ |
+ /** |
+ * Returns next callback id to be used for watch (idempotent). |
+ * |
+ * @return {number} callback id. |
+ */ |
+ var getNextCallbackId = function() { |
+ return nextCallbackId; |
+ }; |
+ |
+ /** |
+ * Adds callback which must be executed when the watch fires. |
+ * |
+ * @param {number} watchId The value returned from "MojoHandle.watch" Mojo |
+ * backend. |
+ * @param {!function(!MojoResult)} callback The callback which should be |
+ * executed when the watch fires. |
+ */ |
+ var addWatchCallback = function(watchId, callback) { |
+ callbackIds.set(watchId, nextCallbackId); |
+ callbacks.set(nextCallbackId, callback); |
+ ++nextCallbackId; |
+ }; |
+ |
+ /** |
+ * Removes callback which should no longer be executed. |
+ * |
+ * @param {!number} watchId The id to remove callback for. |
+ */ |
+ var removeWatchCallback = function (watchId) { |
+ callbacks.delete(callbackIds.get(watchId)); |
+ callbackIds.delete(watchId); |
+ }; |
+ |
+ return { |
+ callCallback: callCallback, |
+ getNextCallbackId: getNextCallbackId, |
+ addWatchCallback: addWatchCallback, |
+ removeWatchCallback: removeWatchCallback |
+ }; |
+})(); |
+ |