diff options
author | Matt A. Tobin <mattatobin@localhost.localdomain> | 2018-02-02 04:16:08 -0500 |
---|---|---|
committer | Matt A. Tobin <mattatobin@localhost.localdomain> | 2018-02-02 04:16:08 -0500 |
commit | 5f8de423f190bbb79a62f804151bc24824fa32d8 (patch) | |
tree | 10027f336435511475e392454359edea8e25895d /dom/presentation/tests/xpcshell/test_tcp_control_channel.js | |
parent | 49ee0794b5d912db1f95dce6eb52d781dc210db5 (diff) | |
download | UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.gz UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.lz UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.tar.xz UXP-5f8de423f190bbb79a62f804151bc24824fa32d8.zip |
Add m-esr52 at 52.6.0
Diffstat (limited to 'dom/presentation/tests/xpcshell/test_tcp_control_channel.js')
-rw-r--r-- | dom/presentation/tests/xpcshell/test_tcp_control_channel.js | 398 |
1 files changed, 398 insertions, 0 deletions
diff --git a/dom/presentation/tests/xpcshell/test_tcp_control_channel.js b/dom/presentation/tests/xpcshell/test_tcp_control_channel.js new file mode 100644 index 000000000..5f3df584d --- /dev/null +++ b/dom/presentation/tests/xpcshell/test_tcp_control_channel.js @@ -0,0 +1,398 @@ +/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */ +/* Any copyright is dedicated to the Public Domain. + * http://creativecommons.org/publicdomain/zero/1.0/ */ + +'use strict'; + +const { classes: Cc, interfaces: Ci, utils: Cu, results: Cr } = Components; + +Cu.import('resource://gre/modules/XPCOMUtils.jsm'); +Cu.import('resource://gre/modules/Services.jsm'); + +var pcs; + +// Call |run_next_test| if all functions in |names| are called +function makeJointSuccess(names) { + let funcs = {}, successCount = 0; + names.forEach(function(name) { + funcs[name] = function() { + do_print('got expected: ' + name); + if (++successCount === names.length) + run_next_test(); + }; + }); + return funcs; +} + +function TestDescription(aType, aTcpAddress, aTcpPort) { + this.type = aType; + this.tcpAddress = Cc["@mozilla.org/array;1"] + .createInstance(Ci.nsIMutableArray); + for (let address of aTcpAddress) { + let wrapper = Cc["@mozilla.org/supports-cstring;1"] + .createInstance(Ci.nsISupportsCString); + wrapper.data = address; + this.tcpAddress.appendElement(wrapper, false); + } + this.tcpPort = aTcpPort; +} + +TestDescription.prototype = { + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationChannelDescription]), +} + +const CONTROLLER_CONTROL_CHANNEL_PORT = 36777; +const PRESENTER_CONTROL_CHANNEL_PORT = 36888; + +var CLOSE_CONTROL_CHANNEL_REASON = Cr.NS_OK; +var candidate; + +// presenter's presentation channel description +const OFFER_ADDRESS = '192.168.123.123'; +const OFFER_PORT = 123; + +// controller's presentation channel description +const ANSWER_ADDRESS = '192.168.321.321'; +const ANSWER_PORT = 321; + +function loopOfferAnser() { + pcs = Cc["@mozilla.org/presentation/control-service;1"] + .createInstance(Ci.nsIPresentationControlService); + pcs.id = 'controllerID'; + pcs.listener = { + onServerReady: function() { + testPresentationServer(); + } + }; + + // First run with TLS enabled. + pcs.startServer(true, PRESENTER_CONTROL_CHANNEL_PORT); +} + + +function testPresentationServer() { + let yayFuncs = makeJointSuccess(['controllerControlChannelClose', + 'presenterControlChannelClose', + 'controllerControlChannelReconnect', + 'presenterControlChannelReconnect']); + let presenterControlChannel; + + pcs.listener = { + + onSessionRequest: function(deviceInfo, url, presentationId, controlChannel) { + presenterControlChannel = controlChannel; + Assert.equal(deviceInfo.id, pcs.id, 'expected device id'); + Assert.equal(deviceInfo.address, '127.0.0.1', 'expected device address'); + Assert.equal(url, 'http://example.com', 'expected url'); + Assert.equal(presentationId, 'testPresentationId', 'expected presentation id'); + + presenterControlChannel.listener = { + status: 'created', + onOffer: function(aOffer) { + Assert.equal(this.status, 'opened', '1. presenterControlChannel: get offer, send answer'); + this.status = 'onOffer'; + + let offer = aOffer.QueryInterface(Ci.nsIPresentationChannelDescription); + Assert.strictEqual(offer.tcpAddress.queryElementAt(0,Ci.nsISupportsCString).data, + OFFER_ADDRESS, + 'expected offer address array'); + Assert.equal(offer.tcpPort, OFFER_PORT, 'expected offer port'); + try { + let tcpType = Ci.nsIPresentationChannelDescription.TYPE_TCP; + let answer = new TestDescription(tcpType, [ANSWER_ADDRESS], ANSWER_PORT); + presenterControlChannel.sendAnswer(answer); + } catch (e) { + Assert.ok(false, 'sending answer fails' + e); + } + }, + onAnswer: function(aAnswer) { + Assert.ok(false, 'get answer'); + }, + onIceCandidate: function(aCandidate) { + Assert.ok(true, '3. presenterControlChannel: get ice candidate, close channel'); + let recvCandidate = JSON.parse(aCandidate); + for (let key in recvCandidate) { + if (typeof(recvCandidate[key]) !== "function") { + Assert.equal(recvCandidate[key], candidate[key], "key " + key + " should match."); + } + } + presenterControlChannel.disconnect(CLOSE_CONTROL_CHANNEL_REASON); + }, + notifyConnected: function() { + Assert.equal(this.status, 'created', '0. presenterControlChannel: opened'); + this.status = 'opened'; + }, + notifyDisconnected: function(aReason) { + Assert.equal(this.status, 'onOffer', '4. presenterControlChannel: closed'); + Assert.equal(aReason, CLOSE_CONTROL_CHANNEL_REASON, 'presenterControlChannel notify closed'); + this.status = 'closed'; + yayFuncs.controllerControlChannelClose(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; + }, + onReconnectRequest: function(deviceInfo, url, presentationId, controlChannel) { + Assert.equal(url, 'http://example.com', 'expected url'); + Assert.equal(presentationId, 'testPresentationId', 'expected presentation id'); + yayFuncs.presenterControlChannelReconnect(); + }, + + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlServerListener]), + }; + + let presenterDeviceInfo = { + id: 'presentatorID', + address: '127.0.0.1', + port: PRESENTER_CONTROL_CHANNEL_PORT, + certFingerprint: pcs.certFingerprint, + QueryInterface: XPCOMUtils.generateQI([Ci.nsITCPDeviceInfo]), + }; + + let controllerControlChannel = pcs.connect(presenterDeviceInfo); + + controllerControlChannel.listener = { + status: 'created', + onOffer: function(offer) { + Assert.ok(false, 'get offer'); + }, + onAnswer: function(aAnswer) { + Assert.equal(this.status, 'opened', '2. controllerControlChannel: get answer, send ICE candidate'); + + let answer = aAnswer.QueryInterface(Ci.nsIPresentationChannelDescription); + Assert.strictEqual(answer.tcpAddress.queryElementAt(0,Ci.nsISupportsCString).data, + ANSWER_ADDRESS, + 'expected answer address array'); + Assert.equal(answer.tcpPort, ANSWER_PORT, 'expected answer port'); + candidate = { + candidate: "1 1 UDP 1 127.0.0.1 34567 type host", + sdpMid: "helloworld", + sdpMLineIndex: 1 + }; + controllerControlChannel.sendIceCandidate(JSON.stringify(candidate)); + }, + onIceCandidate: function(aCandidate) { + Assert.ok(false, 'get ICE candidate'); + }, + notifyConnected: function() { + Assert.equal(this.status, 'created', '0. controllerControlChannel: opened, send offer'); + controllerControlChannel.launch('testPresentationId', 'http://example.com'); + this.status = 'opened'; + try { + let tcpType = Ci.nsIPresentationChannelDescription.TYPE_TCP; + let offer = new TestDescription(tcpType, [OFFER_ADDRESS], OFFER_PORT) + controllerControlChannel.sendOffer(offer); + } catch (e) { + Assert.ok(false, 'sending offer fails:' + e); + } + }, + notifyDisconnected: function(aReason) { + this.status = 'closed'; + Assert.equal(aReason, CLOSE_CONTROL_CHANNEL_REASON, '4. controllerControlChannel notify closed'); + yayFuncs.presenterControlChannelClose(); + + let reconnectControllerControlChannel = pcs.connect(presenterDeviceInfo); + reconnectControllerControlChannel.listener = { + notifyConnected: function() { + reconnectControllerControlChannel.reconnect('testPresentationId', 'http://example.com'); + }, + notifyReconnected: function() { + yayFuncs.controllerControlChannelReconnect(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; +} + +function terminateRequest() { + let yayFuncs = makeJointSuccess(['controllerControlChannelConnected', + 'controllerControlChannelDisconnected', + 'presenterControlChannelDisconnected', + 'terminatedByController', + 'terminatedByReceiver']); + let controllerControlChannel; + let terminatePhase = 'controller'; + + pcs.listener = { + onTerminateRequest: function(deviceInfo, presentationId, controlChannel, isFromReceiver) { + Assert.equal(deviceInfo.address, '127.0.0.1', 'expected device address'); + Assert.equal(presentationId, 'testPresentationId', 'expected presentation id'); + controlChannel.terminate(presentationId); // Reply terminate ack. + + if (terminatePhase === 'controller') { + controllerControlChannel = controlChannel; + Assert.equal(deviceInfo.id, pcs.id, 'expected controller device id'); + Assert.equal(isFromReceiver, false, 'expected request from controller'); + yayFuncs.terminatedByController(); + + controllerControlChannel.listener = { + notifyConnected: function() { + Assert.ok(true, 'control channel notify connected'); + yayFuncs.controllerControlChannelConnected(); + + terminatePhase = 'receiver'; + controllerControlChannel.terminate('testPresentationId'); + }, + notifyDisconnected: function(aReason) { + Assert.equal(aReason, CLOSE_CONTROL_CHANNEL_REASON, 'controllerControlChannel notify disconncted'); + yayFuncs.controllerControlChannelDisconnected(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; + } else { + Assert.equal(deviceInfo.id, presenterDeviceInfo.id, 'expected presenter device id'); + Assert.equal(isFromReceiver, true, 'expected request from receiver'); + yayFuncs.terminatedByReceiver(); + presenterControlChannel.disconnect(CLOSE_CONTROL_CHANNEL_REASON); + } + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsITCPPresentationServerListener]), + }; + + let presenterDeviceInfo = { + id: 'presentatorID', + address: '127.0.0.1', + port: PRESENTER_CONTROL_CHANNEL_PORT, + certFingerprint: pcs.certFingerprint, + QueryInterface: XPCOMUtils.generateQI([Ci.nsITCPDeviceInfo]), + }; + + let presenterControlChannel = pcs.connect(presenterDeviceInfo); + + presenterControlChannel.listener = { + notifyConnected: function() { + presenterControlChannel.terminate('testPresentationId'); + }, + notifyDisconnected: function(aReason) { + Assert.equal(aReason, CLOSE_CONTROL_CHANNEL_REASON, '4. presenterControlChannel notify disconnected'); + yayFuncs.presenterControlChannelDisconnected(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; +} + +function terminateRequestAbnormal() { + let yayFuncs = makeJointSuccess(['controllerControlChannelConnected', + 'controllerControlChannelDisconnected', + 'presenterControlChannelDisconnected']); + let controllerControlChannel; + + pcs.listener = { + onTerminateRequest: function(deviceInfo, presentationId, controlChannel, isFromReceiver) { + Assert.equal(deviceInfo.id, pcs.id, 'expected controller device id'); + Assert.equal(deviceInfo.address, '127.0.0.1', 'expected device address'); + Assert.equal(presentationId, 'testPresentationId', 'expected presentation id'); + Assert.equal(isFromReceiver, false, 'expected request from controller'); + controlChannel.terminate('unmatched-presentationId'); // Reply abnormal terminate ack. + + controllerControlChannel = controlChannel; + + controllerControlChannel.listener = { + notifyConnected: function() { + Assert.ok(true, 'control channel notify connected'); + yayFuncs.controllerControlChannelConnected(); + }, + notifyDisconnected: function(aReason) { + Assert.equal(aReason, Cr.NS_ERROR_FAILURE, 'controllerControlChannel notify disconncted with error'); + yayFuncs.controllerControlChannelDisconnected(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsITCPPresentationServerListener]), + }; + + let presenterDeviceInfo = { + id: 'presentatorID', + address: '127.0.0.1', + port: PRESENTER_CONTROL_CHANNEL_PORT, + certFingerprint: pcs.certFingerprint, + QueryInterface: XPCOMUtils.generateQI([Ci.nsITCPDeviceInfo]), + }; + + let presenterControlChannel = pcs.connect(presenterDeviceInfo); + + presenterControlChannel.listener = { + notifyConnected: function() { + presenterControlChannel.terminate('testPresentationId'); + }, + notifyDisconnected: function(aReason) { + Assert.equal(aReason, Cr.NS_ERROR_FAILURE, '4. presenterControlChannel notify disconnected with error'); + yayFuncs.presenterControlChannelDisconnected(); + }, + QueryInterface: XPCOMUtils.generateQI([Ci.nsIPresentationControlChannelListener]), + }; +} + +function setOffline() { + pcs.listener = { + onServerReady: function(aPort, aCertFingerprint) { + Assert.notEqual(aPort, 0, 'TCPPresentationServer port changed and the port should be valid'); + pcs.close(); + run_next_test(); + }, + }; + + // Let the server socket restart automatically. + Services.io.offline = true; + Services.io.offline = false; +} + +function oneMoreLoop() { + try { + pcs.listener = { + onServerReady: function() { + testPresentationServer(); + } + }; + + // Second run with TLS disabled. + pcs.startServer(false, PRESENTER_CONTROL_CHANNEL_PORT); + } catch (e) { + Assert.ok(false, 'TCP presentation init fail:' + e); + run_next_test(); + } +} + + +function shutdown() +{ + pcs.listener = { + onServerReady: function(aPort, aCertFingerprint) { + Assert.ok(false, 'TCPPresentationServer port changed'); + }, + }; + pcs.close(); + Assert.equal(pcs.port, 0, "TCPPresentationServer closed"); + run_next_test(); +} + +// Test manually close control channel with NS_ERROR_FAILURE +function changeCloseReason() { + CLOSE_CONTROL_CHANNEL_REASON = Cr.NS_ERROR_FAILURE; + run_next_test(); +} + +add_test(loopOfferAnser); +add_test(terminateRequest); +add_test(terminateRequestAbnormal); +add_test(setOffline); +add_test(changeCloseReason); +add_test(oneMoreLoop); +add_test(shutdown); + +function run_test() { + // Need profile dir to store the key / cert + do_get_profile(); + // Ensure PSM is initialized + Cc["@mozilla.org/psm;1"].getService(Ci.nsISupports); + + Services.prefs.setBoolPref("dom.presentation.tcp_server.debug", true); + + do_register_cleanup(() => { + Services.prefs.clearUserPref("dom.presentation.tcp_server.debug"); + }); + + run_next_test(); +} |