tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

test_peerConnection_RTCIceTransport.html (8117B)


      1 <!DOCTYPE HTML>
      2 <html>
      3 <head>
      4  <script type="application/javascript" src="pc.js"></script>
      5  <script type="application/javascript" src="iceTestUtils.js"></script>
      6  <script type="application/javascript" src="helpers_from_wpt/sdp.js"></script></head>
      7 <body>
      8 <pre id="test">
      9 <script type="application/javascript">
     10  createHTML({
     11    bug: "1811912",
     12    title: "Tests for RTCIceTransport"
     13  });
     14 
     15  const tests = [
     16    async function iceRestartNewGathersFirst() {
     17      await pushPrefs(
     18          ['media.peerconnection.nat_simulator.block_udp', true]);
     19      // We block UDP, and configure a fake UDP STUN server; this should result
     20      // in gathering taking a while, because we'll just be sending UDP packets
     21      // off to be eaten by the NAT simulator.
     22      const pc1 = new RTCPeerConnection({ iceServers: [{
     23        urls: ['stun:192.168.1.1']
     24      }] });
     25      const pc2 = new RTCPeerConnection();
     26 
     27      const transceiver = pc1.addTransceiver('audio');
     28      await pc1.setLocalDescription();
     29      const {iceTransport} = transceiver.sender.transport;
     30      is(await nextGatheringState(iceTransport), 'gathering');
     31 
     32      await pc2.setRemoteDescription(pc1.localDescription);
     33      await pc2.setLocalDescription();
     34      await pc1.setRemoteDescription(pc2.localDescription);
     35 
     36      pc1.setConfiguration({iceServers: []});
     37      await pc1.setLocalDescription(await pc1.createOffer({iceRestart: true}));
     38      is(iceTransport.gatheringState, 'gathering');
     39 
     40      const gatheringDonePromise = nextGatheringState(iceTransport);
     41      // The empty candidate should fire for the new underlying transport
     42      // (created by the ICE restart), but there should be no gathering state
     43      // change yet. (Spec says that the RTCIceTransport object is the same
     44      // here, even thougb there's actually a new transport)
     45      await emptyCandidate(pc1);
     46 
     47      // New transport is done gathering, old should not be.
     48      let result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 100))]);
     49      is(result, undefined, 'Gathering should not complete yet');
     50 
     51      await pc2.setRemoteDescription(pc1.localDescription);
     52      await pc2.setLocalDescription();
     53      await pc1.setRemoteDescription(pc2.localDescription);
     54 
     55      // We might or might not have an empty candidate for the generation we
     56      // just abandoned, depending on how the spec shakes out.
     57 
     58      // Completing negotiation should result in a transition to complete very
     59      // quickly
     60      result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 100))]);
     61      is(result, 'complete', 'Gathering should complete soon after the ICE restart is complete');
     62      pc1.close();
     63      pc2.close();
     64      await SpecialPowers.popPrefEnv();
     65    },
     66 
     67    async function iceRestartNewGathersFirstThenRollback() {
     68      await pushPrefs(
     69          ['media.peerconnection.nat_simulator.block_udp', true]);
     70      // This should result in gathering taking a while
     71      const pc1 = new RTCPeerConnection({ iceServers: [{
     72        urls: ['stun:192.168.1.1']
     73      }] });
     74      const pc2 = new RTCPeerConnection();
     75 
     76      const transceiver = pc1.addTransceiver('audio');
     77      await pc1.setLocalDescription();
     78      const {iceTransport} = transceiver.sender.transport;
     79      is(await nextGatheringState(iceTransport), 'gathering');
     80 
     81      await pc2.setRemoteDescription(pc1.localDescription);
     82      await pc2.setLocalDescription();
     83      await pc1.setRemoteDescription(pc2.localDescription);
     84 
     85      pc1.setConfiguration({iceServers: []});
     86      await pc1.setLocalDescription(await pc1.createOffer({iceRestart: true}));
     87      is(iceTransport.gatheringState, 'gathering');
     88 
     89      const gatheringDonePromise = nextGatheringState(iceTransport);
     90      // This should fire for the new transport, but there should be no
     91      // gathering state change yet.
     92      await emptyCandidate(pc1);
     93 
     94      // Rollback should abandon the new transport, and we should remain in
     95      // 'gathering'
     96      await pc1.setLocalDescription({type: 'rollback', sdp: ''});
     97 
     98      let result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 1000))]);
     99      is(result, undefined, 'Gathering should not complete');
    100      pc1.close();
    101      pc2.close();
    102      await SpecialPowers.popPrefEnv();
    103    },
    104 
    105    async function iceRestartOldGathersFirst() {
    106      await pushPrefs(
    107          ['media.peerconnection.nat_simulator.block_udp', true]);
    108      const pc1 = new RTCPeerConnection();
    109      const pc2 = new RTCPeerConnection();
    110 
    111      const transceiver = pc1.addTransceiver('audio');
    112      await pc1.setLocalDescription();
    113      const {iceTransport} = transceiver.sender.transport;
    114      is(await nextGatheringState(iceTransport), 'gathering');
    115      is(await nextGatheringState(iceTransport), 'complete');
    116 
    117      await pc2.setRemoteDescription(pc1.localDescription);
    118      await pc2.setLocalDescription();
    119      await pc1.setRemoteDescription(pc2.localDescription);
    120 
    121      // This should result in gathering taking a while
    122      pc1.setConfiguration({ iceServers: [{
    123        urls: ['stun:192.168.1.1']
    124      }] });
    125      await pc1.setLocalDescription(await pc1.createOffer({iceRestart: true}));
    126 
    127      is(await nextGatheringState(iceTransport), 'gathering');
    128 
    129      const gatheringDonePromise = nextGatheringState(iceTransport);
    130      let result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 100))]);
    131      is(result, undefined, 'Gathering should not complete');
    132 
    133      await pc2.setRemoteDescription(pc1.localDescription);
    134      await pc2.setLocalDescription();
    135      await pc1.setRemoteDescription(pc2.localDescription);
    136 
    137      result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 100))]);
    138      is(result, undefined, 'Gathering should not complete');
    139      pc1.close();
    140      pc2.close();
    141      await SpecialPowers.popPrefEnv();
    142    },
    143 
    144    async function iceRestartOldGathersFirstThenRollback() {
    145      await pushPrefs(
    146          ['media.peerconnection.nat_simulator.block_udp', true]);
    147      const pc1 = new RTCPeerConnection();
    148      const pc2 = new RTCPeerConnection();
    149 
    150      const transceiver = pc1.addTransceiver('audio');
    151      await pc1.setLocalDescription();
    152      const {iceTransport} = transceiver.sender.transport;
    153      is(await nextGatheringState(iceTransport), 'gathering');
    154      is(await nextGatheringState(iceTransport), 'complete');
    155 
    156      await pc2.setRemoteDescription(pc1.localDescription);
    157      await pc2.setLocalDescription();
    158      await pc1.setRemoteDescription(pc2.localDescription);
    159 
    160      // This should result in gathering taking a while
    161      pc1.setConfiguration({ iceServers: [{
    162        urls: ['stun:192.168.1.1']
    163      }] });
    164      await pc1.setLocalDescription(await pc1.createOffer({iceRestart: true}));
    165 
    166      is(await nextGatheringState(iceTransport), 'gathering', 'ICE restart should put us back in gathering');
    167 
    168      const gatheringDonePromise = nextGatheringState(iceTransport);
    169      is(iceTransport.gatheringState, 'gathering');
    170      await pc1.setLocalDescription({type: 'rollback', sdp: ''});
    171      const result = await Promise.race([gatheringDonePromise, new Promise(r => setTimeout(r, 200))]);
    172      is(iceTransport.gatheringState, 'complete', 'Rollback of ICE restart to transport that was already done gathering should result in a transition back to "complete"');
    173      is(result, 'complete', 'Rollback that brings the gathering state back to complete should result in a gatheringstatechange event');
    174      pc1.close();
    175      pc2.close();
    176      await SpecialPowers.popPrefEnv();
    177    },
    178  ];
    179 
    180  runNetworkTest(async () => {
    181    for (const test of tests) {
    182      info(`Running test: ${test.name}`);
    183      try {
    184        await test();
    185      } catch (e) {
    186        ok(false, `Caught ${e.name}: ${e.message} ${e.stack}`);
    187      }
    188      info(`Done running test: ${test.name}`);
    189      // Make sure we don't build up a pile of GC work, and also get PCImpl to
    190      // print their timecards.
    191      await new Promise(r => SpecialPowers.exactGC(r));
    192    }
    193  }, { useIceServer: true });
    194 </script>
    195 </pre>
    196 </body>
    197 </html>