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

Side by Side Diff: extensions/renderer/resources/serial_service.js

Issue 423403002: Implement more of chrome.serial on the Mojo SerialConnection. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@js-serial
Patch Set: add missed GN change Created 6 years, 4 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 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 define('serial_service', [ 5 define('serial_service', [
6 'content/public/renderer/service_provider', 6 'content/public/renderer/service_provider',
7 'device/serial/serial.mojom', 7 'device/serial/serial.mojom',
8 'mojo/public/js/bindings/core',
8 'mojo/public/js/bindings/router', 9 'mojo/public/js/bindings/router',
9 ], function(serviceProvider, serialMojom, routerModule) { 10 ], function(serviceProvider, serialMojom, core, routerModule) {
11 /**
12 * A Javascript client for the serial service and connection Mojo services.
13 *
14 * This provides a thick client around the Mojo services, exposing a JS-style
15 * interface to serial connections and information about serial devices. This
16 * converts parameters and result between the Apps serial API types and the
17 * Mojo types.
18 */
10 19
11 function defineService(proxy, handle) { 20 var service = new serialMojom.SerialServiceProxy(new routerModule.Router(
12 if (!handle) 21 serviceProvider.connectToService(serialMojom.SerialServiceProxy.NAME_)));
13 handle = serviceProvider.connectToService(proxy.NAME_);
14 var router = new routerModule.Router(handle);
15 var service = new proxy(router);
16 return {
17 service: service,
18 router: router,
19 };
20 }
21
22 var service = defineService(serialMojom.SerialServiceProxy).service;
23 22
24 function getDevices() { 23 function getDevices() {
25 return service.getDevices().then(function(response) { 24 return service.getDevices().then(function(response) {
26 return $Array.map(response.devices, function(device) { 25 return $Array.map(response.devices, function(device) {
27 var result = {path: device.path || ''}; 26 var result = {path: device.path || ''};
28 if (device.has_vendor_id) 27 if (device.has_vendor_id)
29 result.vendorId = device.vendor_id; 28 result.vendorId = device.vendor_id;
30 if (device.has_product_id) 29 if (device.has_product_id)
31 result.productId = device.product_id; 30 result.productId = device.product_id;
32 if (device.display_name) 31 if (device.display_name)
33 result.displayName = device.display_name; 32 result.displayName = device.display_name;
34 return result; 33 return result;
35 }); 34 });
36 }); 35 });
37 } 36 }
38 37
38 var DEFAULT_CLIENT_OPTIONS = {
39 persistent: false,
40 name: '',
41 receiveTimeout: 0,
42 sendTimeout: 0,
43 bufferSize: 4096,
44 };
45
46 var DATA_BITS_TO_MOJO = {
47 undefined: serialMojom.DataBits.NONE,
48 'seven': serialMojom.DataBits.SEVEN,
49 'eight': serialMojom.DataBits.EIGHT,
50 };
51 var STOP_BITS_TO_MOJO = {
52 undefined: serialMojom.StopBits.NONE,
53 'one': serialMojom.StopBits.ONE,
54 'two': serialMojom.StopBits.TWO,
55 };
56 var PARITY_BIT_TO_MOJO = {
57 undefined: serialMojom.ParityBit.NONE,
58 'no': serialMojom.ParityBit.NO,
59 'odd': serialMojom.ParityBit.ODD,
60 'even': serialMojom.ParityBit.EVEN,
61 };
62
63 function invertMap(input) {
64 var output = {};
65 for (var key in input) {
66 if (key == 'undefined')
67 output[input[key]] = undefined;
68 else
69 output[input[key]] = key;
70 }
71 return output;
72 }
73 var DATA_BITS_FROM_MOJO = invertMap(DATA_BITS_TO_MOJO);
74 var STOP_BITS_FROM_MOJO = invertMap(STOP_BITS_TO_MOJO);
75 var PARITY_BIT_FROM_MOJO = invertMap(PARITY_BIT_TO_MOJO);
76
77 function getServiceOptions(options) {
78 var out = {};
79 if (options.dataBits)
80 out.data_bits = DATA_BITS_TO_MOJO[options.dataBits];
81 if (options.stopBits)
82 out.stop_bits = STOP_BITS_TO_MOJO[options.stopBits];
83 if (options.parityBit)
84 out.parity_bit = PARITY_BIT_TO_MOJO[options.parityBit];
85 if ('ctsFlowControl' in options) {
86 out.has_cts_flow_control = true;
87 out.cts_flow_control = options.ctsFlowControl;
88 }
89 if ('bitrate' in options)
90 out.bitrate = options.bitrate;
91 return out;
92 }
93
94 function convertServiceInfo(result) {
95 if (!result.info)
96 throw new Error('Failed to get ConnectionInfo.');
97 return {
98 ctsFlowControl: !!result.info.cts_flow_control,
99 bitrate: result.info.bitrate || undefined,
100 dataBits: DATA_BITS_FROM_MOJO[result.info.data_bits],
101 stopBits: STOP_BITS_FROM_MOJO[result.info.stop_bits],
102 parityBit: PARITY_BIT_FROM_MOJO[result.info.parity_bit],
103 };
104 }
105
106 function Connection(remoteConnection, router, id, options) {
107 this.remoteConnection_ = remoteConnection;
108 this.router_ = router;
109 this.id_ = id;
110 getConnections().then(function(connections) {
111 connections[this.id_] = this;
112 }.bind(this));
113 this.paused_ = false;
114 this.options_ = {};
115 for (var key in DEFAULT_CLIENT_OPTIONS) {
116 this.options_[key] = DEFAULT_CLIENT_OPTIONS[key];
117 }
118 this.setClientOptions_(options);
119 }
120
121 Connection.create = function(path, options) {
122 options = options || {};
123 var serviceOptions = getServiceOptions(options);
124 var pipe = core.createMessagePipe();
125 service.connect(path, serviceOptions, pipe.handle0);
126 var router = new routerModule.Router(pipe.handle1);
127 var connection = new serialMojom.ConnectionProxy(router);
128 return connection.getInfo().then(convertServiceInfo).then(
129 function(info) {
130 return Promise.all([info, allocateConnectionId()]);
131 }).catch(function(e) {
132 router.close();
133 throw e;
134 }).then(function(results) {
135 var info = results[0];
136 var id = results[1];
137 var serialConnectionClient = new Connection(
138 connection, router, id, options);
139 var clientInfo = serialConnectionClient.getClientInfo_();
140 for (var key in clientInfo) {
141 info[key] = clientInfo[key];
142 }
143 return {
144 connection: serialConnectionClient,
145 info: info,
146 };
147 });
148 };
149
150 Connection.prototype.close = function() {
151 this.router_.close();
152 return getConnections().then(function(connections) {
153 delete connections[this.id_]
154 return true;
155 }.bind(this));
156 };
157
158 Connection.prototype.getClientInfo_ = function() {
159 var info = {
160 connectionId: this.id_,
161 paused: this.paused_,
162 }
163 for (var key in this.options_) {
164 info[key] = this.options_[key];
165 }
166 return info;
167 };
168
169 Connection.prototype.getInfo = function() {
170 var info = this.getClientInfo_();
171 return this.remoteConnection_.getInfo().then(convertServiceInfo).then(
172 function(result) {
173 for (var key in result) {
174 info[key] = result[key];
175 }
176 return info;
177 }).catch(function() {
178 return info;
179 });
180 };
181
182 Connection.prototype.setClientOptions_ = function(options) {
183 if ('name' in options)
184 this.options_.name = options.name;
185 if ('receiveTimeout' in options)
186 this.options_.receiveTimeout = options.receiveTimeout;
187 if ('sendTimeout' in options)
188 this.options_.sendTimeout = options.sendTimeout;
189 if ('bufferSize' in options)
190 this.options_.bufferSize = options.bufferSize;
191 };
192
193 Connection.prototype.setOptions = function(options) {
194 this.setClientOptions_(options);
195 var serviceOptions = getServiceOptions(options);
196 if ($Object.keys(serviceOptions).length == 0)
197 return true;
198 return this.remoteConnection_.setOptions(serviceOptions).then(
199 function(result) {
200 return !!result.success;
201 }).catch(function() {
202 return false;
203 });
204 };
205
206 Connection.prototype.getControlSignals = function() {
207 return this.remoteConnection_.getControlSignals().then(function(result) {
208 if (!result.signals)
209 throw new Error('Failed to get control signals.');
210 var signals = result.signals;
211 return {
212 dcd: !!signals.dcd,
213 cts: !!signals.cts,
214 ri: !!signals.ri,
215 dsr: !!signals.dsr,
216 };
217 });
218 };
219
220 Connection.prototype.setControlSignals = function(signals) {
221 var controlSignals = {};
222 if ('dtr' in signals) {
223 controlSignals.has_dtr = true;
224 controlSignals.dtr = signals.dtr;
225 }
226 if ('rts' in signals) {
227 controlSignals.has_rts = true;
228 controlSignals.rts = signals.rts;
229 }
230 return this.remoteConnection_.setControlSignals(controlSignals).then(
231 function(result) {
232 return !!result.success;
233 });
234 };
235
236 Connection.prototype.flush = function() {
237 return this.remoteConnection_.flush().then(function(result) {
238 return !!result.success;
239 });
240 };
241
242 Connection.prototype.setPaused = function(paused) {
243 this.paused_ = paused;
244 };
245
246 var connections_ = {};
247 var nextConnectionId_ = 0;
248
249 // Wrap all access to |connections_| through getConnections to avoid adding
250 // any synchronous dependencies on it. This will likely be important when
251 // supporting persistent connections by stashing them.
252 function getConnections() {
253 return Promise.resolve(connections_);
254 }
255
256 function getConnection(id) {
257 return getConnections().then(function(connections) {
258 if (!connections[id])
259 throw new Error ('Serial connection not found.');
260 return connections[id];
261 });
262 }
263
264 function allocateConnectionId() {
265 return Promise.resolve(nextConnectionId_++);
266 }
267
39 return { 268 return {
40 getDevices: getDevices, 269 getDevices: getDevices,
270 createConnection: Connection.create,
271 getConnection: getConnection,
272 getConnections: getConnections,
41 }; 273 };
42 }); 274 });
OLDNEW
« no previous file with comments | « extensions/renderer/resources/serial_custom_bindings.js ('k') | extensions/test/data/serial_unittest.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698