Bug 1395853 - Refactor checkReceivingToneFrom to take a cancel promise. r?jib draft
authorAndreas Pehrson <pehrsons@mozilla.com>
Wed, 06 Sep 2017 18:33:03 +0200
changeset 672728 d5011b6e51d0fb4e206b9de6283ba0ac971850a2
parent 672727 3e3b2db786a10f5a864ec80bb104d5d8e45f76c9
child 672729 3c80ae4d75b483ce1bd21d1d82d397633355d71d
child 673357 38a53a02215131e85f8add9f10bb35f2aa8f1b7d
push id82350
push userbmo:apehrson@mozilla.com
push dateFri, 29 Sep 2017 17:21:28 +0000
reviewersjib
bugs1395853
milestone58.0a1
Bug 1395853 - Refactor checkReceivingToneFrom to take a cancel promise. r?jib MozReview-Commit-ID: 456FVAlZkXJ
dom/media/tests/mochitest/pc.js
--- a/dom/media/tests/mochitest/pc.js
+++ b/dom/media/tests/mochitest/pc.js
@@ -1526,54 +1526,59 @@ PeerConnectionWrapper.prototype = {
    * audio data in the frequency domain.
    *
    * @param {object} from
    *        A PeerConnectionWrapper whose audio RTPSender we use as source for
    *        the audio flow check.
    * @returns {Promise}
    *        A promise that resolves when we're receiving the tone from |from|.
    */
-  checkReceivingToneFrom : function(audiocontext, from) {
-    var inputElem = from.localMediaElements[0];
+  checkReceivingToneFrom : async function(audiocontext, from,
+      cancel = wait(60000, new Error("Tone not detected"))) {
+    let inputElem = from.localMediaElements[0];
 
     // As input we use the stream of |from|'s first available audio sender.
-    var inputSenderTracks = from._pc.getSenders().map(sn => sn.track);
-    var inputAudioStream = from._pc.getLocalStreams()
+    let inputSenderTracks = from._pc.getSenders().map(sn => sn.track);
+    let inputAudioStream = from._pc.getLocalStreams()
       .find(s => inputSenderTracks.some(t => t.kind == "audio" && s.getTrackById(t.id)));
-    var inputAnalyser = new AudioStreamAnalyser(audiocontext, inputAudioStream);
+    let inputAnalyser = new AudioStreamAnalyser(audiocontext, inputAudioStream);
 
     // It would have been nice to have a working getReceivers() here, but until
     // we do, let's use what remote streams we have.
-    var outputAudioStream = this._pc.getRemoteStreams()
+    let outputAudioStream = this._pc.getRemoteStreams()
       .find(s => s.getAudioTracks().length > 0);
-    var outputAnalyser = new AudioStreamAnalyser(audiocontext, outputAudioStream);
+    let outputAnalyser = new AudioStreamAnalyser(audiocontext, outputAudioStream);
 
-    var maxWithIndex = (a, b, i) => (b >= a.value) ? { value: b, index: i } : a;
-    var initial = { value: -1, index: -1 };
+    let error = null;
+    cancel.then(e => error = e);
 
-    return new Promise((resolve, reject) => inputElem.ontimeupdate = () => {
-      var inputData = inputAnalyser.getByteFrequencyData();
-      var outputData = outputAnalyser.getByteFrequencyData();
+    let indexOfMax = data => 
+      data.reduce((max, val, i) => (val >= data[max]) ? i : max, 0);
 
-      var inputMax = inputData.reduce(maxWithIndex, initial);
-      var outputMax = outputData.reduce(maxWithIndex, initial);
-      info("Comparing maxima; input[" + inputMax.index + "] = " + inputMax.value +
-           ", output[" + outputMax.index + "] = " + outputMax.value);
-      if (!inputMax.value || !outputMax.value) {
-        return;
+    await outputAnalyser.waitForAnalysisSuccess(() => {
+      if (error) {
+        throw error;
       }
 
-      // When the input and output maxima are within reasonable distance
-      // from each other, we can be sure that the input tone has made it
-      // through the peer connection.
-      if (Math.abs(inputMax.index - outputMax.index) < 10) {
-        ok(true, "input and output audio data matches");
-        inputElem.ontimeupdate = null;
-        resolve();
+      let inputData = inputAnalyser.getByteFrequencyData();
+      let outputData = outputAnalyser.getByteFrequencyData();
+
+      let inputMax = indexOfMax(inputData);
+      let outputMax = indexOfMax(outputData);
+      info(`Comparing maxima; input[${inputMax}] = ${inputData[inputMax]},`
+        + ` output[${outputMax}] = ${outputData[outputMax]}`);
+      if (!inputData[inputMax] || !outputData[outputMax]) {
+        return false;
       }
+
+      // When the input and output maxima are within reasonable distance (2% of
+      // total length, which means ~10 for length 512) from each other, we can
+      // be sure that the input tone has made it through the peer connection.
+      info(`input data length: ${inputData.length}`);
+      return Math.abs(inputMax - outputMax) < (inputData.length * 0.02);
     });
   },
 
   /**
    * Get stats from the "legacy" getStats callback interface
    */
   getStatsLegacy : function(selector, onSuccess, onFail) {
     let wrapper = stats => {