-
Notifications
You must be signed in to change notification settings - Fork 6
/
index.html
707 lines (695 loc) · 30.3 KB
/
index.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
<!DOCTYPE html>
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<link href="includes/style.css" rel="stylesheet">
<title>QUIC API for Peer-to-peer Connections</title>
<script class="remove" src="https://www.w3.org/Tools/respec/respec-w3c"></script>
<script src="includes/respec-config.js" class="remove"></script>
</head>
<body>
<section id="abstract">
<p>This document defines a set of ECMAScript APIs in WebIDL to allow data to be sent
and received from another browser or device implementing the QUIC protocol.
The specification for multiplexing of QUIC with STUN/TURN/ZRTP/DTLS/RTP/RTCP
[[RFC9443]] was developed within the IETF AVTCORE Working Group.</p>
</section>
<section id="sotd">
</section>
<section class="informative" id="intro">
<h2>Introduction</h2>
<p>
This specification extends the WebRTC [[WEBRTC]], ORTC [[ORTC]] and WebTransport
[[WEBTRANSPORT]] APIs to enable peer-to-peer operation using QUIC [[RFC9000]].
This specification supports the exchange of arbitrary data with remote peers using
NAT-traversal technologies such as ICE, STUN, and TURN. As specified in [[RFC9443]],
QUIC can be multiplexed on the same port as RTP, RTCP, DTLS, STUN and TURN, allowing
the API defined in this specification to be utilized along with the functionality
defined in [[WEBRTC]] and [[ORTC]] including communication using audio/video media
and SCTP data channels.
</p>
<p>
This specification defines an interface to QUIC streams [[RFC9000]] as well as
datagrams [[RFC9221]]. By utilizing a QUIC stream per message, it is possible
to implement support for message-based communications (such as {{RTCDataChannel}})
on top.
</p>
<p class="note">This specification extends the WebTransport API [[WEBTRANSPORT]]
under development within the W3C WebTransport WG.</p>
</section>
<section id="conformance">
<p>
Conformance requirements phrased as algorithms or specific steps may be
implemented in any manner, so long as the end result is equivalent. (In
particular, the algorithms defined in this specification are intended
to be easy to follow, and not intended to be performant.)
</p>
<p>
Implementations that use ECMAScript to implement the APIs defined in
this specification MUST implement them in a manner consistent with the
ECMAScript Bindings defined in the Web IDL specification [[!WEBIDL]],
as this specification uses that specification and terminology.
</p>
</section>
<section>
<h2>Terminology</h2>
<p>
The {{EventHandler}} interface, representing a callback used for event
handlers, is defined in [[!HTML]].
</p>
<p>
The concepts [= queue a task =] and [= networking task source =] are
defined in [[!HTML]].
</p>
<p>
The concept [= fire an event =] is defined in [[!DOM]].
</p>
<p>
The terms [= event =], [= event handlers =] and [= event handler event
types =] are defined in [[!HTML]].
</p>
<p>
{{Performance.timeOrigin}} and {{Performance.now()}} are defined in
[[!hr-time]].
</p>
<p>
The terms <dfn class=fixme data-cite="HTML/structured-data.html#serializable-objects">serializable objects</dfn>,
[= serialization steps =], and [= deserialization steps =] are defined in [[!HTML]].
</p>
<p>
When referring to exceptions, the terms [= exception/throw =] and
[= exception/created =] are defined in [[!WEBIDL]].
</p>
<p>
The callback {{VoidFunction}} is defined in [[!WEBIDL]].
</p>
<p>
The term "throw" is used as specified in [[!INFRA]]: it terminates the
current processing steps.
</p>
<p>
The terms <dfn data-lt="fulfill|fulfillment">fulfilled</dfn>,
<dfn data-lt="reject|rejection|rejecting">rejected</dfn>, <dfn data-lt=
"resolve|resolves">resolved</dfn>, and
<dfn>settled</dfn> used in the context of Promises are defined in
[[!ECMASCRIPT-6.0]].
</p>
<p>
<dfn>WebTransport</dfn> is defined in [[!WEBTRANSPORT]] Section 5.
</p>
<p>
<dfn>RTCIceTransport</dfn> is defined in [[!WEBRTC]] Section 5.6 and [[!ORTC]] Section 3.
</p>
<p>
<dfn>RTCCertificate</dfn> is defined in [[!WEBRTC]] Section 4.9 and [[!ORTC]] Section 15.
</p>
<p>
<dfn>RTCDtlsFingerprint</dfn> is defined in [[!WEBRTC]] Section 5.5.2 and [[!ORTC]] Section 4.5.
</p>
<p>
<dfn data-dfn-for="RTCQuicTransport">[[\State]]</dfn> is defined in [[!WEBTRANSPORT]] Section 5.1.
</p>
</section>
<section id="rtcquictransport*">
<h2><dfn>RTCQuicTransport</dfn> Interface</h2>
<p>
The <code>RTCQuicTransport</code> interface extends the <code><a>WebTransport</a></code> interface
to support peer-to-peer use cases, by adding information relating to use of a
QUIC transport with an ICE transport.
</p>
<section id="rtcquictransport-operation*">
<h3>Operation</h3>
<p>
A <code><a>RTCQuicTransport</a></code> instance is constructed
using an <code><a>RTCIceTransport</a></code> and an optional sequence of
<code><a>RTCCertificate</a></code> objects. A
<code><a>RTCQuicTransport</a></code> object whose {{RTCQuicTransport/[[State]]}} internal
slot is <code>"closed"</code> or <code>"failed"</code> can be
garbage-collected when it is no longer referenced.
</p>
<p>
The QUIC negotiation occurs between transport endpoints determined via ICE.
Multiplexing of QUIC with STUN, TURN, DTLS, RTP and RTCP is defined in [[RFC9443]].
</p>
<p>
A newly constructed <code><a>RTCQuicTransport</a></code> <em class="rfc2119"
title="MUST">MUST</em> listen and respond to incoming QUIC packets before
<code>start()</code> is called. However, to complete the negotiation it is
necessary to verify the remote fingerprint by computing fingerprints for
the selected remote certificate using the digest algorithms provided
in <code><var>remoteParameters</var>.fingerprints[].algorithm</code>. If a
calculated fingerprint and algorithm matches a fingerprint and algorithm
included in <code><var>remoteParameters</var>.fingerprints[]</code>,
the remote fingerprint is verified. After the QUIC handshake exchange
completes (but before the remote fingerprint is verified) incoming media packets
may be received. A modest buffer <em class="rfc2119" title="MUST">MUST</em> be
provided to avoid loss of media prior to remote fingerprint validation (which can
begin after <code>start()</code> is called).
</p>
</section>
<section id="rtcquictransport-interface-definition*">
<h3>Interface Definition</h3>
<div>
<pre class="idl">
[Exposed=Window]
interface RTCQuicTransport : WebTransport {
constructor(<code><a>RTCIceTransport</a></code> transport, optional sequence<<code><a>RTCCertificate</a></code>> certificates);
readonly attribute <code><a>RTCIceTransport</a></code> transport;
RTCQuicParameters getLocalParameters ();
RTCQuicParameters? getRemoteParameters ();
sequence<<code><a>RTCCertificate</a></code>> getCertificates ();
sequence<ArrayBuffer> getRemoteCertificates ();
undefined start (RTCQuicParameters remoteParameters);
};</pre>
<section>
<h2>Constructors</h2>
<p>
When <code><a>RTCQuicTransport</a>.constructor()</code> is invoked,
the user agent <em class="rfc2119" title="MUST">MUST</em> run the
following steps:
</p>
<ol>
<li>
Let <var>transport</var> be the first argument.
</li>
<li>
If <var>transport</var>'s <code>state</code> attribute has the
value <code>"closed"</code> [= exception/throw =] an
<code>InvalidStateError</code> and abort these steps.
<li>
If <var>transport</var> has been used to construct another
<code><a>RTCQuicTransport</a></code> whose {{RTCQuicTransport/[[State]]}} internal
slot is not <code>"closed"</code>, [= exception/throw =] an
<code>InvalidStateError</code> and abort these steps.
</li>
<li>
Let <var>certificates</var> be the second argument if provided,
<code>null</code> otherwise.
</li>
<li>
If <var>certificates</var> is non-null and is non-empty, check that the
<code>expires</code> attribute of each <code><a>RTCCertificate</a></code>
object is in the future. If a certificate has expired, [= exception/throw =]
an <code>InvalidAccessError</code> and abort these steps.
</li>
<li>
Let <var>quictransport</var> be a newly constructed
<code><a>RTCQuicTransport</a></code> object.
</li>
<li>
Let <var>quictransport</var> have a {{RTCQuicTransport/[[State]]}}
internal slot, initialized to <code>"connecting"</code>.
</li>
<li>
Let <var>quictransport</var> have a
<dfn data-dfn-for="RTCQuicTransport">[[\Certificates]]</dfn>
internal slot.
</li>
<li>
If <var>certificates</var> is non-null and is non-empty,
initialize the {{RTCQuicTransport/[[Certificates]]}} internal slot to
<var>certificates</var>.
</li>
<li>
If <var>certificates</var> is <code>null</code> or is empty,
generate a certificate using the default key generation algorithm
and store it in the {{RTCQuicTransport/[[Certificates]]}} internal slot.
</li>
<li>
Return <var>quictransport</var>.
</li>
</ol>
<dl data-link-for="RTCQuicTransport" data-dfn-for="RTCQuicTransport" class=
"constructors">
<dt><code><a>RTCQuicTransport</a></code></dt>
<dd>
<table class="parameters">
<tbody>
<tr>
<th>Parameter</th>
<th>Type</th>
<th>Nullable</th>
<th>Optional</th>
<th>Description</th>
</tr>
<tr>
<td class="prmName">transport</td>
<td class="prmType"><code><a>RTCIceTransport</code></a></td>
<td class="prmNullFalse"><span role="img" aria-label=
"False">✘</span></td>
<td class="prmOptFalse"><span role="img" aria-label=
"False">✘</span></td>
<td class="prmDesc"></td>
</tr>
<tr>
<td class="prmName">certificates</td>
<td class="prmType">
<code>sequence</code><<code><a>RTCCertificate</a></code>></td>
<td class="prmNullFalse"><span role="img" aria-label=
"False">✘</span></td>
<td class="prmOptTrue"><span role="img" aria-label=
"True">✔</span></td>
<td class="prmDesc"></td>
</tr>
</tbody>
</table>
</dd>
</dl>
</section>
<section>
<h2>Attributes</h2>
<dl data-link-for="RTCQuicTransport" data-dfn-for="RTCQuicTransport" class=
"attributes">
<dt><dfn><code>transport</code></dfn> of type <span class=
"idlAttrType"><code><a>RTCIceTransport</code></a></span>, readonly</dt>
<dd>
<p>The associated <code><a>RTCIceTransport</code></a> instance.
When the <code><a>RTCIceTransport</code></a>'s <code>state</code>
attribute changes values, the user agent <em class="rfc2119" title="MUST">MUST</em>
run the following steps:</p>
<ol>
<li>
Let <var>transport</var> be the associated
{{RTCIceTransport}} instance.
</li>
<li>
If <var>transport</var>'s <code>state</code> attribute is not
<code>"closed"</code>, abort these steps.
</li>
<li>
Let <var>quictransport</var> be the <code><a>RTCQuicTransport</a></code>.
</li>
<li>
Set <var>quictransport</var>'s {{RTCQuicTransport/[[State]]}}
internal slot to <code>"closed"</code>.
</li>
</ol>
</dd>
</dl>
</section>
<section>
<h2>Methods</h2>
<dl data-link-for="RTCQuicTransport" data-dfn-for="RTCQuicTransport" class=
"methods">
<dt><code>getLocalParameters</code></dt>
<dd>
<p>
<dfn>getLocalParameters()</dfn> obtains the QUIC parameters of
the local <code><a>RTCQuicTransport</a></code> upon construction.
If multiple certificates were provided in the constructor, then
multiple fingerprints will be returned, one for each certificate.
<code>getLocalParameters().role</code> always returns the default
role of a newly constructed <code><a>RTCQuicTransport</a></code>;
for a browser this will be <code>auto</code>.
</p>
<div>
<em>No parameters.</em>
</div>
<div>
<em>Return type:</em> <code><a>RTCQuicParameters</a></code>
</div>
</dd>
<dt><code>getRemoteParameters</code></dt>
<dd>
<p>
<dfn>getRemoteParameters()</dfn> obtains
the remote QUIC parameters passed in the
<code>start()</code> method. Prior to calling
<code>start()</code>, null is returned.
</p>
<div>
<em>No parameters.</em>
</div>
<div>
<em>Return type:</em> <code><a>RTCQuicParameters</a></code>, nullable
</div>
</dd>
<dt><code>getCertificates</code></dt>
<dd>
<p><dfn>getCertificates()</dfn> returns the value of the <code><a>RTCQuicTransport</a></code>'s
{{RTCQuicTransport/[[Certificates]]}} internal slot.</p>
<div>
<em>No parameters.</em>
</div>
<div>
<em>Return type:</em> <code>sequence<RTCCertificate></code>
</div>
</dd>
<dt><code>getRemoteCertificates</code></dt>
<dd>
<p>
<dfn>getRemoteCertificates()</dfn> returns the certificate chain in use by the remote side, with each
certificate encoded in binary Distinguished Encoding Rules (DER) [[!X690]].
<code><a>getRemoteCertificates()</a></code> returns an empty list prior to
selection of the remote certificate, which is completed once <var>quictransport</var>'s
{{RTCQuicTransport/[[State]]}} internal slot transitions to <code>"connected"</code>.
</p>
<div>
<em>No parameters.</em>
</div>
<div>
<em>Return type:</em> <code>sequence<ArrayBuffer></code>
</div>
</dd>
<dt><dfn><code>start</code></dfn></dt>
<dd>
<p>
Start QUIC transport negotiation with the parameters of the remote QUIC
transport, including verification of the remote fingerprint.
During connection establishment, use of this API must be indicated
by selecting the ALPN token "q2q" in the crypto handshake.
<!-- TODO: register "q2q" with IANA. -->
</p>
<p>
Only a single QUIC transport can be multiplexed over an ICE transport.
Therefore if a <code><a>RTCQuicTransport</a></code> object
<var>quicTransportB</var> is constructed with an
{{RTCIceTransport}} object <var>iceTransport</var>
previously used to construct another <code><a>RTCQuicTransport</a></code>
object <var>quicTransportA</var>, then if
<code>quicTransportB.start()</code> is called prior to having called
<code>quicTransportA.stop()</code>, then [= exception/throw =] an
<code>InvalidStateError</code>.</p>
<p>
If <code>start</code> is called after a previous <code>start</code>
call, or if <var>quictransport</var>'s {{RTCQuicTransport/[[State]]}} internal slot is
<code>"closed"</code>, [= exception/throw = ] an <code>InvalidStateError</code>.
</p>
<p>
If all of the values of
<code><var>remoteParameters</var>.fingerprints[<var>j</var>].algorithm</code>
are unsupported, where <var>j</var> goes from 0 to the number of fingerprints,
[= exception/throw =] a <code>NotSupportedError</code>.
</p>
<table class="parameters">
<tbody>
<tr>
<th>Parameter</th>
<th>Type</th>
<th>Nullable</th>
<th>Optional</th>
<th>Description</th>
</tr>
<tr>
<td class="prmName">remoteParameters</td>
<td class="prmType"><code><a>RTCQuicParameters</a></code></td>
<td class="prmNullFalse"><span role="img" aria-label=
"False">✘</span></td>
<td class="prmOptFalse"><span role="img" aria-label=
"False">✘</span></td>
<td class="prmDesc"></td>
</tr>
</tbody>
</table>
<div>
<em>Return type:</em> <code>void</code>
</div>
</dd>
</dl>
</section>
</div>
</section>
<section id="rtcquicparameters*">
<h3><dfn>RTCQuicParameters</dfn> Dictionary</h3>
<p>The <code>RTCQuicParameters</code> dictionary includes information
relating to QUIC configuration.</p>
<div>
<pre class="idl">dictionary RTCQuicParameters {
RTCQuicRole role = "auto";
required sequence<RTCDtlsFingerprint> fingerprints;
};</pre>
<section>
<h2>Dictionary <a class="idlType">RTCQuicParameters</a> Members</h2>
<dl data-link-for="RTCQuicParameters" data-dfn-for="RTCQuicParameters" class=
"dictionary-members">
<dt><dfn><code>role</code></dfn> of type <span class=
"idlMemberType"><a>RTCQuicRole</a></span>, defaulting to
<code>"auto"</code></dt>
<dd>
<p>The QUIC role, with a default of <code>auto</code>.</p>
</dd>
<dt><dfn><code>fingerprints</code></dfn> of type <span class=
"idlMemberType">sequence<{{RTCDtlsFingerprint}}></span></dt>
<dd>
<p>Sequence of fingerprints, at least one fingerprint for each certificate
(with one computed with the digest algorithm used in the certificate
signature).</p>
</dd>
</dl>
</section>
</div>
</section>
<section id="rtcquicrole*">
<h3><dfn>RTCQuicRole</dfn> Enum</h3>
<p><code>RTCQuicRole</code> indicates the role of the QUIC
transport.</p>
<div>
<pre class="idl">enum RTCQuicRole {
"auto",
"client",
"server"
};</pre>
<table data-link-for="RTCQuicRole" data-dfn-for="RTCQuicRole" class="simple">
<tbody>
<tr>
<th colspan="2">Enumeration description</th>
</tr>
<tr>
<td><dfn><code id="idl-def-RTCQuicRole.auto">auto</code></dfn></td>
<td>
<p>The QUIC role is determined based on the resolved ICE role:
the ICE <code>"controlled"</code> role acts as the QUIC client and
the ICE <code>"controlling"</code> role acts as the QUIC server.</p>
</td>
</tr>
<tr>
<td><dfn><code id="idl-def-RTCQuicRole.client">client</code></dfn></td>
<td>
<p>The QUIC client role.</p>
</td>
</tr>
<tr>
<td><dfn><code id="idl-def-RTCQuicRole.server">server</code></dfn></td>
<td>
<p>The QUIC server role.</p>
</td>
</tr>
</tbody>
</table>
</div>
</section>
<section id="rtcquicroleinfo">
<h3>QUIC role determination</h3>
<p>
To diagnose QUIC role issues, an application may wish to determine
the desired and actual QUIC role of an <code><a>RTCQuicTransport</a></code>.
For a browser implementing ORTC, a <code><a>RTCQuicTransport</a></code>
object assumes a QUIC role of <code>auto</code> upon construction.
This implies that the QUIC role is determined by the ICE role. Since
<code>getLocalParameters().role</code> always returns the role assigned
to an <code><a>RTCQuicTransport</a></code> object upon construction
(<code>auto</code> for a browser), the <code>getLocalParameters</code>
method cannot be used to determine the desired or actual role of an
<code><a>RTCQuicTransport</a></code>.
</p>
<p>
An application can determine the desired role of an
<code><a>RTCQuicTransport</a></code> from the value of
<code><var>remoteParameters</var>.role</code> passed to
<code><a>RTCQuicTransport</a>.start(<var>remoteParameters</var>)</code>.
If <code><var>remoteParameters</var>.role</code> is <code>server</code>
then the desired role of the <code><a>RTCQuicTransport</a></code>
is <code>client</code>. If <code><var>remoteParameters</var>.role</code>
is <code>client</code> then the desired role of the
<code><a>RTCQuicTransport</a></code> is <code>server</code>.
</p>
<p>
The <code>RTCQuicTransport.transport.onstatechange</code> EventHandler
can be used to determine whether an <code><a>RTCQuicTransport</a></code>
transitions to the desired role. When
<code><a>RTCQuicTransport</a>.transport.state</code> transitions to
<code>connected</code>, if <code><a>RTCQuicTransport</a>.transport.role</code>
is <code>controlled</code> then the role of the
<code><a>RTCQuicTransport</a></code> is <code>client</code>.
If <code><a>RTCQuicTransport</a>.transport.role</code>
is <code>controlling</code> then the role of the
<code><a>RTCQuicTransport</a></code> is <code>server</code>.
</p>
</section>
</section>
<section class="informative" id="rtcquicexample*">
<h2>Examples</h2>
<pre class="example highlight">
function initiate(mySignaller) {
// Prepare the ICE gatherer
var gatherOptions = {
gatherPolicy: "all",
iceServers: [
{ urls: "stun:stun1.example.net" },
{ urls: "turn:turn.example.org", username: "user", credential: "myPassword",
credentialType: "password" }
]
};
var iceGatherer = new RTCIceGatherer(gatherOptions);
// Handle state changes
iceGatherer.onstatechange = function(event) {
myIceGathererStateChange("iceGatherer", event.state);
};
// Handle errors
iceGatherer.onerror = errorHandler;
// Prepare to signal local candidates
iceGatherer.onlocalcandidate = function(event) {
mySignaller.mySendLocalCandidate(event.candidate);
};
// Start gathering
iceGatherer.gather();
// Create ICE transport
var ice = new RTCIceTransport(iceGatherer);
// Prepare to handle remote ICE candidates
mySignaller.onRemoteCandidate = function(remote) {
ice.addRemoteCandidate(remote.candidate);
};
// Create the DTLS certificate
var certs;
var keygenAlgorithm = { name: "ECDSA", namedCurve: "P-256" };
RTCCertificate.generateCertificate(keygenAlgorithm).then(function(certificate){
certs[0] = certificate;
}, function(){
trace('Certificate could not be created');
});
// Create DTLS and QUIC transport
var dtls = new RTCDtlsTransport(ice, certs);
var quic = new RTCQuicTransport(ice, certs);
mySignaller.sendInitiate({
ice: iceGatherer.getLocalParameters(),
dtls: dtls.getLocalParameters(),
quic: quic.getLocalParameters(),
// ... marshall RtpSender/RtpReceiver capabilities as illustrated in Section 6.5 Example 9.
}, function(remote) {
// Start the ICE, DTLS and QUIC transports
ice.start(iceGatherer, remote.ice, RTCIceRole.controlling);
dtls.start(remote.dtls);
quic.start(remote.quic);
// ... configure RtpSender/RtpReceiver objects as illustrated in Section 6.5 Example 9.
});
}
</pre>
<pre class="example highlight">
// This is an example of how to answer
// Include some helper functions
import {trace, errorHandler, mySendLocalCandidate, myIceGathererStateChange,
myIceTransportStateChange, myDtlsTransportStateChange} from 'helper';
function accept(mySignaller, remote) {
var gatherOptions = {
gatherPolicy: "all",
iceServers: [
{ urls: "stun:stun1.example.net" },
{ urls: "turn:turn.example.org", username: "user", credential: "myPassword",
credentialType: "password" }
]
};
var iceGatherer = new RTCIceGatherer(gatherOptions);
// Handle state changes
iceGatherer.onstatechange = function(event) {
myIceGathererStateChange("iceGatherer", event.state);
};
// Handle errors
iceGatherer.onerror = errorHandler;
// Prepare to signal local candidates
iceGatherer.onlocalcandidate = function(event) {
mySignaller.mySendLocalCandidate(event.candidate);
};
// Start gathering
iceGatherer.gather();
// Create ICE transport
var ice = new RTCIceTransport(iceGatherer);
// Prepare to handle remote ICE candidates
mySignaller.onRemoteCandidate = function(remote) {
ice.addRemoteCandidate(remote.candidate);
};
// Create the DTLS certificate
var certs;
var keygenAlgorithm = { name: "ECDSA", namedCurve: "P-256" };
RTCCertificate.generateCertificate(keygenAlgorithm).then(function(certificate){
certs[0] = certificate;
}, function(){
trace('Certificate could not be created');
});
// Create DTLS and SCTP transport
var dtls = new RTCDtlsTransport(ice, certs);
var quic = new RTCQuicTransport(ice, certs);
mySignaller.sendAccept({
ice: iceGatherer.getLocalParameters(),
dtls: dtls.getLocalParameters(),
quic: quic.getLocalParameters(),
// ... marshall RtpSender/RtpReceiver capabilities as illustrated in Section 6.5 Example 9.
});
// Start the ICE, DTLS and SCTP transports
ice.start(iceGatherer, remote.ice, RTCIceRole.controlled);
dtls.start(remote.dtls);
// Start the QuicTransport
quic.start(remote.quic);
// ... configure RtpSender/RtpReceiver objects as illustrated in Section 6.5 Example 9.
}
</pre>
</section>
<section id="privacy-security">
<h2>Privacy and Security Considerations</h2>
<p>
This section is non-normative; it specifies no new behaviour, but
instead summarizes information already present in other parts of the
specification. The overall security considerations of the
APIs and protocols used in WebRTC are described in [[RFC8827]].
</p>
<section>
<h2>Impact on same origin policy</h2>
<p>
The QUIC API enables data to be communicated between
browsers and other devices, including other browsers.
</p>
<p>
This means that data can be shared between applications
running in different browsers, or between an application running in the
same browser and something that is not a browser. This is an extension
to the Web model which has had barriers against sending data
between entities with different origins.
</p>
<p>
This specification provides no user prompts or chrome indicators
for communication; it assumes that once the Web page has been allowed to
access data, it is free to share that data with other entities as it
chooses. Peer-to-peer exchanges of data via QUIC can therefore
occur without any user explicit consent or involvement.
</p>
</section>
<section>
<h2>Impact on local network</h2>
<p>Since the browser is an active platform executing in a trusted network
environment (inside the firewall), it is important to limit the damage
that the browser can do to other elements on the local network, and it is
important to protect data from interception, manipulation and
modification by untrusted participants.</p>
<p>Mitigations include:</p>
<ul>
<li>An UA will always request permission from the correspondent UA to
communicate using ICE. This ensures that the UA can only send to
partners who you have shared credentials with.</li>
<li>An UA will always request ongoing permission to continue sending
using ICE consent [[!RFC7675]]. This enables a receiver to withdraw
consent to receive.</li>
<li>An UA will always encrypt data, with strong per-session keying.</li>
<li>An UA will always use congestion control. This ensures that QUIC
cannot be used to flood the network.</li>
</ul>
<p>These measures are specified in the relevant IETF documents.</p>
</section>
<section>
<h2>Persistent information</h2>
<p>Utilizing the <code>generateCertificate()</code> API in [[!WEBRTC]], it is possible to
generate and store certificates that can subsequently be reused in constructing
<code><a>RTCQuicTransport</a></code> objects. These persistent certificates
can therefore be used to identify a user.</p>
</section>
</section>
</body>
</html>