Coverage Report

Created: 2026-09-03 07:24

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/samba/third_party/ngtcp2/lib/ngtcp2_conn.c
Line
Count
Source
1
/*
2
 * ngtcp2
3
 *
4
 * Copyright (c) 2017 ngtcp2 contributors
5
 *
6
 * Permission is hereby granted, free of charge, to any person obtaining
7
 * a copy of this software and associated documentation files (the
8
 * "Software"), to deal in the Software without restriction, including
9
 * without limitation the rights to use, copy, modify, merge, publish,
10
 * distribute, sublicense, and/or sell copies of the Software, and to
11
 * permit persons to whom the Software is furnished to do so, subject to
12
 * the following conditions:
13
 *
14
 * The above copyright notice and this permission notice shall be
15
 * included in all copies or substantial portions of the Software.
16
 *
17
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18
 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20
 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21
 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22
 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23
 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24
 */
25
#include "ngtcp2_conn.h"
26
27
#include <string.h>
28
#include <assert.h>
29
30
#include "ngtcp2_macro.h"
31
#include "ngtcp2_log.h"
32
#include "ngtcp2_cid.h"
33
#include "ngtcp2_conv.h"
34
#include "ngtcp2_vec.h"
35
#include "ngtcp2_addr.h"
36
#include "ngtcp2_path.h"
37
#include "ngtcp2_rcvry.h"
38
#include "ngtcp2_unreachable.h"
39
#include "ngtcp2_net.h"
40
#include "ngtcp2_transport_params.h"
41
#include "ngtcp2_settings.h"
42
#include "ngtcp2_callbacks.h"
43
#include "ngtcp2_tstamp.h"
44
#include "ngtcp2_frame_chain.h"
45
#include "ngtcp2_conn_info.h"
46
47
/* NGTCP2_FLOW_WINDOW_RTT_FACTOR is the factor of RTT when flow
48
   control window auto-tuning is triggered. */
49
0
#define NGTCP2_FLOW_WINDOW_RTT_FACTOR 2
50
/* NGTCP2_FLOW_WINDOW_SCALING_FACTOR is the growth factor of flow
51
   control window. */
52
0
#define NGTCP2_FLOW_WINDOW_SCALING_FACTOR 2
53
/* NGTCP2_MIN_COALESCED_PAYLOADLEN is the minimum length of QUIC
54
   packet payload that should be coalesced to a long packet. */
55
0
#define NGTCP2_MIN_COALESCED_PAYLOADLEN 128
56
/* NGTCP2_MAX_ACK_PER_PKT is the maximum number of ACK frame per an
57
   incoming QUIC packet to process.  ACK frames that exceed this limit
58
   are not processed. */
59
0
#define NGTCP2_MAX_ACK_PER_PKT 1
60
61
0
ngtcp2_objalloc_def(strm, ngtcp2_strm, oplent)
Unexecuted instantiation: ngtcp2_objalloc_strm_get
Unexecuted instantiation: ngtcp2_objalloc_strm_len_get
62
63
/*
64
 * conn_local_stream returns nonzero if |stream_id| indicates that it
65
 * is the stream initiated by local endpoint.
66
 */
67
0
static int conn_local_stream(ngtcp2_conn *conn, int64_t stream_id) {
68
0
  return (uint8_t)(stream_id & 1) == conn->server;
69
0
}
70
71
/*
72
 * bidi_stream returns nonzero if |stream_id| is a bidirectional
73
 * stream ID.
74
 */
75
0
static int bidi_stream(int64_t stream_id) { return (stream_id & 0x2) == 0; }
76
77
0
static void conn_update_timestamp(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
78
0
  assert(conn->log.last_ts <= ts);
79
0
  assert(conn->qlog.last_ts <= ts);
80
81
0
  conn->log.last_ts = ts;
82
0
  conn->qlog.last_ts = ts;
83
0
}
84
85
/*
86
 * conn_is_tls_handshake_completed returns nonzero if TLS handshake
87
 * has completed and 1 RTT keys are available.
88
 */
89
0
static int conn_is_tls_handshake_completed(ngtcp2_conn *conn) {
90
0
  return (conn->flags & NGTCP2_CONN_FLAG_TLS_HANDSHAKE_COMPLETED) &&
91
0
         conn->pktns.crypto.rx.ckm && conn->pktns.crypto.tx.ckm;
92
0
}
93
94
static int conn_call_recv_client_initial(ngtcp2_conn *conn,
95
0
                                         const ngtcp2_cid *dcid) {
96
0
  int rv;
97
98
0
  assert(conn->callbacks.recv_client_initial);
99
100
0
  rv = conn->callbacks.recv_client_initial(conn, dcid, conn->user_data);
101
0
  if (rv != 0) {
102
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
103
0
  }
104
105
0
  return 0;
106
0
}
107
108
0
static int conn_call_handshake_completed(ngtcp2_conn *conn) {
109
0
  int rv;
110
111
0
  if (!conn->callbacks.handshake_completed) {
112
0
    return 0;
113
0
  }
114
115
0
  rv = conn->callbacks.handshake_completed(conn, conn->user_data);
116
0
  if (rv != 0) {
117
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
118
0
  }
119
120
0
  return 0;
121
0
}
122
123
static int conn_call_recv_stream_data(ngtcp2_conn *conn, ngtcp2_strm *strm,
124
                                      uint32_t flags, uint64_t offset,
125
0
                                      const uint8_t *data, size_t datalen) {
126
0
  int rv;
127
128
0
  if (!conn->callbacks.recv_stream_data) {
129
0
    return 0;
130
0
  }
131
132
0
  rv = conn->callbacks.recv_stream_data(conn, flags, strm->stream_id, offset,
133
0
                                        data, datalen, conn->user_data,
134
0
                                        strm->stream_user_data);
135
0
  if (rv != 0) {
136
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
137
0
  }
138
139
0
  return 0;
140
0
}
141
142
static int conn_call_recv_crypto_data(ngtcp2_conn *conn,
143
                                      ngtcp2_encryption_level encryption_level,
144
                                      uint64_t offset, const uint8_t *data,
145
0
                                      size_t datalen) {
146
0
  int rv;
147
148
0
  assert(conn->callbacks.recv_crypto_data);
149
150
0
  rv = conn->callbacks.recv_crypto_data(conn, encryption_level, offset, data,
151
0
                                        datalen, conn->user_data);
152
0
  switch (rv) {
153
0
  case 0:
154
0
  case NGTCP2_ERR_CRYPTO:
155
0
  case NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM:
156
0
  case NGTCP2_ERR_MALFORMED_TRANSPORT_PARAM:
157
0
  case NGTCP2_ERR_TRANSPORT_PARAM:
158
0
  case NGTCP2_ERR_PROTO:
159
0
  case NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE:
160
0
  case NGTCP2_ERR_NOMEM:
161
0
  case NGTCP2_ERR_CALLBACK_FAILURE:
162
0
    return rv;
163
0
  default:
164
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
165
0
  }
166
0
}
167
168
0
static int conn_call_stream_open(ngtcp2_conn *conn, ngtcp2_strm *strm) {
169
0
  int rv;
170
171
0
  if (!conn->callbacks.stream_open) {
172
0
    return 0;
173
0
  }
174
175
0
  rv = conn->callbacks.stream_open(conn, strm->stream_id, conn->user_data);
176
0
  if (rv != 0) {
177
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
178
0
  }
179
180
0
  return 0;
181
0
}
182
183
0
static int conn_call_stream_close(ngtcp2_conn *conn, ngtcp2_strm *strm) {
184
0
  int rv;
185
0
  uint32_t flags = NGTCP2_STREAM_CLOSE_FLAG_NONE;
186
187
0
  if (!conn->callbacks.stream_close) {
188
0
    return 0;
189
0
  }
190
191
0
  if (strm->flags & NGTCP2_STRM_FLAG_APP_ERROR_CODE_SET) {
192
0
    flags |= NGTCP2_STREAM_CLOSE_FLAG_APP_ERROR_CODE_SET;
193
0
  }
194
195
0
  rv = conn->callbacks.stream_close(conn, flags, strm->stream_id,
196
0
                                    strm->app_error_code, conn->user_data,
197
0
                                    strm->stream_user_data);
198
0
  if (rv != 0) {
199
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
200
0
  }
201
202
0
  return 0;
203
0
}
204
205
static int conn_call_stream_reset(ngtcp2_conn *conn, int64_t stream_id,
206
                                  uint64_t final_size, uint64_t app_error_code,
207
0
                                  void *stream_user_data) {
208
0
  int rv;
209
210
0
  if (!conn->callbacks.stream_reset) {
211
0
    return 0;
212
0
  }
213
214
0
  rv = conn->callbacks.stream_reset(conn, stream_id, final_size, app_error_code,
215
0
                                    conn->user_data, stream_user_data);
216
0
  if (rv != 0) {
217
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
218
0
  }
219
220
0
  return 0;
221
0
}
222
223
static int conn_call_extend_max_local_streams_bidi(ngtcp2_conn *conn,
224
0
                                                   uint64_t max_streams) {
225
0
  int rv;
226
227
0
  if (!conn->callbacks.extend_max_local_streams_bidi) {
228
0
    return 0;
229
0
  }
230
231
0
  rv = conn->callbacks.extend_max_local_streams_bidi(conn, max_streams,
232
0
                                                     conn->user_data);
233
0
  if (rv != 0) {
234
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
235
0
  }
236
237
0
  return 0;
238
0
}
239
240
static int conn_call_extend_max_local_streams_uni(ngtcp2_conn *conn,
241
0
                                                  uint64_t max_streams) {
242
0
  int rv;
243
244
0
  if (!conn->callbacks.extend_max_local_streams_uni) {
245
0
    return 0;
246
0
  }
247
248
0
  rv = conn->callbacks.extend_max_local_streams_uni(conn, max_streams,
249
0
                                                    conn->user_data);
250
0
  if (rv != 0) {
251
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
252
0
  }
253
254
0
  return 0;
255
0
}
256
257
static int conn_call_get_new_connection_id(ngtcp2_conn *conn, ngtcp2_cid *cid,
258
                                           ngtcp2_stateless_reset_token *token,
259
0
                                           size_t cidlen) {
260
0
  int rv;
261
262
0
  if (conn->callbacks.get_new_connection_id2) {
263
0
    rv = conn->callbacks.get_new_connection_id2(conn, cid, token, cidlen,
264
0
                                                conn->user_data);
265
0
  } else {
266
0
    assert(conn->callbacks.get_new_connection_id);
267
268
0
    rv = conn->callbacks.get_new_connection_id(conn, cid, token->data, cidlen,
269
0
                                               conn->user_data);
270
0
  }
271
272
0
  if (rv != 0) {
273
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
274
0
  }
275
276
0
  return 0;
277
0
}
278
279
static int conn_call_remove_connection_id(ngtcp2_conn *conn,
280
0
                                          const ngtcp2_cid *cid) {
281
0
  int rv;
282
283
0
  if (!conn->callbacks.remove_connection_id) {
284
0
    return 0;
285
0
  }
286
287
0
  rv = conn->callbacks.remove_connection_id(conn, cid, conn->user_data);
288
0
  if (rv != 0) {
289
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
290
0
  }
291
292
0
  return 0;
293
0
}
294
295
static int conn_call_begin_path_validation(ngtcp2_conn *conn,
296
0
                                           const ngtcp2_pv *pv) {
297
0
  int rv;
298
0
  uint32_t flags = NGTCP2_PATH_VALIDATION_FLAG_NONE;
299
0
  const ngtcp2_path *fallback_path = NULL;
300
301
0
  if (!pv || !conn->callbacks.begin_path_validation) {
302
0
    return 0;
303
0
  }
304
305
0
  if (pv->flags & NGTCP2_PV_FLAG_PREFERRED_ADDR) {
306
0
    flags |= NGTCP2_PATH_VALIDATION_FLAG_PREFERRED_ADDR;
307
0
  }
308
309
0
  if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
310
0
    fallback_path = &pv->fallback_dcid.ps.path;
311
0
  }
312
313
0
  rv = conn->callbacks.begin_path_validation(conn, flags, &pv->dcid.ps.path,
314
0
                                             fallback_path, conn->user_data);
315
0
  if (rv != 0) {
316
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
317
0
  }
318
319
0
  return 0;
320
0
}
321
322
static int conn_call_path_validation(ngtcp2_conn *conn, const ngtcp2_pv *pv,
323
0
                                     ngtcp2_path_validation_result res) {
324
0
  int rv;
325
0
  uint32_t flags = NGTCP2_PATH_VALIDATION_FLAG_NONE;
326
0
  const ngtcp2_path *fallback_path = NULL;
327
328
0
  if (!conn->callbacks.path_validation) {
329
0
    return 0;
330
0
  }
331
332
0
  if (pv->flags & NGTCP2_PV_FLAG_PREFERRED_ADDR) {
333
0
    flags |= NGTCP2_PATH_VALIDATION_FLAG_PREFERRED_ADDR;
334
0
  }
335
336
0
  if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
337
0
    fallback_path = &pv->fallback_dcid.ps.path;
338
0
  }
339
340
0
  if (conn->server && fallback_path &&
341
0
      (ngtcp2_addr_cmp(&pv->dcid.ps.path.remote, &fallback_path->remote) &
342
0
       (NGTCP2_ADDR_CMP_FLAG_ADDR | NGTCP2_ADDR_CMP_FLAG_FAMILY))) {
343
0
    flags |= NGTCP2_PATH_VALIDATION_FLAG_NEW_TOKEN;
344
0
  }
345
346
0
  rv = conn->callbacks.path_validation(conn, flags, &pv->dcid.ps.path,
347
0
                                       fallback_path, res, conn->user_data);
348
0
  if (rv != 0) {
349
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
350
0
  }
351
352
0
  return 0;
353
0
}
354
355
static int conn_call_select_preferred_addr(ngtcp2_conn *conn,
356
0
                                           ngtcp2_path *dest) {
357
0
  int rv;
358
359
0
  if (!conn->callbacks.select_preferred_addr) {
360
0
    return 0;
361
0
  }
362
363
0
  assert(conn->remote.transport_params);
364
0
  assert(conn->remote.transport_params->preferred_addr_present);
365
366
0
  rv = conn->callbacks.select_preferred_addr(
367
0
    conn, dest, &conn->remote.transport_params->preferred_addr,
368
0
    conn->user_data);
369
0
  if (rv != 0) {
370
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
371
0
  }
372
373
0
  return 0;
374
0
}
375
376
static int conn_call_extend_max_remote_streams_bidi(ngtcp2_conn *conn,
377
0
                                                    uint64_t max_streams) {
378
0
  int rv;
379
380
0
  if (!conn->callbacks.extend_max_remote_streams_bidi) {
381
0
    return 0;
382
0
  }
383
384
0
  rv = conn->callbacks.extend_max_remote_streams_bidi(conn, max_streams,
385
0
                                                      conn->user_data);
386
0
  if (rv != 0) {
387
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
388
0
  }
389
390
0
  return 0;
391
0
}
392
393
static int conn_call_extend_max_remote_streams_uni(ngtcp2_conn *conn,
394
0
                                                   uint64_t max_streams) {
395
0
  int rv;
396
397
0
  if (!conn->callbacks.extend_max_remote_streams_uni) {
398
0
    return 0;
399
0
  }
400
401
0
  rv = conn->callbacks.extend_max_remote_streams_uni(conn, max_streams,
402
0
                                                     conn->user_data);
403
0
  if (rv != 0) {
404
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
405
0
  }
406
407
0
  return 0;
408
0
}
409
410
static int conn_call_extend_max_stream_data(ngtcp2_conn *conn,
411
                                            ngtcp2_strm *strm,
412
                                            int64_t stream_id,
413
0
                                            uint64_t datalen) {
414
0
  int rv;
415
416
0
  if (!conn->callbacks.extend_max_stream_data) {
417
0
    return 0;
418
0
  }
419
420
0
  rv = conn->callbacks.extend_max_stream_data(
421
0
    conn, stream_id, datalen, conn->user_data, strm->stream_user_data);
422
0
  if (rv != 0) {
423
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
424
0
  }
425
426
0
  return 0;
427
0
}
428
429
static int conn_call_dcid_status(ngtcp2_conn *conn,
430
                                 ngtcp2_connection_id_status_type type,
431
0
                                 const ngtcp2_dcid *dcid) {
432
0
  int rv;
433
434
0
  if (conn->callbacks.dcid_status2) {
435
0
    rv = conn->callbacks.dcid_status2(
436
0
      conn, type, dcid->seq, &dcid->cid,
437
0
      (dcid->flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT) ? &dcid->token : NULL,
438
0
      conn->user_data);
439
0
  } else if (conn->callbacks.dcid_status) {
440
0
    rv = conn->callbacks.dcid_status(
441
0
      conn, type, dcid->seq, &dcid->cid,
442
0
      (dcid->flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT) ? dcid->token.data : NULL,
443
0
      conn->user_data);
444
0
  } else {
445
0
    return 0;
446
0
  }
447
448
0
  if (rv != 0) {
449
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
450
0
  }
451
452
0
  return 0;
453
0
}
454
455
0
static int conn_call_activate_dcid(ngtcp2_conn *conn, const ngtcp2_dcid *dcid) {
456
0
  return conn_call_dcid_status(conn, NGTCP2_CONNECTION_ID_STATUS_TYPE_ACTIVATE,
457
0
                               dcid);
458
0
}
459
460
static int conn_call_deactivate_dcid(ngtcp2_conn *conn,
461
0
                                     const ngtcp2_dcid *dcid) {
462
0
  return conn_call_dcid_status(
463
0
    conn, NGTCP2_CONNECTION_ID_STATUS_TYPE_DEACTIVATE, dcid);
464
0
}
465
466
static int conn_call_stream_stop_sending(ngtcp2_conn *conn, int64_t stream_id,
467
                                         uint64_t app_error_code,
468
0
                                         void *stream_user_data) {
469
0
  int rv;
470
471
0
  if (!conn->callbacks.stream_stop_sending) {
472
0
    return 0;
473
0
  }
474
475
0
  rv = conn->callbacks.stream_stop_sending(conn, stream_id, app_error_code,
476
0
                                           conn->user_data, stream_user_data);
477
0
  if (rv != 0) {
478
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
479
0
  }
480
481
0
  return 0;
482
0
}
483
484
static void conn_call_delete_crypto_aead_ctx(ngtcp2_conn *conn,
485
0
                                             ngtcp2_crypto_aead_ctx *aead_ctx) {
486
0
  if (!aead_ctx->native_handle) {
487
0
    return;
488
0
  }
489
490
0
  assert(conn->callbacks.delete_crypto_aead_ctx);
491
492
0
  conn->callbacks.delete_crypto_aead_ctx(conn, aead_ctx, conn->user_data);
493
0
}
494
495
static void
496
conn_call_delete_crypto_cipher_ctx(ngtcp2_conn *conn,
497
0
                                   ngtcp2_crypto_cipher_ctx *cipher_ctx) {
498
0
  if (!cipher_ctx->native_handle) {
499
0
    return;
500
0
  }
501
502
0
  assert(conn->callbacks.delete_crypto_cipher_ctx);
503
504
0
  conn->callbacks.delete_crypto_cipher_ctx(conn, cipher_ctx, conn->user_data);
505
0
}
506
507
0
static int conn_call_client_initial(ngtcp2_conn *conn) {
508
0
  int rv;
509
510
0
  assert(conn->callbacks.client_initial);
511
512
0
  rv = conn->callbacks.client_initial(conn, conn->user_data);
513
0
  if (rv != 0) {
514
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
515
0
  }
516
517
0
  return 0;
518
0
}
519
520
static int conn_call_get_path_challenge_data(ngtcp2_conn *conn,
521
0
                                             ngtcp2_path_challenge_data *data) {
522
0
  int rv;
523
524
0
  if (conn->callbacks.get_path_challenge_data2) {
525
0
    rv = conn->callbacks.get_path_challenge_data2(conn, data, conn->user_data);
526
0
  } else {
527
0
    assert(conn->callbacks.get_path_challenge_data);
528
529
0
    rv = conn->callbacks.get_path_challenge_data(conn, data->data,
530
0
                                                 conn->user_data);
531
0
  }
532
533
0
  if (rv != 0) {
534
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
535
0
  }
536
537
0
  return 0;
538
0
}
539
540
static int conn_call_recv_version_negotiation(ngtcp2_conn *conn,
541
                                              const ngtcp2_pkt_hd *hd,
542
0
                                              const uint32_t *sv, size_t nsv) {
543
0
  int rv;
544
545
0
  if (!conn->callbacks.recv_version_negotiation) {
546
0
    return 0;
547
0
  }
548
549
0
  rv = conn->callbacks.recv_version_negotiation(conn, hd, sv, nsv,
550
0
                                                conn->user_data);
551
0
  if (rv != 0) {
552
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
553
0
  }
554
555
0
  return 0;
556
0
}
557
558
0
static int conn_call_recv_retry(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd) {
559
0
  int rv;
560
561
0
  assert(conn->callbacks.recv_retry);
562
563
0
  rv = conn->callbacks.recv_retry(conn, hd, conn->user_data);
564
0
  if (rv != 0) {
565
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
566
0
  }
567
568
0
  return 0;
569
0
}
570
571
static int
572
conn_call_recv_stateless_reset(ngtcp2_conn *conn,
573
0
                               const ngtcp2_pkt_stateless_reset2 *sr) {
574
0
  int rv;
575
0
  ngtcp2_pkt_stateless_reset legacy_sr;
576
577
0
  if (conn->callbacks.recv_stateless_reset2) {
578
0
    rv = conn->callbacks.recv_stateless_reset2(conn, sr, conn->user_data);
579
0
  } else if (conn->callbacks.recv_stateless_reset) {
580
0
    memcpy(legacy_sr.stateless_reset_token, sr->token.data,
581
0
           sizeof(legacy_sr.stateless_reset_token));
582
0
    legacy_sr.rand = sr->rand;
583
0
    legacy_sr.randlen = sr->randlen;
584
585
0
    rv =
586
0
      conn->callbacks.recv_stateless_reset(conn, &legacy_sr, conn->user_data);
587
0
  } else {
588
0
    return 0;
589
0
  }
590
591
0
  if (rv != 0) {
592
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
593
0
  }
594
595
0
  return 0;
596
0
}
597
598
static int conn_call_recv_new_token(ngtcp2_conn *conn, const uint8_t *token,
599
0
                                    size_t tokenlen) {
600
0
  int rv;
601
602
0
  if (!conn->callbacks.recv_new_token) {
603
0
    return 0;
604
0
  }
605
606
0
  rv = conn->callbacks.recv_new_token(conn, token, tokenlen, conn->user_data);
607
0
  if (rv != 0) {
608
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
609
0
  }
610
611
0
  return 0;
612
0
}
613
614
0
static int conn_call_handshake_confirmed(ngtcp2_conn *conn) {
615
0
  int rv;
616
617
0
  if (!conn->callbacks.handshake_confirmed) {
618
0
    return 0;
619
0
  }
620
621
0
  rv = conn->callbacks.handshake_confirmed(conn, conn->user_data);
622
0
  if (rv != 0) {
623
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
624
0
  }
625
626
0
  return 0;
627
0
}
628
629
static int conn_call_recv_datagram(ngtcp2_conn *conn,
630
0
                                   const ngtcp2_datagram *fr) {
631
0
  const uint8_t *data;
632
0
  size_t datalen;
633
0
  int rv;
634
0
  uint32_t flags = NGTCP2_DATAGRAM_FLAG_NONE;
635
636
0
  if (!conn->callbacks.recv_datagram) {
637
0
    return 0;
638
0
  }
639
640
0
  if (fr->datacnt) {
641
0
    assert(fr->datacnt == 1);
642
643
0
    data = fr->data->base;
644
0
    datalen = fr->data->len;
645
0
  } else {
646
0
    data = NULL;
647
0
    datalen = 0;
648
0
  }
649
650
0
  if (!conn_is_tls_handshake_completed(conn)) {
651
0
    flags |= NGTCP2_DATAGRAM_FLAG_0RTT;
652
0
  }
653
654
0
  rv =
655
0
    conn->callbacks.recv_datagram(conn, flags, data, datalen, conn->user_data);
656
0
  if (rv != 0) {
657
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
658
0
  }
659
660
0
  return 0;
661
0
}
662
663
static int
664
conn_call_update_key(ngtcp2_conn *conn, uint8_t *rx_secret, uint8_t *tx_secret,
665
                     ngtcp2_crypto_aead_ctx *rx_aead_ctx, uint8_t *rx_iv,
666
                     ngtcp2_crypto_aead_ctx *tx_aead_ctx, uint8_t *tx_iv,
667
                     const uint8_t *current_rx_secret,
668
0
                     const uint8_t *current_tx_secret, size_t secretlen) {
669
0
  int rv;
670
671
0
  assert(conn->callbacks.update_key);
672
673
0
  rv = conn->callbacks.update_key(
674
0
    conn, rx_secret, tx_secret, rx_aead_ctx, rx_iv, tx_aead_ctx, tx_iv,
675
0
    current_rx_secret, current_tx_secret, secretlen, conn->user_data);
676
0
  if (rv != 0) {
677
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
678
0
  }
679
680
0
  return 0;
681
0
}
682
683
static int conn_call_version_negotiation(ngtcp2_conn *conn, uint32_t version,
684
0
                                         const ngtcp2_cid *dcid) {
685
0
  int rv;
686
687
0
  assert(conn->callbacks.version_negotiation);
688
689
0
  rv =
690
0
    conn->callbacks.version_negotiation(conn, version, dcid, conn->user_data);
691
0
  if (rv != 0) {
692
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
693
0
  }
694
695
0
  return 0;
696
0
}
697
698
static int conn_call_recv_rx_key(ngtcp2_conn *conn,
699
0
                                 ngtcp2_encryption_level level) {
700
0
  int rv;
701
702
0
  if (!conn->callbacks.recv_rx_key) {
703
0
    return 0;
704
0
  }
705
706
0
  rv = conn->callbacks.recv_rx_key(conn, level, conn->user_data);
707
0
  if (rv != 0) {
708
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
709
0
  }
710
711
0
  return 0;
712
0
}
713
714
static int conn_call_recv_tx_key(ngtcp2_conn *conn,
715
0
                                 ngtcp2_encryption_level level) {
716
0
  int rv;
717
718
0
  if (!conn->callbacks.recv_tx_key) {
719
0
    return 0;
720
0
  }
721
722
0
  rv = conn->callbacks.recv_tx_key(conn, level, conn->user_data);
723
0
  if (rv != 0) {
724
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
725
0
  }
726
727
0
  return 0;
728
0
}
729
730
/*
731
 * pktns_init initializes |pktns|.  It assumes that the object pointed
732
 * by |pktns| is zero-cleared.
733
 */
734
static void pktns_init(ngtcp2_pktns *pktns, ngtcp2_pktns_id pktns_id,
735
                       ngtcp2_rst *rst, ngtcp2_cc *cc, int64_t initial_pkt_num,
736
                       ngtcp2_log *log, ngtcp2_qlog *qlog,
737
                       ngtcp2_objalloc *rtb_entry_objalloc,
738
0
                       ngtcp2_objalloc *frc_objalloc, const ngtcp2_mem *mem) {
739
0
  ngtcp2_gaptr_init(&pktns->rx.pngap, mem);
740
741
0
  pktns->tx.last_pkt_num = initial_pkt_num - 1;
742
0
  pktns->tx.non_ack_pkt_start_ts = UINT64_MAX;
743
0
  pktns->rx.max_ack_eliciting_pkt_num = -1;
744
0
  pktns->id = pktns_id;
745
746
0
  ngtcp2_acktr_init(&pktns->acktr, log, mem);
747
748
0
  ngtcp2_strm_init(&pktns->crypto.strm, 0, NGTCP2_STRM_FLAG_NONE, 0, 0, NULL,
749
0
                   frc_objalloc, mem);
750
751
0
  ngtcp2_rtb_init(&pktns->rtb, rst, cc, initial_pkt_num, log, qlog,
752
0
                  rtb_entry_objalloc, frc_objalloc, mem);
753
0
}
754
755
static int pktns_new(ngtcp2_pktns **ppktns, ngtcp2_pktns_id pktns_id,
756
                     ngtcp2_rst *rst, ngtcp2_cc *cc, int64_t initial_pkt_num,
757
                     ngtcp2_log *log, ngtcp2_qlog *qlog,
758
                     ngtcp2_objalloc *rtb_entry_objalloc,
759
0
                     ngtcp2_objalloc *frc_objalloc, const ngtcp2_mem *mem) {
760
0
  *ppktns = ngtcp2_mem_calloc(mem, 1, sizeof(ngtcp2_pktns));
761
0
  if (*ppktns == NULL) {
762
0
    return NGTCP2_ERR_NOMEM;
763
0
  }
764
765
0
  pktns_init(*ppktns, pktns_id, rst, cc, initial_pkt_num, log, qlog,
766
0
             rtb_entry_objalloc, frc_objalloc, mem);
767
768
0
  return 0;
769
0
}
770
771
0
static int cycle_less(const ngtcp2_pq_entry *lhs, const ngtcp2_pq_entry *rhs) {
772
0
  ngtcp2_strm *ls = ngtcp2_struct_of(lhs, ngtcp2_strm, pe);
773
0
  ngtcp2_strm *rs = ngtcp2_struct_of(rhs, ngtcp2_strm, pe);
774
775
0
  if (ls->cycle == rs->cycle) {
776
0
    return ls->stream_id < rs->stream_id;
777
0
  }
778
779
0
  return rs->cycle - ls->cycle <= 1;
780
0
}
781
782
0
static void delete_buffed_pkts(ngtcp2_pkt_chain *pc, const ngtcp2_mem *mem) {
783
0
  ngtcp2_pkt_chain *next;
784
785
0
  for (; pc;) {
786
0
    next = pc->next;
787
0
    ngtcp2_pkt_chain_del(pc, mem);
788
0
    pc = next;
789
0
  }
790
0
}
791
792
static void delete_buf_chain(ngtcp2_buf_chain *bufchain,
793
0
                             const ngtcp2_mem *mem) {
794
0
  ngtcp2_buf_chain *next;
795
796
0
  for (; bufchain;) {
797
0
    next = bufchain->next;
798
0
    ngtcp2_buf_chain_del(bufchain, mem);
799
0
    bufchain = next;
800
0
  }
801
0
}
802
803
0
static void pktns_free(ngtcp2_pktns *pktns, const ngtcp2_mem *mem) {
804
0
  delete_buf_chain(pktns->crypto.tx.data, mem);
805
806
0
  delete_buffed_pkts(pktns->rx.buffed_pkts, mem);
807
808
0
  ngtcp2_frame_chain_list_objalloc_del(pktns->tx.frq, pktns->rtb.frc_objalloc,
809
0
                                       mem);
810
811
0
  ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, mem);
812
0
  ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, mem);
813
814
0
  ngtcp2_rtb_free(&pktns->rtb);
815
0
  ngtcp2_strm_free(&pktns->crypto.strm);
816
0
  ngtcp2_acktr_free(&pktns->acktr);
817
0
  ngtcp2_gaptr_free(&pktns->rx.pngap);
818
0
}
819
820
0
static void pktns_del(ngtcp2_pktns *pktns, const ngtcp2_mem *mem) {
821
0
  if (pktns == NULL) {
822
0
    return;
823
0
  }
824
825
0
  pktns_free(pktns, mem);
826
827
0
  ngtcp2_mem_free(mem, pktns);
828
0
}
829
830
0
static int cid_less(const ngtcp2_ksl_key *lhs, const ngtcp2_ksl_key *rhs) {
831
0
  return ngtcp2_cid_less(lhs, rhs);
832
0
}
833
834
ngtcp2_ksl_search_def(cid_less, cid_less)
835
836
static int retired_ts_less(const ngtcp2_pq_entry *lhs,
837
0
                           const ngtcp2_pq_entry *rhs) {
838
0
  const ngtcp2_scid *a = ngtcp2_struct_of(lhs, ngtcp2_scid, pe);
839
0
  const ngtcp2_scid *b = ngtcp2_struct_of(rhs, ngtcp2_scid, pe);
840
841
0
  return a->retired_ts < b->retired_ts;
842
0
}
843
844
/*
845
 * conn_reset_conn_stat_cc resets congestion state in |cstat|.
846
 */
847
static void conn_reset_conn_stat_cc(ngtcp2_conn *conn,
848
0
                                    ngtcp2_conn_stat *cstat) {
849
0
  cstat->latest_rtt = 0;
850
0
  cstat->min_rtt = UINT64_MAX;
851
0
  cstat->smoothed_rtt = conn->local.settings.initial_rtt;
852
0
  cstat->rttvar = conn->local.settings.initial_rtt / 2;
853
0
  cstat->first_rtt_sample_ts = UINT64_MAX;
854
0
  cstat->pto_count = 0;
855
0
  cstat->loss_detection_timer = UINT64_MAX;
856
0
  cstat->max_tx_udp_payload_size =
857
0
    ngtcp2_conn_get_path_max_tx_udp_payload_size(conn);
858
0
  cstat->cwnd = ngtcp2_cc_compute_initcwnd(cstat->max_tx_udp_payload_size);
859
0
  cstat->ssthresh = UINT64_MAX;
860
0
  cstat->congestion_recovery_start_ts = UINT64_MAX;
861
0
  cstat->bytes_in_flight = 0;
862
0
  cstat->delivery_rate_sec = 0;
863
0
  cstat->pacing_interval_m = 0;
864
0
  cstat->send_quantum = 64 * 1024;
865
0
}
866
867
/*
868
 * reset_conn_stat_recovery resets the fields related to the recovery
869
 * function
870
 */
871
0
static void reset_conn_stat_recovery(ngtcp2_conn_stat *cstat) {
872
  /* Initializes them with UINT64_MAX. */
873
0
  memset(cstat->loss_time, 0xFF, sizeof(cstat->loss_time));
874
0
  memset(cstat->last_tx_pkt_ts, 0xFF, sizeof(cstat->last_tx_pkt_ts));
875
0
}
876
877
/*
878
 * conn_reset_conn_stat resets |cstat|.  The following fields are not
879
 * reset: initial_rtt and max_udp_payload_size.
880
 */
881
0
static void conn_reset_conn_stat(ngtcp2_conn *conn, ngtcp2_conn_stat *cstat) {
882
0
  conn_reset_conn_stat_cc(conn, cstat);
883
0
  reset_conn_stat_recovery(cstat);
884
0
}
885
886
0
static void delete_scid(ngtcp2_ksl *scids, const ngtcp2_mem *mem) {
887
0
  ngtcp2_ksl_it it;
888
889
0
  for (it = ngtcp2_ksl_begin(scids); !ngtcp2_ksl_it_end(&it);
890
0
       ngtcp2_ksl_it_next(&it)) {
891
0
    ngtcp2_mem_free(mem, ngtcp2_ksl_it_get(&it));
892
0
  }
893
0
}
894
895
/*
896
 * compute_pto computes PTO.
897
 */
898
static ngtcp2_duration compute_pto(ngtcp2_duration smoothed_rtt,
899
                                   ngtcp2_duration rttvar,
900
0
                                   ngtcp2_duration max_ack_delay) {
901
0
  ngtcp2_duration var = ngtcp2_max_uint64(4 * rttvar, NGTCP2_GRANULARITY);
902
0
  return smoothed_rtt + var + max_ack_delay;
903
0
}
904
905
/*
906
 * conn_compute_initial_pto computes PTO using the initial RTT.
907
 */
908
static ngtcp2_duration conn_compute_initial_pto(ngtcp2_conn *conn,
909
0
                                                ngtcp2_pktns *pktns) {
910
0
  ngtcp2_duration initial_rtt = conn->local.settings.initial_rtt;
911
0
  ngtcp2_duration max_ack_delay;
912
913
0
  if (pktns->id == NGTCP2_PKTNS_ID_APPLICATION &&
914
0
      conn->remote.transport_params) {
915
0
    max_ack_delay = conn->remote.transport_params->max_ack_delay;
916
0
  } else {
917
0
    max_ack_delay = 0;
918
0
  }
919
0
  return compute_pto(initial_rtt, initial_rtt / 2, max_ack_delay);
920
0
}
921
922
/*
923
 * conn_compute_pto computes the current PTO.
924
 */
925
static ngtcp2_duration conn_compute_pto(ngtcp2_conn *conn,
926
0
                                        ngtcp2_pktns *pktns) {
927
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
928
0
  ngtcp2_duration max_ack_delay;
929
930
0
  if (pktns->id == NGTCP2_PKTNS_ID_APPLICATION &&
931
0
      conn->remote.transport_params) {
932
0
    max_ack_delay = conn->remote.transport_params->max_ack_delay;
933
0
  } else {
934
0
    max_ack_delay = 0;
935
0
  }
936
0
  return compute_pto(cstat->smoothed_rtt, cstat->rttvar, max_ack_delay);
937
0
}
938
939
ngtcp2_duration ngtcp2_conn_compute_pto(ngtcp2_conn *conn,
940
0
                                        ngtcp2_pktns *pktns) {
941
0
  return conn_compute_pto(conn, pktns);
942
0
}
943
944
/*
945
 * conn_compute_pv_timeout_pto returns path validation timeout using
946
 * the given |pto|.
947
 */
948
static ngtcp2_duration conn_compute_pv_timeout_pto(ngtcp2_conn *conn,
949
0
                                                   ngtcp2_duration pto) {
950
0
  ngtcp2_duration initial_pto = conn_compute_initial_pto(conn, &conn->pktns);
951
952
0
  return 3 * ngtcp2_max_uint64(pto, initial_pto);
953
0
}
954
955
/*
956
 * conn_compute_pv_timeout returns path validation timeout.
957
 */
958
0
static ngtcp2_duration conn_compute_pv_timeout(ngtcp2_conn *conn) {
959
0
  return conn_compute_pv_timeout_pto(conn,
960
0
                                     conn_compute_pto(conn, &conn->pktns));
961
0
}
962
963
static void conn_handle_tx_ecn(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
964
                               uint16_t *prtb_entry_flags, ngtcp2_pktns *pktns,
965
0
                               const ngtcp2_pkt_hd *hd, ngtcp2_tstamp ts) {
966
0
  assert(pi);
967
968
0
  if (pi->ecn != NGTCP2_ECN_NOT_ECT) {
969
    /* We have already made a transition of validation state and
970
      deceided to send UDP datagram with ECN bit set.  Coalesced QUIC
971
      packets also bear ECN bits set. */
972
0
    if (pktns->tx.ecn.start_pkt_num == INT64_MAX) {
973
0
      pktns->tx.ecn.start_pkt_num = hd->pkt_num;
974
0
    }
975
976
0
    ++pktns->tx.ecn.validation_pkt_sent;
977
978
0
    if (prtb_entry_flags) {
979
0
      *prtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ECN;
980
0
    }
981
982
0
    ++pktns->tx.ecn.ect0;
983
984
0
    return;
985
0
  }
986
987
0
  switch (conn->tx.ecn.state) {
988
0
  case NGTCP2_ECN_STATE_TESTING:
989
0
    if (conn->tx.ecn.validation_start_ts == UINT64_MAX) {
990
0
      assert(0 == pktns->tx.ecn.validation_pkt_sent);
991
0
      assert(0 == pktns->tx.ecn.validation_pkt_lost);
992
993
0
      conn->tx.ecn.validation_start_ts = ts;
994
0
    } else if (ts - conn->tx.ecn.validation_start_ts >=
995
0
               3 * conn_compute_pto(conn, pktns)) {
996
0
      conn->tx.ecn.state = NGTCP2_ECN_STATE_UNKNOWN;
997
0
      break;
998
0
    }
999
1000
0
    if (pktns->tx.ecn.start_pkt_num == INT64_MAX) {
1001
0
      pktns->tx.ecn.start_pkt_num = hd->pkt_num;
1002
0
    }
1003
1004
0
    ++pktns->tx.ecn.validation_pkt_sent;
1005
1006
0
    if (++conn->tx.ecn.dgram_sent == NGTCP2_ECN_MAX_NUM_VALIDATION_PKTS) {
1007
0
      conn->tx.ecn.state = NGTCP2_ECN_STATE_UNKNOWN;
1008
0
    }
1009
    /* fall through */
1010
0
  case NGTCP2_ECN_STATE_CAPABLE:
1011
    /* pi is provided per UDP datagram. */
1012
0
    assert(NGTCP2_ECN_NOT_ECT == pi->ecn);
1013
1014
0
    pi->ecn = NGTCP2_ECN_ECT_0;
1015
1016
0
    if (prtb_entry_flags) {
1017
0
      *prtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ECN;
1018
0
    }
1019
1020
0
    ++pktns->tx.ecn.ect0;
1021
0
    break;
1022
0
  case NGTCP2_ECN_STATE_UNKNOWN:
1023
0
  case NGTCP2_ECN_STATE_FAILED:
1024
0
    break;
1025
0
  default:
1026
0
    ngtcp2_unreachable();
1027
0
  }
1028
0
}
1029
1030
0
static void conn_reset_ecn_validation_state(ngtcp2_conn *conn) {
1031
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
1032
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
1033
0
  ngtcp2_pktns *pktns = &conn->pktns;
1034
1035
0
  conn->tx.ecn.state = NGTCP2_ECN_STATE_TESTING;
1036
0
  conn->tx.ecn.validation_start_ts = UINT64_MAX;
1037
0
  conn->tx.ecn.dgram_sent = 0;
1038
1039
0
  if (in_pktns) {
1040
0
    in_pktns->tx.ecn.start_pkt_num = INT64_MAX;
1041
0
    in_pktns->tx.ecn.validation_pkt_sent = 0;
1042
0
    in_pktns->tx.ecn.validation_pkt_lost = 0;
1043
0
  }
1044
1045
0
  if (hs_pktns) {
1046
0
    hs_pktns->tx.ecn.start_pkt_num = INT64_MAX;
1047
0
    hs_pktns->tx.ecn.validation_pkt_sent = 0;
1048
0
    hs_pktns->tx.ecn.validation_pkt_lost = 0;
1049
0
  }
1050
1051
0
  pktns->tx.ecn.start_pkt_num = INT64_MAX;
1052
0
  pktns->tx.ecn.validation_pkt_sent = 0;
1053
0
  pktns->tx.ecn.validation_pkt_lost = 0;
1054
0
}
1055
1056
/* server_default_available_versions is the default available_versions
1057
   field sent by server. */
1058
static uint8_t server_default_available_versions[] = {0, 0, 0, 1};
1059
1060
/*
1061
 * available_versions_init writes |versions| of length |versionslen|
1062
 * in network byte order to the buffer pointed by |buf|, suitable for
1063
 * sending in available_versions field of version_information QUIC
1064
 * transport parameter.  This function returns the pointer to the one
1065
 * beyond the last byte written.
1066
 */
1067
static void *available_versions_init(void *buf, const uint32_t *versions,
1068
0
                                     size_t versionslen) {
1069
0
  size_t i;
1070
1071
0
  for (i = 0; i < versionslen; ++i) {
1072
0
    buf = ngtcp2_put_uint32be(buf, versions[i]);
1073
0
  }
1074
1075
0
  return 0;
1076
0
}
1077
1078
static void
1079
conn_set_local_transport_params(ngtcp2_conn *conn,
1080
0
                                const ngtcp2_transport_params *params) {
1081
0
  ngtcp2_transport_params *p = &conn->local.transport_params;
1082
0
  uint32_t chosen_version = p->version_info.chosen_version;
1083
1084
0
  *p = *params;
1085
1086
0
  if (conn->server) {
1087
0
    p->version_info.chosen_version = chosen_version;
1088
0
  } else {
1089
0
    p->version_info.chosen_version = conn->client_chosen_version;
1090
0
  }
1091
0
  p->version_info.available_versions = conn->vneg.available_versions;
1092
0
  p->version_info.available_versionslen = conn->vneg.available_versionslen;
1093
0
  p->version_info_present = 1;
1094
0
}
1095
1096
0
static void conn_update_skip_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns) {
1097
0
  const int64_t min_gap = 3;
1098
0
  uint8_t r;
1099
0
  int64_t gap;
1100
1101
0
  assert(INT64_MAX != pktns->tx.skip_pkt.next_pkt_num);
1102
1103
0
  conn->callbacks.rand(&r, 1, &conn->local.settings.rand_ctx);
1104
1105
0
  if (1LL << pktns->tx.skip_pkt.exponent >
1106
0
      (NGTCP2_MAX_PKT_NUM - min_gap) / ((int64_t)r + 1)) {
1107
0
    pktns->tx.skip_pkt.next_pkt_num = INT64_MAX;
1108
0
    return;
1109
0
  }
1110
1111
0
  gap = ((int64_t)r + 1) * (1LL << pktns->tx.skip_pkt.exponent++) + min_gap;
1112
1113
0
  if (pktns->tx.last_pkt_num > NGTCP2_MAX_PKT_NUM - gap) {
1114
0
    pktns->tx.skip_pkt.next_pkt_num = INT64_MAX;
1115
0
    return;
1116
0
  }
1117
1118
0
  pktns->tx.skip_pkt.next_pkt_num = pktns->tx.last_pkt_num + gap;
1119
1120
0
  ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON, "next skip pkn=%" PRId64,
1121
0
                   pktns->tx.skip_pkt.next_pkt_num);
1122
0
}
1123
1124
static int conn_handle_skip_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
1125
0
                                ngtcp2_tstamp ts) {
1126
0
  ngtcp2_rtb_entry *rtbent;
1127
0
  ngtcp2_pkt_hd hd;
1128
0
  int rv;
1129
1130
0
  assert(NGTCP2_PKTNS_ID_APPLICATION == pktns->id);
1131
1132
0
  if (pktns->tx.last_pkt_num + 1 != pktns->tx.skip_pkt.next_pkt_num) {
1133
0
    return 0;
1134
0
  }
1135
1136
0
  ngtcp2_pkt_hd_init(&hd, 0, NGTCP2_PKT_1RTT, NULL, NULL,
1137
0
                     pktns->tx.skip_pkt.next_pkt_num, 0, 0);
1138
1139
0
  rv = ngtcp2_rtb_entry_objalloc_new(&rtbent, &hd, NULL, ts, 0,
1140
0
                                     NGTCP2_RTB_ENTRY_FLAG_SKIP,
1141
0
                                     &conn->rtb_entry_objalloc);
1142
0
  if (rv != 0) {
1143
0
    assert(ngtcp2_err_is_fatal(rv));
1144
0
    return rv;
1145
0
  }
1146
1147
0
  rv = ngtcp2_rtb_add(&pktns->rtb, rtbent, &conn->cstat);
1148
0
  if (rv != 0) {
1149
0
    ngtcp2_rtb_entry_objalloc_del(rtbent, &conn->rtb_entry_objalloc,
1150
0
                                  &conn->frc_objalloc, conn->mem);
1151
0
    return rv;
1152
0
  }
1153
1154
0
  ++pktns->tx.last_pkt_num;
1155
1156
0
  conn_update_skip_pkt(conn, pktns);
1157
1158
0
  return 0;
1159
0
}
1160
1161
0
static size_t buflen_align(size_t buflen) {
1162
0
  return (buflen + 0x7) & (size_t)~0x7;
1163
0
}
1164
1165
0
static void *buf_align(void *buf) {
1166
0
  return (void *)((uintptr_t)((uint8_t *)buf + 0x7) & (uintptr_t)~0x7);
1167
0
}
1168
1169
0
static void *buf_advance(void *buf, size_t n) { return (uint8_t *)buf + n; }
1170
1171
static int conn_new(ngtcp2_conn **pconn, const ngtcp2_cid *dcid,
1172
                    const ngtcp2_cid *scid, const ngtcp2_path *path,
1173
                    uint32_t client_chosen_version, int callbacks_version,
1174
                    const ngtcp2_callbacks *callbacks, int settings_version,
1175
                    const ngtcp2_settings *settings,
1176
                    int transport_params_version,
1177
                    const ngtcp2_transport_params *params,
1178
0
                    const ngtcp2_mem *mem, void *user_data, int server) {
1179
0
  int rv;
1180
0
  ngtcp2_scid *scident;
1181
0
  void *buf, *tokenbuf;
1182
0
  size_t buflen;
1183
0
  uint8_t fixed_bit_byte;
1184
0
  size_t i;
1185
0
  uint32_t *preferred_versions;
1186
0
  ngtcp2_settings settingsbuf;
1187
0
  ngtcp2_transport_params paramsbuf;
1188
0
  ngtcp2_callbacks callbacksbuf;
1189
0
  uint64_t seed;
1190
0
  (void)settings_version;
1191
1192
0
  settings =
1193
0
    ngtcp2_settings_convert_to_latest(&settingsbuf, settings_version, settings);
1194
0
  params = ngtcp2_transport_params_convert_to_latest(
1195
0
    &paramsbuf, transport_params_version, params);
1196
0
  callbacks = ngtcp2_callbacks_convert_to_latest(&callbacksbuf,
1197
0
                                                 callbacks_version, callbacks);
1198
1199
0
  assert(settings->max_window <= NGTCP2_MAX_VARINT);
1200
0
  assert(settings->max_stream_window <= NGTCP2_MAX_VARINT);
1201
0
  assert(settings->max_tx_udp_payload_size >= NGTCP2_MAX_UDP_PAYLOAD_SIZE);
1202
0
  assert(settings->max_tx_udp_payload_size <= NGTCP2_MAX_TX_UDP_PAYLOAD_SIZE);
1203
0
  assert(settings->initial_pkt_num <= INT32_MAX);
1204
0
  assert(settings->initial_rtt);
1205
0
  assert(params->active_connection_id_limit >=
1206
0
         NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT);
1207
0
  assert(params->active_connection_id_limit <=
1208
0
         NGTCP2_DCIDTR_MAX_UNUSED_DCID_SIZE);
1209
0
  assert(params->initial_max_data <= NGTCP2_MAX_VARINT);
1210
0
  assert(params->initial_max_stream_data_bidi_local <= NGTCP2_MAX_VARINT);
1211
0
  assert(params->initial_max_stream_data_bidi_remote <= NGTCP2_MAX_VARINT);
1212
0
  assert(params->initial_max_stream_data_uni <= NGTCP2_MAX_VARINT);
1213
0
  assert((server && params->original_dcid_present) ||
1214
0
         (!server && !params->original_dcid_present));
1215
0
  assert(!params->initial_scid_present);
1216
0
  assert(server || !params->stateless_reset_token_present);
1217
0
  assert(server || !params->preferred_addr_present);
1218
0
  assert(server || !params->retry_scid_present);
1219
0
  assert(params->max_idle_timeout != UINT64_MAX);
1220
0
  assert(params->max_ack_delay < (1 << 14) * NGTCP2_MILLISECONDS);
1221
0
  assert(server || callbacks->client_initial);
1222
0
  assert(!server || callbacks->recv_client_initial);
1223
0
  assert(callbacks->recv_crypto_data);
1224
0
  assert(callbacks->encrypt);
1225
0
  assert(callbacks->decrypt);
1226
0
  assert(callbacks->hp_mask);
1227
0
  assert(server || callbacks->recv_retry);
1228
0
  assert(callbacks->rand);
1229
0
  assert(callbacks->get_new_connection_id2 || callbacks->get_new_connection_id);
1230
0
  assert(callbacks->update_key);
1231
0
  assert(callbacks->delete_crypto_aead_ctx);
1232
0
  assert(callbacks->delete_crypto_cipher_ctx);
1233
0
  assert(callbacks->get_path_challenge_data2 ||
1234
0
         callbacks->get_path_challenge_data);
1235
0
  assert(!server || !ngtcp2_is_reserved_version(client_chosen_version));
1236
1237
0
  for (i = 0; i < settings->pmtud_probeslen; ++i) {
1238
0
    assert(settings->pmtud_probes[i] > NGTCP2_MAX_UDP_PAYLOAD_SIZE);
1239
0
    assert(settings->pmtud_probes[i] <= NGTCP2_MAX_TX_UDP_PAYLOAD_SIZE);
1240
0
  }
1241
1242
0
  if (mem == NULL) {
1243
0
    mem = ngtcp2_mem_default();
1244
0
  }
1245
1246
0
  buflen = sizeof(ngtcp2_conn);
1247
0
  if (settings->qlog_write) {
1248
0
    buflen = buflen_align(buflen);
1249
0
    buflen += NGTCP2_QLOG_BUFLEN;
1250
0
  }
1251
1252
0
  if (settings->pmtud_probeslen) {
1253
0
    buflen = buflen_align(buflen);
1254
0
    buflen += sizeof(settings->pmtud_probes[0]) * settings->pmtud_probeslen;
1255
0
  }
1256
1257
0
  if (settings->preferred_versionslen) {
1258
0
    buflen = buflen_align(buflen);
1259
0
    buflen +=
1260
0
      sizeof(settings->preferred_versions[0]) * settings->preferred_versionslen;
1261
0
  }
1262
1263
0
  if (settings->available_versionslen) {
1264
0
    buflen = buflen_align(buflen);
1265
0
    buflen +=
1266
0
      sizeof(settings->available_versions[0]) * settings->available_versionslen;
1267
0
  } else if (server) {
1268
0
    if (settings->preferred_versionslen) {
1269
0
      buflen = buflen_align(buflen);
1270
0
      buflen += sizeof(settings->preferred_versions[0]) *
1271
0
                settings->preferred_versionslen;
1272
0
    }
1273
0
  } else if (!ngtcp2_is_reserved_version(client_chosen_version)) {
1274
0
    buflen = buflen_align(buflen);
1275
0
    buflen += sizeof(client_chosen_version);
1276
0
  }
1277
1278
0
  buf = ngtcp2_mem_calloc(mem, 1, buflen);
1279
0
  if (buf == NULL) {
1280
0
    return NGTCP2_ERR_NOMEM;
1281
0
  }
1282
1283
0
  *pconn = buf;
1284
0
  buf = buf_advance(buf, sizeof(ngtcp2_conn));
1285
1286
0
  (*pconn)->server = server;
1287
1288
0
  ngtcp2_objalloc_frame_chain_init(&(*pconn)->frc_objalloc, 16, mem);
1289
0
  ngtcp2_objalloc_rtb_entry_init(&(*pconn)->rtb_entry_objalloc, 16, mem);
1290
0
  ngtcp2_objalloc_strm_init(&(*pconn)->strm_objalloc, 16, mem);
1291
1292
0
  ngtcp2_dcidtr_init(&(*pconn)->dcid.dtr);
1293
1294
0
  ngtcp2_gaptr_init(&(*pconn)->dcid.seqgap, mem);
1295
1296
0
  ngtcp2_ksl_init(&(*pconn)->scid.set, cid_less, ksl_cid_less_search,
1297
0
                  sizeof(ngtcp2_cid), mem);
1298
1299
0
  ngtcp2_pq_init(&(*pconn)->scid.used, retired_ts_less, mem);
1300
1301
0
  callbacks->rand((uint8_t *)&seed, sizeof(seed), &settings->rand_ctx);
1302
0
  ngtcp2_map_init(&(*pconn)->strms, seed, mem);
1303
1304
0
  callbacks->rand((uint8_t *)&seed, sizeof(seed), &settings->rand_ctx);
1305
0
  ngtcp2_pcg32_init(&(*pconn)->pcg, seed);
1306
1307
0
  ngtcp2_pq_init(&(*pconn)->tx.strmq, cycle_less, mem);
1308
1309
0
  ngtcp2_idtr_init(&(*pconn)->remote.bidi.idtr, mem);
1310
1311
0
  ngtcp2_idtr_init(&(*pconn)->remote.uni.idtr, mem);
1312
1313
0
  ngtcp2_static_ringbuf_path_challenge_init(&(*pconn)->rx.path_challenge);
1314
1315
0
  ngtcp2_log_init(&(*pconn)->log, scid, settings->log_printf,
1316
0
                  settings->initial_ts, user_data);
1317
0
  ngtcp2_qlog_init(&(*pconn)->qlog, settings->qlog_write, settings->initial_ts,
1318
0
                   user_data);
1319
0
  if ((*pconn)->qlog.write) {
1320
0
    buf = buf_align(buf);
1321
0
    ngtcp2_buf_init(&(*pconn)->qlog.buf, buf, NGTCP2_QLOG_BUFLEN);
1322
0
    buf = buf_advance(buf, NGTCP2_QLOG_BUFLEN);
1323
0
  }
1324
1325
0
  (*pconn)->local.settings = *settings;
1326
1327
0
  if (settings->tokenlen) {
1328
0
    tokenbuf = ngtcp2_mem_malloc(mem, settings->tokenlen);
1329
0
    if (tokenbuf == NULL) {
1330
0
      rv = NGTCP2_ERR_NOMEM;
1331
0
      goto fail_token;
1332
0
    }
1333
0
    memcpy(tokenbuf, settings->token, settings->tokenlen);
1334
0
    (*pconn)->local.settings.token = tokenbuf;
1335
0
  } else {
1336
0
    (*pconn)->local.settings.token = NULL;
1337
0
  }
1338
1339
0
  if (settings->pmtud_probeslen) {
1340
0
    (*pconn)->local.settings.pmtud_probes = buf_align(buf);
1341
0
    buf = ngtcp2_cpymem(
1342
0
      (uint16_t *)(*pconn)->local.settings.pmtud_probes, settings->pmtud_probes,
1343
0
      sizeof(settings->pmtud_probes[0]) * settings->pmtud_probeslen);
1344
0
  }
1345
1346
0
  if (!(*pconn)->local.settings.original_version) {
1347
0
    (*pconn)->local.settings.original_version = client_chosen_version;
1348
0
  }
1349
1350
0
  ngtcp2_dcid_init(&(*pconn)->dcid.current, 0, dcid, NULL);
1351
0
  ngtcp2_dcid_set_path(&(*pconn)->dcid.current, path);
1352
1353
0
  assert((size_t)path->local.addrlen <= sizeof((*pconn)->hs_local_addr));
1354
1355
0
  memcpy(&(*pconn)->hs_local_addr, path->local.addr,
1356
0
         (size_t)path->local.addrlen);
1357
1358
0
  rv = ngtcp2_gaptr_push(&(*pconn)->dcid.seqgap, 0, 1);
1359
0
  if (rv != 0) {
1360
0
    goto fail_seqgap_push;
1361
0
  }
1362
1363
0
  conn_reset_conn_stat(*pconn, &(*pconn)->cstat);
1364
0
  (*pconn)->cstat.initial_rtt = settings->initial_rtt;
1365
1366
0
  ngtcp2_rst_init(&(*pconn)->rst);
1367
1368
0
  (*pconn)->cc_algo = settings->cc_algo;
1369
1370
0
  switch (settings->cc_algo) {
1371
0
  case NGTCP2_CC_ALGO_RENO:
1372
0
    ngtcp2_cc_reno_init(&(*pconn)->reno, &(*pconn)->log, &(*pconn)->cstat);
1373
1374
0
    break;
1375
0
  case NGTCP2_CC_ALGO_CUBIC:
1376
0
    ngtcp2_cc_cubic_init(&(*pconn)->cubic, &(*pconn)->log, &(*pconn)->cstat,
1377
0
                         &(*pconn)->rst);
1378
1379
0
    break;
1380
0
  case NGTCP2_CC_ALGO_BBR:
1381
0
    ngtcp2_cc_bbr_init(&(*pconn)->bbr, &(*pconn)->log, &(*pconn)->cstat,
1382
0
                       &(*pconn)->rst, settings->initial_ts, &(*pconn)->pcg);
1383
1384
0
    break;
1385
0
  default:
1386
0
    ngtcp2_unreachable();
1387
0
  }
1388
1389
0
  ngtcp2_static_ringbuf_path_history_init(&(*pconn)->path_history);
1390
1391
0
  ngtcp2_ratelim_init(&(*pconn)->glitch_rlim, settings->glitch_ratelim_burst,
1392
0
                      settings->glitch_ratelim_rate, settings->initial_ts);
1393
1394
0
  (*pconn)->callbacks = *callbacks;
1395
1396
0
  rv = pktns_new(&(*pconn)->in_pktns, NGTCP2_PKTNS_ID_INITIAL, &(*pconn)->rst,
1397
0
                 &(*pconn)->cc, settings->initial_pkt_num, &(*pconn)->log,
1398
0
                 &(*pconn)->qlog, &(*pconn)->rtb_entry_objalloc,
1399
0
                 &(*pconn)->frc_objalloc, mem);
1400
0
  if (rv != 0) {
1401
0
    goto fail_in_pktns_init;
1402
0
  }
1403
1404
0
  rv = pktns_new(&(*pconn)->hs_pktns, NGTCP2_PKTNS_ID_HANDSHAKE, &(*pconn)->rst,
1405
0
                 &(*pconn)->cc, settings->initial_pkt_num, &(*pconn)->log,
1406
0
                 &(*pconn)->qlog, &(*pconn)->rtb_entry_objalloc,
1407
0
                 &(*pconn)->frc_objalloc, mem);
1408
0
  if (rv != 0) {
1409
0
    goto fail_hs_pktns_init;
1410
0
  }
1411
1412
0
  pktns_init(&(*pconn)->pktns, NGTCP2_PKTNS_ID_APPLICATION, &(*pconn)->rst,
1413
0
             &(*pconn)->cc, settings->initial_pkt_num, &(*pconn)->log,
1414
0
             &(*pconn)->qlog, &(*pconn)->rtb_entry_objalloc,
1415
0
             &(*pconn)->frc_objalloc, mem);
1416
1417
0
  conn_update_skip_pkt(*pconn, &(*pconn)->pktns);
1418
1419
0
  scident = ngtcp2_mem_malloc(mem, sizeof(*scident));
1420
0
  if (scident == NULL) {
1421
0
    rv = NGTCP2_ERR_NOMEM;
1422
0
    goto fail_scident;
1423
0
  }
1424
1425
  /* Set stateless reset token later if it is available in the local
1426
     transport parameters */
1427
0
  ngtcp2_scid_init(scident, 0, scid);
1428
1429
0
  rv = ngtcp2_ksl_insert(&(*pconn)->scid.set, NULL, &scident->cid, scident);
1430
0
  if (rv != 0) {
1431
0
    goto fail_scid_set_insert;
1432
0
  }
1433
1434
0
  scident = NULL;
1435
1436
0
  if (settings->preferred_versionslen) {
1437
0
    if (!server && !ngtcp2_is_reserved_version(client_chosen_version)) {
1438
0
      for (i = 0; i < settings->preferred_versionslen; ++i) {
1439
0
        if (settings->preferred_versions[i] == client_chosen_version) {
1440
0
          break;
1441
0
        }
1442
0
      }
1443
1444
0
      assert(i < settings->preferred_versionslen);
1445
0
    }
1446
1447
0
    preferred_versions = buf_align(buf);
1448
0
    buf = buf_advance(preferred_versions, sizeof(preferred_versions[0]) *
1449
0
                                            settings->preferred_versionslen);
1450
1451
0
    for (i = 0; i < settings->preferred_versionslen; ++i) {
1452
0
      assert(ngtcp2_is_supported_version(settings->preferred_versions[i]));
1453
1454
0
      preferred_versions[i] = settings->preferred_versions[i];
1455
0
    }
1456
1457
0
    (*pconn)->vneg.preferred_versions = preferred_versions;
1458
0
    (*pconn)->vneg.preferred_versionslen = settings->preferred_versionslen;
1459
0
  }
1460
1461
0
  (*pconn)->local.settings.preferred_versions = NULL;
1462
0
  (*pconn)->local.settings.preferred_versionslen = 0;
1463
1464
0
  if (settings->available_versionslen) {
1465
0
    if (!server && !ngtcp2_is_reserved_version(client_chosen_version)) {
1466
0
      for (i = 0; i < settings->available_versionslen; ++i) {
1467
0
        if (settings->available_versions[i] == client_chosen_version) {
1468
0
          break;
1469
0
        }
1470
0
      }
1471
1472
0
      assert(i < settings->available_versionslen);
1473
0
    }
1474
1475
0
    for (i = 0; i < settings->available_versionslen; ++i) {
1476
0
      assert(ngtcp2_is_reserved_version(settings->available_versions[i]) ||
1477
0
             ngtcp2_is_supported_version(settings->available_versions[i]));
1478
0
    }
1479
1480
0
    (*pconn)->vneg.available_versions = buf_align(buf);
1481
0
    (*pconn)->vneg.available_versionslen =
1482
0
      sizeof(uint32_t) * settings->available_versionslen;
1483
1484
0
    buf = available_versions_init((*pconn)->vneg.available_versions,
1485
0
                                  settings->available_versions,
1486
0
                                  settings->available_versionslen);
1487
0
  } else if (server) {
1488
0
    if (settings->preferred_versionslen) {
1489
0
      (*pconn)->vneg.available_versions = buf_align(buf);
1490
0
      (*pconn)->vneg.available_versionslen =
1491
0
        sizeof(uint32_t) * settings->preferred_versionslen;
1492
1493
0
      buf = available_versions_init((*pconn)->vneg.available_versions,
1494
0
                                    settings->preferred_versions,
1495
0
                                    settings->preferred_versionslen);
1496
0
    } else {
1497
0
      (*pconn)->vneg.available_versions = server_default_available_versions;
1498
0
      (*pconn)->vneg.available_versionslen =
1499
0
        sizeof(server_default_available_versions);
1500
0
    }
1501
0
  } else if (!ngtcp2_is_reserved_version(client_chosen_version)) {
1502
0
    (*pconn)->vneg.available_versions = buf_align(buf);
1503
0
    (*pconn)->vneg.available_versionslen = sizeof(uint32_t);
1504
1505
0
    buf = available_versions_init((*pconn)->vneg.available_versions,
1506
0
                                  &client_chosen_version, 1);
1507
0
  }
1508
1509
0
  (*pconn)->local.settings.available_versions = NULL;
1510
0
  (*pconn)->local.settings.available_versionslen = 0;
1511
1512
0
  (*pconn)->client_chosen_version = client_chosen_version;
1513
1514
0
  conn_set_local_transport_params(*pconn, params);
1515
1516
0
  callbacks->rand(&fixed_bit_byte, 1, &settings->rand_ctx);
1517
0
  if (fixed_bit_byte & 1) {
1518
0
    (*pconn)->flags |= NGTCP2_CONN_FLAG_CLEAR_FIXED_BIT;
1519
0
  }
1520
1521
0
  (*pconn)->keep_alive.last_ts = UINT64_MAX;
1522
0
  (*pconn)->keep_alive.timeout = UINT64_MAX;
1523
1524
0
  (*pconn)->oscid = *scid;
1525
0
  (*pconn)->mem = mem;
1526
0
  (*pconn)->user_data = user_data;
1527
0
  (*pconn)->idle_ts = settings->initial_ts;
1528
0
  (*pconn)->handshake_confirmed_ts = UINT64_MAX;
1529
0
  (*pconn)->crypto.key_update.confirmed_ts = UINT64_MAX;
1530
0
  (*pconn)->tx.last_max_data_ts = UINT64_MAX;
1531
0
  (*pconn)->tx.pacing.next_ts = UINT64_MAX;
1532
0
  (*pconn)->tx.last_blocked_offset = UINT64_MAX;
1533
0
  (*pconn)->rx.preferred_addr.pkt_num = -1;
1534
0
  (*pconn)->early.discard_started_ts = UINT64_MAX;
1535
1536
0
  conn_reset_ecn_validation_state(*pconn);
1537
1538
0
  ngtcp2_qlog_start(&(*pconn)->qlog,
1539
0
                    server
1540
0
                      ? ((*pconn)->local.transport_params.retry_scid_present
1541
0
                           ? &(*pconn)->local.transport_params.retry_scid
1542
0
                           : &(*pconn)->local.transport_params.original_dcid)
1543
0
                      : dcid,
1544
0
                    server);
1545
1546
0
  return 0;
1547
1548
0
fail_scid_set_insert:
1549
0
  ngtcp2_mem_free(mem, scident);
1550
0
fail_scident:
1551
0
  pktns_del((*pconn)->hs_pktns, mem);
1552
0
fail_hs_pktns_init:
1553
0
  pktns_del((*pconn)->in_pktns, mem);
1554
0
fail_in_pktns_init:
1555
0
  ngtcp2_gaptr_free(&(*pconn)->dcid.seqgap);
1556
0
fail_seqgap_push:
1557
0
  ngtcp2_mem_free(mem, (uint8_t *)(*pconn)->local.settings.token);
1558
0
fail_token:
1559
0
  ngtcp2_mem_free(mem, *pconn);
1560
1561
0
  *pconn = NULL;
1562
1563
0
  return rv;
1564
0
}
1565
1566
int ngtcp2_conn_client_new_versioned(
1567
  ngtcp2_conn **pconn, const ngtcp2_cid *dcid, const ngtcp2_cid *scid,
1568
  const ngtcp2_path *path, uint32_t client_chosen_version,
1569
  int callbacks_version, const ngtcp2_callbacks *callbacks,
1570
  int settings_version, const ngtcp2_settings *settings,
1571
  int transport_params_version, const ngtcp2_transport_params *params,
1572
0
  const ngtcp2_mem *mem, void *user_data) {
1573
0
  int rv;
1574
1575
0
  rv = conn_new(pconn, dcid, scid, path, client_chosen_version,
1576
0
                callbacks_version, callbacks, settings_version, settings,
1577
0
                transport_params_version, params, mem, user_data, 0);
1578
0
  if (rv != 0) {
1579
0
    return rv;
1580
0
  }
1581
0
  (*pconn)->rcid = *dcid;
1582
0
  (*pconn)->state = NGTCP2_CS_CLIENT_INITIAL;
1583
0
  (*pconn)->local.bidi.next_stream_id = 0;
1584
0
  (*pconn)->local.uni.next_stream_id = 2;
1585
0
  (*pconn)->flags |= NGTCP2_CONN_FLAG_CRUMBLE_INITIAL_CRYPTO;
1586
1587
0
  rv = ngtcp2_conn_commit_local_transport_params(*pconn);
1588
0
  if (rv != 0) {
1589
0
    ngtcp2_conn_del(*pconn);
1590
0
    *pconn = NULL;
1591
1592
0
    return rv;
1593
0
  }
1594
1595
0
  return 0;
1596
0
}
1597
1598
int ngtcp2_conn_server_new_versioned(
1599
  ngtcp2_conn **pconn, const ngtcp2_cid *dcid, const ngtcp2_cid *scid,
1600
  const ngtcp2_path *path, uint32_t client_chosen_version,
1601
  int callbacks_version, const ngtcp2_callbacks *callbacks,
1602
  int settings_version, const ngtcp2_settings *settings,
1603
  int transport_params_version, const ngtcp2_transport_params *params,
1604
0
  const ngtcp2_mem *mem, void *user_data) {
1605
0
  int rv;
1606
1607
0
  rv = conn_new(pconn, dcid, scid, path, client_chosen_version,
1608
0
                callbacks_version, callbacks, settings_version, settings,
1609
0
                transport_params_version, params, mem, user_data, 1);
1610
0
  if (rv != 0) {
1611
0
    return rv;
1612
0
  }
1613
1614
0
  (*pconn)->state = NGTCP2_CS_SERVER_INITIAL;
1615
0
  (*pconn)->local.bidi.next_stream_id = 1;
1616
0
  (*pconn)->local.uni.next_stream_id = 3;
1617
1618
0
  if ((*pconn)->local.settings.tokenlen) {
1619
    /* Usage of token lifts amplification limit */
1620
0
    (*pconn)->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
1621
0
  }
1622
1623
0
  return 0;
1624
0
}
1625
1626
/*
1627
 * conn_fc_credits returns the number of bytes allowed to be sent to
1628
 * the given stream.  Both connection and stream level flow control
1629
 * credits are considered.
1630
 */
1631
0
static uint64_t conn_fc_credits(ngtcp2_conn *conn, ngtcp2_strm *strm) {
1632
0
  return ngtcp2_min_uint64(strm->tx.max_offset - strm->tx.offset,
1633
0
                           conn->tx.max_offset - conn->tx.offset);
1634
0
}
1635
1636
/*
1637
 * conn_enforce_flow_control returns the number of bytes allowed to be
1638
 * sent to the given stream.  |len| might be shorted because of
1639
 * available flow control credits.
1640
 */
1641
static uint64_t conn_enforce_flow_control(ngtcp2_conn *conn, ngtcp2_strm *strm,
1642
0
                                          uint64_t len) {
1643
0
  uint64_t fc_credits = conn_fc_credits(conn, strm);
1644
0
  return ngtcp2_min_uint64(len, fc_credits);
1645
0
}
1646
1647
0
static int delete_strms_each(void *data, void *ptr) {
1648
0
  ngtcp2_conn *conn = ptr;
1649
0
  ngtcp2_strm *s = data;
1650
1651
0
  ngtcp2_strm_free(s);
1652
0
  ngtcp2_objalloc_strm_release(&conn->strm_objalloc, s);
1653
1654
0
  return 0;
1655
0
}
1656
1657
0
static void conn_vneg_crypto_free(ngtcp2_conn *conn) {
1658
0
  if (conn->vneg.rx.ckm) {
1659
0
    conn_call_delete_crypto_aead_ctx(conn, &conn->vneg.rx.ckm->aead_ctx);
1660
0
  }
1661
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->vneg.rx.hp_ctx);
1662
1663
0
  if (conn->vneg.tx.ckm) {
1664
0
    conn_call_delete_crypto_aead_ctx(conn, &conn->vneg.tx.ckm->aead_ctx);
1665
0
  }
1666
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->vneg.tx.hp_ctx);
1667
1668
0
  ngtcp2_crypto_km_del(conn->vneg.rx.ckm, conn->mem);
1669
0
  ngtcp2_crypto_km_del(conn->vneg.tx.ckm, conn->mem);
1670
0
}
1671
1672
0
void ngtcp2_conn_del(ngtcp2_conn *conn) {
1673
0
  if (conn == NULL) {
1674
0
    return;
1675
0
  }
1676
1677
0
  ngtcp2_qlog_end(&conn->qlog);
1678
1679
0
  if (conn->early.ckm) {
1680
0
    conn_call_delete_crypto_aead_ctx(conn, &conn->early.ckm->aead_ctx);
1681
0
  }
1682
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->early.hp_ctx);
1683
1684
0
  if (conn->crypto.key_update.old_rx_ckm) {
1685
0
    conn_call_delete_crypto_aead_ctx(
1686
0
      conn, &conn->crypto.key_update.old_rx_ckm->aead_ctx);
1687
0
  }
1688
0
  if (conn->crypto.key_update.new_rx_ckm) {
1689
0
    conn_call_delete_crypto_aead_ctx(
1690
0
      conn, &conn->crypto.key_update.new_rx_ckm->aead_ctx);
1691
0
  }
1692
0
  if (conn->crypto.key_update.new_tx_ckm) {
1693
0
    conn_call_delete_crypto_aead_ctx(
1694
0
      conn, &conn->crypto.key_update.new_tx_ckm->aead_ctx);
1695
0
  }
1696
1697
0
  if (conn->pktns.crypto.rx.ckm) {
1698
0
    conn_call_delete_crypto_aead_ctx(conn,
1699
0
                                     &conn->pktns.crypto.rx.ckm->aead_ctx);
1700
0
  }
1701
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->pktns.crypto.rx.hp_ctx);
1702
1703
0
  if (conn->pktns.crypto.tx.ckm) {
1704
0
    conn_call_delete_crypto_aead_ctx(conn,
1705
0
                                     &conn->pktns.crypto.tx.ckm->aead_ctx);
1706
0
  }
1707
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->pktns.crypto.tx.hp_ctx);
1708
1709
0
  if (conn->hs_pktns) {
1710
0
    if (conn->hs_pktns->crypto.rx.ckm) {
1711
0
      conn_call_delete_crypto_aead_ctx(
1712
0
        conn, &conn->hs_pktns->crypto.rx.ckm->aead_ctx);
1713
0
    }
1714
0
    conn_call_delete_crypto_cipher_ctx(conn, &conn->hs_pktns->crypto.rx.hp_ctx);
1715
1716
0
    if (conn->hs_pktns->crypto.tx.ckm) {
1717
0
      conn_call_delete_crypto_aead_ctx(
1718
0
        conn, &conn->hs_pktns->crypto.tx.ckm->aead_ctx);
1719
0
    }
1720
0
    conn_call_delete_crypto_cipher_ctx(conn, &conn->hs_pktns->crypto.tx.hp_ctx);
1721
0
  }
1722
0
  if (conn->in_pktns) {
1723
0
    if (conn->in_pktns->crypto.rx.ckm) {
1724
0
      conn_call_delete_crypto_aead_ctx(
1725
0
        conn, &conn->in_pktns->crypto.rx.ckm->aead_ctx);
1726
0
    }
1727
0
    conn_call_delete_crypto_cipher_ctx(conn, &conn->in_pktns->crypto.rx.hp_ctx);
1728
1729
0
    if (conn->in_pktns->crypto.tx.ckm) {
1730
0
      conn_call_delete_crypto_aead_ctx(
1731
0
        conn, &conn->in_pktns->crypto.tx.ckm->aead_ctx);
1732
0
    }
1733
0
    conn_call_delete_crypto_cipher_ctx(conn, &conn->in_pktns->crypto.tx.hp_ctx);
1734
0
  }
1735
1736
0
  conn_call_delete_crypto_aead_ctx(conn, &conn->crypto.retry_aead_ctx);
1737
1738
0
  ngtcp2_transport_params_del(conn->remote.transport_params, conn->mem);
1739
0
  ngtcp2_transport_params_del(conn->remote.pending_transport_params, conn->mem);
1740
1741
0
  conn_vneg_crypto_free(conn);
1742
1743
0
  ngtcp2_mem_free(conn->mem, conn->crypto.decrypt_buf.base);
1744
0
  ngtcp2_mem_free(conn->mem, conn->crypto.decrypt_hp_buf.base);
1745
0
  ngtcp2_mem_free(conn->mem, (uint8_t *)conn->local.settings.token);
1746
1747
0
  ngtcp2_crypto_km_del(conn->crypto.key_update.old_rx_ckm, conn->mem);
1748
0
  ngtcp2_crypto_km_del(conn->crypto.key_update.new_rx_ckm, conn->mem);
1749
0
  ngtcp2_crypto_km_del(conn->crypto.key_update.new_tx_ckm, conn->mem);
1750
0
  ngtcp2_crypto_km_del(conn->early.ckm, conn->mem);
1751
1752
0
  pktns_free(&conn->pktns, conn->mem);
1753
0
  pktns_del(conn->hs_pktns, conn->mem);
1754
0
  pktns_del(conn->in_pktns, conn->mem);
1755
1756
0
  ngtcp2_pmtud_del(conn->pmtud);
1757
0
  ngtcp2_pv_del(conn->pv);
1758
1759
0
  ngtcp2_mem_free(conn->mem, (uint8_t *)conn->rx.ccerr.reason);
1760
1761
0
  ngtcp2_idtr_free(&conn->remote.uni.idtr);
1762
0
  ngtcp2_idtr_free(&conn->remote.bidi.idtr);
1763
0
  ngtcp2_pq_free(&conn->tx.strmq);
1764
0
  ngtcp2_map_each(&conn->strms, delete_strms_each, (void *)conn);
1765
0
  ngtcp2_map_free(&conn->strms);
1766
1767
0
  ngtcp2_pq_free(&conn->scid.used);
1768
0
  delete_scid(&conn->scid.set, conn->mem);
1769
0
  ngtcp2_ksl_free(&conn->scid.set);
1770
0
  ngtcp2_gaptr_free(&conn->dcid.seqgap);
1771
1772
0
  ngtcp2_objalloc_free(&conn->strm_objalloc);
1773
0
  ngtcp2_objalloc_free(&conn->rtb_entry_objalloc);
1774
0
  ngtcp2_objalloc_free(&conn->frc_objalloc);
1775
1776
0
  ngtcp2_mem_free(conn->mem, conn);
1777
0
}
1778
1779
/*
1780
 * conn_compute_ack_delay computes ACK delay for outgoing protected
1781
 * ACK.
1782
 */
1783
0
static ngtcp2_duration conn_compute_ack_delay(ngtcp2_conn *conn) {
1784
0
  return ngtcp2_min_uint64(
1785
0
    conn->local.transport_params.max_ack_delay,
1786
0
    ngtcp2_max_uint64(conn->cstat.smoothed_rtt / 8, NGTCP2_NANOSECONDS));
1787
0
}
1788
1789
/*
1790
 * conn_ppe_write_frame writes |fr| to |ppe|.  If |hd_logged| is not
1791
 * NULL and |*hd_logged| is zero, packet header is logged, and 1 is
1792
 * assigned to |*hd_logged|.
1793
 *
1794
 * This function returns 0 if it succeeds, or one of the following
1795
 * negative error codes:
1796
 *
1797
 * NGTCP2_ERR_NOBUF
1798
 *     Buffer is too small.
1799
 */
1800
static int conn_ppe_write_frame_hd_log(ngtcp2_conn *conn, ngtcp2_ppe *ppe,
1801
                                       int *hd_logged, const ngtcp2_pkt_hd *hd,
1802
0
                                       ngtcp2_frame *fr) {
1803
0
  int rv;
1804
1805
0
  rv = ngtcp2_ppe_encode_frame(ppe, fr);
1806
0
  if (rv != 0) {
1807
0
    assert(NGTCP2_ERR_NOBUF == rv);
1808
0
    return rv;
1809
0
  }
1810
1811
0
  if (hd_logged && !*hd_logged) {
1812
0
    *hd_logged = 1;
1813
0
    ngtcp2_log_tx_pkt_hd(&conn->log, hd);
1814
0
    ngtcp2_qlog_pkt_sent_start(&conn->qlog);
1815
0
  }
1816
1817
0
  ngtcp2_log_tx_fr(&conn->log, hd, fr);
1818
0
  ngtcp2_qlog_write_frame(&conn->qlog, fr);
1819
1820
0
  return 0;
1821
0
}
1822
1823
/*
1824
 * conn_ppe_write_frame writes |fr| to |ppe|.
1825
 *
1826
 * This function returns 0 if it succeeds, or one of the following
1827
 * negative error codes:
1828
 *
1829
 * NGTCP2_ERR_NOBUF
1830
 *     Buffer is too small.
1831
 */
1832
static int conn_ppe_write_frame(ngtcp2_conn *conn, ngtcp2_ppe *ppe,
1833
0
                                const ngtcp2_pkt_hd *hd, ngtcp2_frame *fr) {
1834
0
  return conn_ppe_write_frame_hd_log(conn, ppe, NULL, hd, fr);
1835
0
}
1836
1837
/*
1838
 * conn_on_pkt_sent is called when new non-ACK-only packet is sent.
1839
 *
1840
 * This function returns 0 if it succeeds, or one of the following
1841
 * negative error codes:
1842
 *
1843
 * NGTCP2_ERR_NOMEM
1844
 *     Out of memory
1845
 */
1846
static int conn_on_pkt_sent(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
1847
0
                            ngtcp2_rtb_entry *ent) {
1848
0
  ngtcp2_rtb *rtb = &pktns->rtb;
1849
0
  ngtcp2_cc_pkt cc_pkt;
1850
0
  int rv;
1851
1852
0
  if ((ent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
1853
0
      conn->cc.on_pkt_sent) {
1854
0
    conn->cc.on_pkt_sent(
1855
0
      &conn->cc, &conn->cstat,
1856
0
      ngtcp2_cc_pkt_init(&cc_pkt, ent->hd.pkt_num, ent->pktlen, pktns->id,
1857
0
                         ent->ts, /* lost = */ 0,
1858
0
                         /* tx_in_flight = */ 0, /* is_app_limited = */ 0));
1859
0
  }
1860
1861
  /* This function implements OnPacketSent, but it handles only
1862
     non-ACK-only packet. */
1863
0
  rv = ngtcp2_rtb_add(rtb, ent, &conn->cstat);
1864
0
  if (rv != 0) {
1865
0
    return rv;
1866
0
  }
1867
1868
0
  if (ent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
1869
0
    conn->cstat.last_tx_pkt_ts[pktns->id] = ent->ts;
1870
0
  }
1871
1872
0
  ngtcp2_conn_set_loss_detection_timer(conn, ent->ts);
1873
1874
0
  return 0;
1875
0
}
1876
1877
/*
1878
 * pktns_select_pkt_numlen selects shortest packet number encoding for
1879
 * the next packet number based on the largest acknowledged packet
1880
 * number.  It returns the number of bytes to encode the packet
1881
 * number.
1882
 */
1883
0
static size_t pktns_select_pkt_numlen(ngtcp2_pktns *pktns) {
1884
0
  int64_t pkt_num = pktns->tx.last_pkt_num + 1;
1885
0
  ngtcp2_rtb *rtb = &pktns->rtb;
1886
0
  int64_t n = pkt_num - rtb->largest_acked_tx_pkt_num;
1887
1888
0
  if (NGTCP2_MAX_PKT_NUM / 2 < n) {
1889
0
    return 4;
1890
0
  }
1891
1892
0
  n = n * 2 - 1;
1893
1894
0
  if (n > 0xFFFFFF) {
1895
0
    return 4;
1896
0
  }
1897
0
  if (n > 0xFFFF) {
1898
0
    return 3;
1899
0
  }
1900
0
  if (n > 0xFF) {
1901
0
    return 2;
1902
0
  }
1903
0
  return 1;
1904
0
}
1905
1906
/*
1907
 * conn_cwnd_is_zero returns nonzero if the number of bytes the local
1908
 * endpoint can sent at this time is zero.
1909
 */
1910
0
static int conn_cwnd_is_zero(ngtcp2_conn *conn) {
1911
0
  uint64_t bytes_in_flight = conn->cstat.bytes_in_flight;
1912
0
  uint64_t cwnd = conn->cstat.cwnd;
1913
1914
0
  if (bytes_in_flight >= cwnd) {
1915
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_LDC,
1916
0
                     "cwnd limited bytes_in_flight=%lu cwnd=%lu",
1917
0
                     bytes_in_flight, cwnd);
1918
0
  }
1919
1920
0
  return bytes_in_flight >= cwnd;
1921
0
}
1922
1923
/*
1924
 * conn_retry_early_payloadlen returns the estimated wire length of
1925
 * the first STREAM frame of 0-RTT packet which should be
1926
 * retransmitted due to Retry packet.
1927
 */
1928
0
static uint64_t conn_retry_early_payloadlen(ngtcp2_conn *conn) {
1929
0
  ngtcp2_frame_chain *frc;
1930
0
  ngtcp2_strm *strm;
1931
0
  uint64_t len;
1932
1933
0
  if (conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) {
1934
0
    return 0;
1935
0
  }
1936
1937
0
  for (; !ngtcp2_pq_empty(&conn->tx.strmq);) {
1938
0
    strm = ngtcp2_conn_tx_strmq_top(conn);
1939
0
    if (ngtcp2_strm_streamfrq_empty(strm)) {
1940
0
      ngtcp2_conn_tx_strmq_pop(conn);
1941
0
      continue;
1942
0
    }
1943
1944
0
    frc = ngtcp2_strm_streamfrq_top(strm);
1945
1946
0
    len = ngtcp2_vec_len(frc->fr.stream.data, frc->fr.stream.datacnt) +
1947
0
          NGTCP2_STREAM_OVERHEAD;
1948
1949
    /* Take the min because in conn_should_pad_pkt we take max in
1950
       order to deal with unbreakable DATAGRAM. */
1951
0
    return ngtcp2_min_uint64(len, NGTCP2_MIN_COALESCED_PAYLOADLEN);
1952
0
  }
1953
1954
0
  return 0;
1955
0
}
1956
1957
/*
1958
 * conn_verify_dcid verifies that destination connection ID in |hd| is
1959
 * valid for the connection.  If it is successfully verified and the
1960
 * remote endpoint uses new DCID in the packet, nonzero value is
1961
 * assigned to |*pnew_cid_used| if it is not NULL.  Otherwise 0 is
1962
 * assigned to it.
1963
 *
1964
 * This function returns 0 if it succeeds, or one of the following
1965
 * negative error codes:
1966
 *
1967
 * NGTCP2_ERR_NOMEM
1968
 *     Out of memory.
1969
 * NGTCP2_ERR_INVALID_ARGUMENT
1970
 *     |dcid| is not known to the local endpoint.
1971
 */
1972
static int conn_verify_dcid(ngtcp2_conn *conn, int *pnew_cid_used,
1973
0
                            const ngtcp2_pkt_hd *hd) {
1974
0
  ngtcp2_ksl_it it;
1975
0
  ngtcp2_scid *scid;
1976
0
  int rv;
1977
1978
0
  it = ngtcp2_ksl_lower_bound(&conn->scid.set, &hd->dcid);
1979
0
  if (ngtcp2_ksl_it_end(&it)) {
1980
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
1981
0
  }
1982
1983
0
  scid = ngtcp2_ksl_it_get(&it);
1984
0
  if (!ngtcp2_cid_eq(&scid->cid, &hd->dcid)) {
1985
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
1986
0
  }
1987
1988
0
  if (!(scid->flags & NGTCP2_SCID_FLAG_USED)) {
1989
0
    scid->flags |= NGTCP2_SCID_FLAG_USED;
1990
1991
0
    if (scid->pe.index == NGTCP2_PQ_BAD_INDEX) {
1992
0
      rv = ngtcp2_pq_push(&conn->scid.used, &scid->pe);
1993
0
      if (rv != 0) {
1994
0
        return rv;
1995
0
      }
1996
0
    }
1997
1998
0
    if (pnew_cid_used) {
1999
0
      *pnew_cid_used = 1;
2000
0
    }
2001
0
  } else if (pnew_cid_used) {
2002
0
    *pnew_cid_used = 0;
2003
0
  }
2004
2005
0
  return 0;
2006
0
}
2007
2008
static int conn_can_send_next_pkt(ngtcp2_conn *conn, size_t left,
2009
0
                                  uint64_t min_payloadlen) {
2010
  /* TODO the next packet type should be taken into account */
2011
0
  return left >=
2012
         /* TODO Assuming that pkt_num is encoded in 1 byte. */
2013
0
         NGTCP2_MIN_LONG_HEADERLEN + conn->dcid.current.cid.datalen +
2014
0
           conn->oscid.datalen + NGTCP2_PKT_LENGTHLEN - 1 + min_payloadlen +
2015
0
           NGTCP2_MAX_AEAD_OVERHEAD;
2016
0
}
2017
2018
/*
2019
 * conn_should_pad_pkt returns nonzero if the packet should be padded.
2020
 * |type| is the type of packet.  |left| is the space left in packet
2021
 * buffer.  |write_datalen| is the number of bytes which will be sent
2022
 * in the next, coalesced 0-RTT packet.
2023
 */
2024
static int conn_should_pad_pkt(ngtcp2_conn *conn, uint8_t type, size_t left,
2025
                               uint64_t write_datalen, int ack_eliciting,
2026
0
                               int require_padding) {
2027
0
  uint64_t min_payloadlen;
2028
2029
0
  if (type == NGTCP2_PKT_INITIAL) {
2030
0
    if (conn->server) {
2031
0
      if (!ack_eliciting) {
2032
0
        return 0;
2033
0
      }
2034
2035
0
      if ((conn->hs_pktns->crypto.tx.ckm &&
2036
0
           (conn->hs_pktns->rtb.probe_pkt_left ||
2037
0
            !ngtcp2_strm_streamfrq_empty(&conn->hs_pktns->crypto.strm) ||
2038
0
            !ngtcp2_acktr_empty(&conn->hs_pktns->acktr))) ||
2039
0
          conn->pktns.crypto.tx.ckm) {
2040
        /* If we have something to send in Handshake or 1RTT packet,
2041
           then add PADDING in that packet. */
2042
0
        min_payloadlen = NGTCP2_MIN_COALESCED_PAYLOADLEN;
2043
0
      } else {
2044
0
        return 1;
2045
0
      }
2046
0
    } else {
2047
0
      if (conn->hs_pktns->crypto.tx.ckm &&
2048
0
          (conn->hs_pktns->rtb.probe_pkt_left ||
2049
0
           !ngtcp2_strm_streamfrq_empty(&conn->hs_pktns->crypto.strm) ||
2050
0
           !ngtcp2_acktr_empty(&conn->hs_pktns->acktr))) {
2051
        /* If we have something to send in Handshake packet, then add
2052
           PADDING in Handshake packet. */
2053
0
        min_payloadlen = NGTCP2_MIN_COALESCED_PAYLOADLEN;
2054
0
      } else if (conn->early.ckm && write_datalen > 0) {
2055
        /* If we have something to send in 0RTT packet, then add
2056
           PADDING in that packet.  Take maximum in case that
2057
           write_datalen includes DATAGRAM which cannot be split. */
2058
0
        min_payloadlen =
2059
0
          ngtcp2_max_uint64(write_datalen, NGTCP2_MIN_COALESCED_PAYLOADLEN);
2060
0
      } else {
2061
0
        return 1;
2062
0
      }
2063
0
    }
2064
2065
0
    return !conn_can_send_next_pkt(conn, left, min_payloadlen);
2066
0
  }
2067
2068
0
  assert(type == NGTCP2_PKT_HANDSHAKE);
2069
2070
0
  if (!require_padding) {
2071
    /* If we have 1RTT key, pad this Handshake packet so that the next
2072
       1RTT packet can be squeezed into the same GSO buffer. */
2073
0
    return conn->pktns.crypto.tx.ckm &&
2074
0
           !conn_can_send_next_pkt(conn, left, NGTCP2_MIN_COALESCED_PAYLOADLEN);
2075
0
  }
2076
2077
0
  if (!conn->pktns.crypto.tx.ckm) {
2078
0
    return 1;
2079
0
  }
2080
2081
  /* We might send Handshake packet even if exceeding CWND.  In that
2082
     case, we do not write non-probe 1RTT packet. */
2083
0
  if (conn_cwnd_is_zero(conn) && conn->pktns.rtb.probe_pkt_left == 0) {
2084
0
    return 1;
2085
0
  }
2086
2087
0
  return !conn_can_send_next_pkt(conn, left, NGTCP2_MIN_COALESCED_PAYLOADLEN);
2088
0
}
2089
2090
0
static void conn_restart_timer_on_write(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2091
0
  conn->idle_ts = ts;
2092
0
  conn->flags &= (uint32_t)~NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE;
2093
0
}
2094
2095
0
static void conn_restart_timer_on_read(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2096
0
  conn->idle_ts = ts;
2097
0
  conn->flags |= NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE;
2098
0
}
2099
2100
/*
2101
 * conn_keep_alive_enabled returns nonzero if keep-alive is enabled.
2102
 */
2103
0
static int conn_keep_alive_enabled(ngtcp2_conn *conn) {
2104
0
  return conn->keep_alive.last_ts != UINT64_MAX &&
2105
0
         conn->keep_alive.timeout != UINT64_MAX;
2106
0
}
2107
2108
/*
2109
 * conn_keep_alive_expired returns nonzero if keep-alive timer has
2110
 * expired.
2111
 */
2112
0
static int conn_keep_alive_expired(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2113
0
  return ngtcp2_tstamp_elapsed(conn->keep_alive.last_ts,
2114
0
                               conn->keep_alive.timeout, ts);
2115
0
}
2116
2117
/*
2118
 * conn_keep_alive_expiry returns the expiry time of keep-alive timer.
2119
 */
2120
0
static ngtcp2_tstamp conn_keep_alive_expiry(ngtcp2_conn *conn) {
2121
0
  if ((conn->flags & NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED) ||
2122
0
      !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) ||
2123
0
      !conn_keep_alive_enabled(conn) ||
2124
0
      conn->keep_alive.last_ts >= UINT64_MAX - conn->keep_alive.timeout) {
2125
0
    return UINT64_MAX;
2126
0
  }
2127
2128
0
  return conn->keep_alive.last_ts + conn->keep_alive.timeout;
2129
0
}
2130
2131
/*
2132
 * conn_cancel_expired_keep_alive_timer cancels the expired keep-alive
2133
 * timer.
2134
 */
2135
static void conn_cancel_expired_keep_alive_timer(ngtcp2_conn *conn,
2136
0
                                                 ngtcp2_tstamp ts) {
2137
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED) &&
2138
0
      conn_keep_alive_expired(conn, ts)) {
2139
0
    conn->flags |= NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED;
2140
0
  }
2141
0
}
2142
2143
/*
2144
 * conn_update_keep_alive_last_ts updates the base time point of
2145
 * keep-alive timer.
2146
 */
2147
static void conn_update_keep_alive_last_ts(ngtcp2_conn *conn,
2148
0
                                           ngtcp2_tstamp ts) {
2149
0
  conn->keep_alive.last_ts = ts;
2150
0
  conn->flags &= (uint32_t)~NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED;
2151
0
}
2152
2153
void ngtcp2_conn_set_keep_alive_timeout(ngtcp2_conn *conn,
2154
0
                                        ngtcp2_duration timeout) {
2155
0
  if (timeout == 0) {
2156
0
    timeout = UINT64_MAX;
2157
0
  }
2158
2159
0
  conn->keep_alive.timeout = timeout;
2160
0
}
2161
2162
static void conn_cancel_expired_pkt_tx_timer(ngtcp2_conn *conn,
2163
0
                                             ngtcp2_tstamp ts) {
2164
0
  if (conn->tx.pacing.next_ts == UINT64_MAX) {
2165
0
    return;
2166
0
  }
2167
2168
0
  if (conn->tx.pacing.next_ts > ts) {
2169
0
    return;
2170
0
  }
2171
2172
0
  if (ts > conn->tx.pacing.next_ts) {
2173
0
    conn->tx.pacing.compensation += ts - conn->tx.pacing.next_ts;
2174
0
  }
2175
2176
0
  conn->tx.pacing.next_ts = UINT64_MAX;
2177
0
}
2178
2179
0
static int conn_pacing_pkt_tx_allowed(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2180
0
  if (conn->tx.pacing.next_ts == UINT64_MAX) {
2181
0
    return 1;
2182
0
  }
2183
2184
0
  if (conn->tx.pacing.next_ts > ts) {
2185
0
    return 0;
2186
0
  }
2187
2188
0
  conn->tx.pacing.compensation += ts - conn->tx.pacing.next_ts;
2189
0
  conn->tx.pacing.next_ts = UINT64_MAX;
2190
2191
0
  return 1;
2192
0
}
2193
2194
0
static uint8_t conn_pkt_flags(ngtcp2_conn *conn) {
2195
0
  if (conn->remote.transport_params &&
2196
0
      conn->remote.transport_params->grease_quic_bit &&
2197
0
      (conn->flags & NGTCP2_CONN_FLAG_CLEAR_FIXED_BIT)) {
2198
0
    return NGTCP2_PKT_FLAG_FIXED_BIT_CLEAR;
2199
0
  }
2200
2201
0
  return NGTCP2_PKT_FLAG_NONE;
2202
0
}
2203
2204
0
static uint8_t conn_pkt_flags_long(ngtcp2_conn *conn) {
2205
0
  return NGTCP2_PKT_FLAG_LONG_FORM | conn_pkt_flags(conn);
2206
0
}
2207
2208
0
static uint8_t conn_pkt_flags_short(ngtcp2_conn *conn) {
2209
0
  return (uint8_t)(conn_pkt_flags(conn) | ((conn->pktns.crypto.tx.ckm->flags &
2210
0
                                            NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE)
2211
0
                                             ? NGTCP2_PKT_FLAG_KEY_PHASE
2212
0
                                             : NGTCP2_PKT_FLAG_NONE));
2213
0
}
2214
2215
/*
2216
 * conn_cut_crypto_frame splits frc->fr.stream by removing
2217
 * |removed_data| from frc->fr.stream.data[0].  frc->fr.stream.data[0]
2218
 * must contain |removed_data|, and frc->fr.stream.datacnt >= 1.  New
2219
 * ngtcp2_frame_chain object that contains |removed_data| is created,
2220
 * and pushed to |crypto_strm| via ngtcp2_strm_streamfrq_push.  If
2221
 * there are data following the removed part of data, new
2222
 * ngtcp2_frame_chain object is created for it, and frc->next points
2223
 * to the object.
2224
 *
2225
 * This function returns 0 if it succeeds, or one of the following
2226
 * negative error codes:
2227
 *
2228
 * NGTCP2_ERR_NOMEM
2229
 *     Out of memory
2230
 */
2231
static int conn_cut_crypto_frame(ngtcp2_conn *conn, ngtcp2_frame_chain *frc,
2232
                                 ngtcp2_strm *crypto_strm,
2233
0
                                 const ngtcp2_vec *removed_data) {
2234
0
  ngtcp2_vec *data = frc->fr.stream.data;
2235
0
  size_t datacnt = frc->fr.stream.datacnt;
2236
0
  size_t ndatacnt;
2237
0
  ngtcp2_frame_chain *right_frc = NULL, *removed_frc;
2238
0
  size_t offset;
2239
0
  int rv;
2240
2241
0
  assert(datacnt);
2242
0
  assert(data[0].base < removed_data->base);
2243
0
  assert(ngtcp2_vec_end(removed_data) <= ngtcp2_vec_end(&data[0]));
2244
2245
0
  offset = (size_t)(removed_data->base - data->base);
2246
2247
0
  rv = ngtcp2_frame_chain_stream_datacnt_objalloc_new(
2248
0
    &removed_frc, 1, &conn->frc_objalloc, conn->mem);
2249
0
  if (rv != 0) {
2250
0
    return rv;
2251
0
  }
2252
2253
  /* ngtcp2_frame_chain for the removed data */
2254
0
  removed_frc->fr.stream.type = NGTCP2_FRAME_CRYPTO;
2255
0
  removed_frc->fr.stream.flags = 0;
2256
0
  removed_frc->fr.stream.fin = 0;
2257
0
  removed_frc->fr.stream.stream_id = 0;
2258
0
  removed_frc->fr.stream.offset = frc->fr.stream.offset + offset;
2259
0
  removed_frc->fr.stream.datacnt = 1;
2260
0
  removed_frc->fr.stream.data[0] = (ngtcp2_vec){
2261
0
    .base = data->base + offset,
2262
0
    .len = removed_data->len,
2263
0
  };
2264
2265
0
  rv = ngtcp2_strm_streamfrq_push(crypto_strm, removed_frc);
2266
0
  if (rv != 0) {
2267
0
    ngtcp2_frame_chain_objalloc_del(removed_frc, &conn->frc_objalloc,
2268
0
                                    conn->mem);
2269
0
    return rv;
2270
0
  }
2271
2272
0
  if (data[0].len == offset + removed_data->len) {
2273
0
    ndatacnt = datacnt - 1;
2274
0
  } else {
2275
0
    ndatacnt = datacnt;
2276
0
  }
2277
2278
0
  if (ndatacnt) {
2279
    /* ngtcp2_frame_chain after the removed data */
2280
0
    rv = ngtcp2_frame_chain_stream_datacnt_objalloc_new(
2281
0
      &right_frc, ndatacnt, &conn->frc_objalloc, conn->mem);
2282
0
    if (rv != 0) {
2283
0
      return rv;
2284
0
    }
2285
2286
0
    right_frc->fr.stream.type = NGTCP2_FRAME_CRYPTO;
2287
0
    right_frc->fr.stream.offset =
2288
0
      removed_frc->fr.stream.offset + removed_frc->fr.stream.data->len;
2289
0
    right_frc->fr.stream.datacnt = 0;
2290
0
    ngtcp2_vec_split(right_frc->fr.stream.data, &right_frc->fr.stream.datacnt,
2291
0
                     data, &datacnt, offset + removed_data->len, ndatacnt);
2292
2293
0
    assert(ndatacnt == right_frc->fr.stream.datacnt);
2294
0
    assert(1 == datacnt);
2295
0
  }
2296
2297
0
  frc->fr.stream.datacnt = 1;
2298
0
  frc->fr.stream.data[0].len = offset;
2299
0
  frc->next = right_frc;
2300
2301
0
  return 0;
2302
0
}
2303
2304
/*
2305
 * conn_crumble_initial_crypto splits CRYPTO frame (*pfrc)->fr.stream
2306
 * into pieces and adds PADDING and PING frames, and reorder those
2307
 * frames.  Those frames are encoded in the buffer pointed by |data|
2308
 * and |offsets|.  |data| is the pointer to the array of ngtcp2_vec of
2309
 * at least NGTCP2_MAX_STREAM_DATACNT.  |offsets| contains the CRYPTO
2310
 * offset of the corresponding ngtcp2_vec in |data|, and it also
2311
 * should have the capacity at least NGTCP2_MAX_STREAM_DATACNT
2312
 * uint64_t.  |left| is the number of bytes available for the current
2313
 * packet.  |crypto_offset| is the next smallest CRYPTO offset.
2314
 * |crypto_strm| is the CRYPTO stream.
2315
 *
2316
 * This function returns the number of objects written to |data| and
2317
 * |offsets|, or one of the following negative error codes:
2318
 *
2319
 * NGTCP2_ERR_NOMEM
2320
 *     Out of memory
2321
 */
2322
static ngtcp2_ssize
2323
conn_crumble_initial_crypto(ngtcp2_conn *conn, ngtcp2_frame_chain **pfrc,
2324
                            ngtcp2_vec *data, uint64_t *offsets,
2325
                            ngtcp2_strm *crypto_strm, size_t left,
2326
0
                            uint64_t crypto_offset) {
2327
0
  ngtcp2_vec server_name;
2328
0
  ngtcp2_vec removed_data;
2329
0
  size_t max_add_frames = 10;
2330
0
  size_t single_crypto_overhead =
2331
0
    1 + ngtcp2_put_uvarintlen(crypto_offset + left - 1) +
2332
0
    ngtcp2_put_uvarintlen(left);
2333
0
  size_t total_crypto_overhead = single_crypto_overhead * max_add_frames;
2334
0
  size_t datacnt;
2335
0
  size_t i;
2336
0
  int rv;
2337
2338
0
  if (left <= total_crypto_overhead) {
2339
0
    return 0;
2340
0
  }
2341
2342
0
  left -= total_crypto_overhead;
2343
2344
0
  left = ngtcp2_pkt_crypto_max_datalen(crypto_offset, left, left);
2345
0
  if (left == (size_t)-1) {
2346
0
    return 0;
2347
0
  }
2348
2349
0
  rv = ngtcp2_strm_streamfrq_pop(crypto_strm, pfrc, left);
2350
0
  if (rv != 0) {
2351
0
    assert(ngtcp2_err_is_fatal(rv));
2352
0
    return rv;
2353
0
  }
2354
2355
0
  if (*pfrc == NULL) {
2356
0
    return 0;
2357
0
  }
2358
2359
0
  assert(crypto_offset == (*pfrc)->fr.stream.offset);
2360
2361
0
  ngtcp2_vec_copy(data, (*pfrc)->fr.stream.data, (*pfrc)->fr.stream.datacnt);
2362
0
  datacnt = (*pfrc)->fr.stream.datacnt;
2363
2364
0
  offsets[0] = (*pfrc)->fr.stream.offset;
2365
2366
0
  for (i = 1; i < datacnt; ++i) {
2367
0
    offsets[i] = offsets[i - 1] + data[i - 1].len;
2368
0
  }
2369
2370
0
  if (datacnt < NGTCP2_MAX_STREAM_DATACNT &&
2371
0
      ngtcp2_pkt_find_server_name(&server_name, data) && server_name.len > 1) {
2372
0
    if (ngtcp2_strm_streamfrq_empty(crypto_strm) ||
2373
0
        ngtcp2_strm_streamfrq_unacked_offset(crypto_strm) == (uint64_t)-1) {
2374
0
      datacnt = ngtcp2_pkt_split_vec_at(
2375
0
        data, datacnt, offsets,
2376
0
        (size_t)(server_name.base - data[0].base) + server_name.len / 2);
2377
0
    } else {
2378
      /* If we have another data to send (most likely in the another
2379
         packet), remove the part of SNI from this packet. */
2380
0
      datacnt = ngtcp2_pkt_remove_vec_partial(
2381
0
        &removed_data, data, datacnt, offsets, &conn->pcg, &server_name);
2382
2383
0
      rv = conn_cut_crypto_frame(conn, *pfrc, crypto_strm, &removed_data);
2384
0
      if (rv != 0) {
2385
0
        ngtcp2_frame_chain_objalloc_del(*pfrc, &conn->frc_objalloc, conn->mem);
2386
0
        return rv;
2387
0
      }
2388
2389
      /* Add the length of removed data to total_crypto_overhead so
2390
         that we can use them for inter CRYPTO frames padding. */
2391
0
      total_crypto_overhead += removed_data.len;
2392
0
    }
2393
0
  }
2394
2395
0
  if (datacnt < max_add_frames + 1) {
2396
0
    max_add_frames -= datacnt - 1;
2397
2398
0
    datacnt = ngtcp2_pkt_split_vec_rand(data, datacnt, offsets, &conn->pcg,
2399
0
                                        max_add_frames);
2400
0
  }
2401
2402
0
  for (i = 1; i < datacnt; ++i) {
2403
0
    total_crypto_overhead -= 1 + ngtcp2_put_uvarintlen(offsets[i]) +
2404
0
                             ngtcp2_put_uvarintlen(data[i].len);
2405
0
  }
2406
2407
0
  datacnt = ngtcp2_pkt_append_ping_and_padding(data, datacnt, &conn->pcg,
2408
0
                                               total_crypto_overhead);
2409
2410
0
  ngtcp2_pkt_permutate_vec(data, datacnt, offsets, &conn->pcg);
2411
2412
0
  return (ngtcp2_ssize)datacnt;
2413
0
}
2414
2415
0
static size_t conn_dgram_padding(ngtcp2_conn *conn, ngtcp2_ppe *ppe) {
2416
0
  if (conn->local.settings.no_tx_udp_payload_size_shaping) {
2417
0
    return ngtcp2_ppe_dgram_padding_size(
2418
0
      ppe, conn->local.settings.max_tx_udp_payload_size);
2419
0
  }
2420
2421
0
  return ngtcp2_ppe_dgram_padding(ppe);
2422
0
}
2423
2424
static size_t conn_min_pktlen(ngtcp2_conn *conn);
2425
2426
/*
2427
 * conn_write_handshake_pkt writes handshake packet in the buffer
2428
 * pointed by |dest| whose length is |destlen|.  |dgram_offset| is the
2429
 * offset in UDP datagram payload where this QUIC packet is positioned
2430
 * at.  |type| specifies long packet type.  It should be either
2431
 * NGTCP2_PKT_INITIAL or NGTCP2_PKT_HANDSHAKE_PKT.
2432
 *
2433
 * |write_datalen| is the minimum length of application data ready to
2434
 * send in subsequent 0RTT packet.
2435
 *
2436
 * This function returns the number of bytes written in |dest| if it
2437
 * succeeds, or one of the following negative error codes:
2438
 *
2439
 * NGTCP2_ERR_NOMEM
2440
 *     Out of memory.
2441
 * NGTCP2_ERR_CALLBACK_FAILURE
2442
 *     User-defined callback function failed.
2443
 */
2444
static ngtcp2_ssize
2445
conn_write_handshake_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi, uint8_t *dest,
2446
                         size_t destlen, size_t dgram_offset, uint8_t type,
2447
                         uint8_t flags, uint64_t write_datalen,
2448
0
                         ngtcp2_tstamp ts) {
2449
0
  int rv;
2450
0
  ngtcp2_ppe ppe;
2451
0
  ngtcp2_pkt_hd hd;
2452
0
  ngtcp2_frame_chain *frq = NULL, **pfrc = &frq;
2453
0
  ngtcp2_frame_chain *nfrc;
2454
0
  ngtcp2_ack_range ack_ranges[NGTCP2_MAX_ACK_RANGES];
2455
0
  ngtcp2_frame lfr;
2456
0
  ngtcp2_ssize spktlen;
2457
0
  ngtcp2_crypto_cc cc;
2458
0
  ngtcp2_rtb_entry *rtbent;
2459
0
  ngtcp2_pktns *pktns;
2460
0
  size_t left;
2461
0
  uint16_t rtb_entry_flags = NGTCP2_RTB_ENTRY_FLAG_NONE;
2462
0
  int require_padding = (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING) != 0;
2463
0
  int pkt_empty = 1;
2464
0
  int min_padded = 0;
2465
0
  int padded = 0;
2466
0
  int hd_logged = 0;
2467
0
  uint64_t crypto_offset;
2468
0
  ngtcp2_ssize num_reclaimed;
2469
0
  uint32_t version;
2470
2471
0
  switch (type) {
2472
0
  case NGTCP2_PKT_INITIAL:
2473
0
    if (!conn->in_pktns) {
2474
0
      return 0;
2475
0
    }
2476
0
    assert(conn->in_pktns->crypto.tx.ckm);
2477
0
    pktns = conn->in_pktns;
2478
0
    version = conn->negotiated_version ? conn->negotiated_version
2479
0
                                       : conn->client_chosen_version;
2480
0
    if (version == conn->client_chosen_version) {
2481
0
      cc.ckm = pktns->crypto.tx.ckm;
2482
0
      cc.hp_ctx = pktns->crypto.tx.hp_ctx;
2483
0
    } else {
2484
0
      assert(conn->vneg.version == version);
2485
2486
0
      cc.ckm = conn->vneg.tx.ckm;
2487
0
      cc.hp_ctx = conn->vneg.tx.hp_ctx;
2488
0
    }
2489
0
    break;
2490
0
  case NGTCP2_PKT_HANDSHAKE:
2491
0
    if (!conn->hs_pktns || !conn->hs_pktns->crypto.tx.ckm) {
2492
0
      return 0;
2493
0
    }
2494
0
    pktns = conn->hs_pktns;
2495
0
    version = conn->negotiated_version;
2496
0
    cc.ckm = pktns->crypto.tx.ckm;
2497
0
    cc.hp_ctx = pktns->crypto.tx.hp_ctx;
2498
0
    break;
2499
0
  default:
2500
0
    ngtcp2_unreachable();
2501
0
  }
2502
2503
0
  cc.aead = pktns->crypto.ctx.aead;
2504
0
  cc.hp = pktns->crypto.ctx.hp;
2505
0
  cc.encrypt = conn->callbacks.encrypt;
2506
0
  cc.hp_mask = conn->callbacks.hp_mask;
2507
2508
0
  ngtcp2_pkt_hd_init(
2509
0
    &hd, conn_pkt_flags_long(conn), type, &conn->dcid.current.cid, &conn->oscid,
2510
0
    pktns->tx.last_pkt_num + 1, pktns_select_pkt_numlen(pktns), version);
2511
2512
0
  if (!conn->server && type == NGTCP2_PKT_INITIAL &&
2513
0
      conn->local.settings.tokenlen) {
2514
0
    hd.token = conn->local.settings.token;
2515
0
    hd.tokenlen = conn->local.settings.tokenlen;
2516
0
  }
2517
2518
0
  ngtcp2_ppe_init(&ppe, dest, destlen, dgram_offset, &cc);
2519
2520
0
  rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
2521
0
  if (rv != 0) {
2522
0
    assert(NGTCP2_ERR_NOBUF == rv);
2523
0
    return 0;
2524
0
  }
2525
2526
0
  if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
2527
0
    return 0;
2528
0
  }
2529
2530
0
  lfr.ack.ranges = ack_ranges;
2531
0
  if (ngtcp2_acktr_create_ack_frame(&pktns->acktr, &lfr.ack, type, ts,
2532
0
                                    /* ack_delay = */ 0,
2533
0
                                    NGTCP2_DEFAULT_ACK_DELAY_EXPONENT) == 0) {
2534
0
    rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2535
0
    if (rv != 0) {
2536
0
      assert(NGTCP2_ERR_NOBUF == rv);
2537
0
    } else {
2538
0
      ngtcp2_acktr_commit_ack(&pktns->acktr);
2539
0
      ngtcp2_acktr_add_ack(&pktns->acktr, hd.pkt_num, lfr.ack.largest_ack);
2540
0
      pkt_empty = 0;
2541
0
    }
2542
0
  }
2543
2544
  /* Server requires at least NGTCP2_MAX_UDP_PAYLOAD_SIZE bytes in
2545
     order to send ack-eliciting Initial packet. */
2546
0
  if (!conn->server || type != NGTCP2_PKT_INITIAL ||
2547
0
      destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
2548
0
  build_pkt:
2549
0
    for (; !ngtcp2_strm_streamfrq_empty(&pktns->crypto.strm);) {
2550
0
      crypto_offset = ngtcp2_strm_streamfrq_unacked_offset(&pktns->crypto.strm);
2551
0
      if (crypto_offset == (uint64_t)-1) {
2552
0
        ngtcp2_strm_streamfrq_clear(&pktns->crypto.strm);
2553
0
        break;
2554
0
      }
2555
2556
0
      left = ngtcp2_ppe_left(&ppe);
2557
0
      if (left == 0) {
2558
0
        break;
2559
0
      }
2560
2561
0
      if (type == NGTCP2_PKT_INITIAL &&
2562
0
          (conn->flags & NGTCP2_CONN_FLAG_CRUMBLE_INITIAL_CRYPTO)) {
2563
0
        ngtcp2_vec data[NGTCP2_MAX_STREAM_DATACNT];
2564
0
        uint64_t offsets[NGTCP2_MAX_STREAM_DATACNT];
2565
0
        ngtcp2_ssize datacnt;
2566
0
        size_t i;
2567
2568
0
        datacnt = conn_crumble_initial_crypto(
2569
0
          conn, &nfrc, data, offsets, &pktns->crypto.strm, left, crypto_offset);
2570
0
        if (datacnt < 0) {
2571
0
          assert(ngtcp2_err_is_fatal((int)datacnt));
2572
0
          ngtcp2_frame_chain_list_objalloc_del(frq, &conn->frc_objalloc,
2573
0
                                               conn->mem);
2574
2575
0
          return datacnt;
2576
0
        }
2577
2578
0
        if (datacnt == 0) {
2579
0
          break;
2580
0
        }
2581
2582
0
        for (i = 0; i < (size_t)datacnt; ++i) {
2583
0
          if (data[i].base == NULL) {
2584
0
            if (data[i].len == 0) {
2585
0
              lfr.ping.type = NGTCP2_FRAME_PING;
2586
0
            } else {
2587
0
              lfr.padding = (ngtcp2_padding){
2588
0
                .type = NGTCP2_FRAME_PADDING,
2589
0
                .len = data[i].len,
2590
0
              };
2591
0
            }
2592
0
          } else {
2593
0
            lfr.stream = (ngtcp2_stream){
2594
0
              .type = NGTCP2_FRAME_CRYPTO,
2595
0
              .offset = offsets[i],
2596
0
              .datacnt = 1,
2597
0
              .data = &data[i],
2598
0
            };
2599
0
          }
2600
2601
0
          rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2602
0
          if (rv != 0) {
2603
0
            ngtcp2_unreachable();
2604
0
          }
2605
0
        }
2606
0
      } else {
2607
0
        left = ngtcp2_pkt_crypto_max_datalen(crypto_offset, left, left);
2608
0
        if (left == (size_t)-1) {
2609
0
          break;
2610
0
        }
2611
2612
0
        rv = ngtcp2_strm_streamfrq_pop(&pktns->crypto.strm, &nfrc, left);
2613
0
        if (rv != 0) {
2614
0
          assert(ngtcp2_err_is_fatal(rv));
2615
0
          ngtcp2_frame_chain_list_objalloc_del(frq, &conn->frc_objalloc,
2616
0
                                               conn->mem);
2617
0
          return rv;
2618
0
        }
2619
2620
0
        if (nfrc == NULL) {
2621
0
          break;
2622
0
        }
2623
2624
0
        rv =
2625
0
          conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &nfrc->fr);
2626
0
        if (rv != 0) {
2627
0
          ngtcp2_unreachable();
2628
0
        }
2629
0
      }
2630
2631
0
      *pfrc = nfrc;
2632
2633
0
      for (; nfrc->next;) {
2634
0
        nfrc = nfrc->next;
2635
0
      }
2636
2637
0
      pfrc = &nfrc->next;
2638
2639
0
      pkt_empty = 0;
2640
0
      rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
2641
0
                         NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
2642
0
                         NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
2643
0
    }
2644
2645
0
    if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2646
0
        pktns->rtb.num_retransmittable && pktns->rtb.probe_pkt_left) {
2647
0
      num_reclaimed = ngtcp2_rtb_reclaim_on_pto(
2648
0
        &pktns->rtb, conn, pktns,
2649
0
        !conn->server && type == NGTCP2_PKT_INITIAL ? 2 : 1);
2650
0
      if (num_reclaimed < 0) {
2651
0
        ngtcp2_frame_chain_list_objalloc_del(frq, &conn->frc_objalloc,
2652
0
                                             conn->mem);
2653
0
        return num_reclaimed;
2654
0
      }
2655
0
      if (num_reclaimed) {
2656
0
        goto build_pkt;
2657
0
      }
2658
      /* We had pktns->rtb.num_retransmittable > 0 but the contents of
2659
         those packets have been acknowledged (i.e., retransmission in
2660
         another packet).  For server, in this case, we don't have to
2661
         send any probe packet.  Client needs to send probe packets
2662
         until it knows that server has completed address
2663
         validation. */
2664
0
      if (pktns->rtb.num_pto_eliciting == 0 &&
2665
0
          (conn->server ||
2666
0
           (conn->flags & NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED))) {
2667
0
        pktns->rtb.probe_pkt_left = 0;
2668
0
        ngtcp2_conn_set_loss_detection_timer(conn, ts);
2669
        /* TODO If packet is empty, we should return now if cwnd is
2670
           zero. */
2671
0
      }
2672
0
    }
2673
2674
0
    if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2675
0
        pktns->rtb.probe_pkt_left) {
2676
0
      lfr.ping.type = NGTCP2_FRAME_PING;
2677
2678
0
      rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2679
0
      if (rv != 0) {
2680
0
        assert(rv == NGTCP2_ERR_NOBUF);
2681
0
      } else {
2682
0
        rtb_entry_flags |=
2683
0
          NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING | NGTCP2_RTB_ENTRY_FLAG_PROBE;
2684
0
        pkt_empty = 0;
2685
0
      }
2686
0
    }
2687
2688
0
    if (!pkt_empty) {
2689
0
      if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
2690
0
        if (ngtcp2_tstamp_elapsed(pktns->tx.non_ack_pkt_start_ts,
2691
0
                                  conn->cstat.smoothed_rtt, ts)) {
2692
0
          lfr.ping.type = NGTCP2_FRAME_PING;
2693
2694
0
          rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2695
0
          if (rv != 0) {
2696
0
            assert(rv == NGTCP2_ERR_NOBUF);
2697
0
          } else {
2698
0
            rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
2699
0
            pktns->tx.non_ack_pkt_start_ts = UINT64_MAX;
2700
0
            pkt_empty = 0;
2701
0
          }
2702
0
        } else if (pktns->tx.non_ack_pkt_start_ts == UINT64_MAX) {
2703
0
          pktns->tx.non_ack_pkt_start_ts = ts;
2704
0
        }
2705
0
      } else {
2706
0
        pktns->tx.non_ack_pkt_start_ts = UINT64_MAX;
2707
0
      }
2708
0
    }
2709
0
  }
2710
2711
0
  if (pkt_empty && !require_padding) {
2712
0
    return 0;
2713
0
  }
2714
2715
  /* If we cannot write another packet, then we need to add padding to
2716
     Initial here. */
2717
0
  if (conn_should_pad_pkt(
2718
0
        conn, type, ngtcp2_ppe_left(&ppe), write_datalen,
2719
0
        (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) != 0,
2720
0
        require_padding)) {
2721
0
    lfr.padding.type = NGTCP2_FRAME_PADDING;
2722
0
    lfr.padding.len = conn_dgram_padding(conn, &ppe);
2723
0
  } else if (pkt_empty) {
2724
0
    return 0;
2725
0
  } else {
2726
0
    lfr.padding.type = NGTCP2_FRAME_PADDING;
2727
0
    lfr.padding.len = ngtcp2_ppe_padding_size(&ppe, conn_min_pktlen(conn));
2728
0
    min_padded = 1;
2729
0
  }
2730
2731
0
  if (lfr.padding.len) {
2732
0
    if (!min_padded ||
2733
0
        (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
2734
0
      padded = 1;
2735
0
    }
2736
0
    ngtcp2_log_tx_fr(&conn->log, &hd, &lfr);
2737
0
    ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
2738
0
  }
2739
2740
0
  spktlen = ngtcp2_ppe_final(&ppe, NULL);
2741
0
  if (spktlen < 0) {
2742
0
    assert(ngtcp2_err_is_fatal((int)spktlen));
2743
0
    ngtcp2_frame_chain_list_objalloc_del(frq, &conn->frc_objalloc, conn->mem);
2744
0
    return spktlen;
2745
0
  }
2746
2747
0
  ngtcp2_qlog_pkt_sent_end(&conn->qlog, &hd, (size_t)spktlen);
2748
2749
0
  if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) {
2750
0
    if (pi) {
2751
0
      conn_handle_tx_ecn(conn, pi, &rtb_entry_flags, pktns, &hd, ts);
2752
0
    }
2753
2754
0
    rv =
2755
0
      ngtcp2_rtb_entry_objalloc_new(&rtbent, &hd, frq, ts, (size_t)spktlen,
2756
0
                                    rtb_entry_flags, &conn->rtb_entry_objalloc);
2757
0
    if (rv != 0) {
2758
0
      assert(ngtcp2_err_is_fatal(rv));
2759
0
      ngtcp2_frame_chain_list_objalloc_del(frq, &conn->frc_objalloc, conn->mem);
2760
0
      return rv;
2761
0
    }
2762
2763
0
    rv = conn_on_pkt_sent(conn, pktns, rtbent);
2764
0
    if (rv != 0) {
2765
0
      ngtcp2_rtb_entry_objalloc_del(rtbent, &conn->rtb_entry_objalloc,
2766
0
                                    &conn->frc_objalloc, conn->mem);
2767
0
      return rv;
2768
0
    }
2769
2770
0
    if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2771
0
        (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE)) {
2772
0
      conn_restart_timer_on_write(conn, ts);
2773
0
    }
2774
0
  } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
2775
0
    conn_handle_tx_ecn(conn, pi, NULL, pktns, &hd, ts);
2776
0
  }
2777
2778
0
  if (pktns->rtb.probe_pkt_left &&
2779
0
      (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
2780
0
    --pktns->rtb.probe_pkt_left;
2781
0
  }
2782
2783
0
  conn_update_keep_alive_last_ts(conn, ts);
2784
2785
0
  conn->dcid.current.bytes_sent += (uint64_t)spktlen;
2786
2787
0
  conn->tx.pacing.pktlen += (size_t)spktlen;
2788
2789
0
  ++conn->cstat.pkt_sent;
2790
0
  conn->cstat.bytes_sent += (uint64_t)spktlen;
2791
2792
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
2793
2794
0
  ++pktns->tx.last_pkt_num;
2795
2796
0
  return spktlen;
2797
0
}
2798
2799
/*
2800
 * conn_write_ack_pkt writes QUIC packet for type |type| which only
2801
 * includes ACK frame in the buffer pointed by |dest| whose length is
2802
 * |destlen|.
2803
 *
2804
 * This function returns the number of bytes written in |dest| if it
2805
 * succeeds, or one of the following negative error codes:
2806
 *
2807
 * NGTCP2_ERR_CALLBACK_FAILURE
2808
 *     User-defined callback function failed.
2809
 * NGTCP2_ERR_NOMEM
2810
 *     Out of memory.
2811
 */
2812
static ngtcp2_ssize conn_write_ack_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
2813
                                       uint8_t *dest, size_t destlen,
2814
0
                                       uint8_t type, ngtcp2_tstamp ts) {
2815
0
  ngtcp2_pktns *pktns;
2816
0
  ngtcp2_duration ack_delay;
2817
0
  uint64_t ack_delay_exponent;
2818
0
  ngtcp2_ssize spktlen;
2819
0
  ngtcp2_ack_range ack_ranges[NGTCP2_MAX_ACK_RANGES];
2820
0
  ngtcp2_frame fr;
2821
2822
0
  assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
2823
2824
0
  switch (type) {
2825
0
  case NGTCP2_PKT_INITIAL:
2826
0
    assert(conn->server);
2827
0
    pktns = conn->in_pktns;
2828
0
    ack_delay = 0;
2829
0
    ack_delay_exponent = NGTCP2_DEFAULT_ACK_DELAY_EXPONENT;
2830
0
    break;
2831
0
  case NGTCP2_PKT_HANDSHAKE:
2832
0
    pktns = conn->hs_pktns;
2833
0
    ack_delay = 0;
2834
0
    ack_delay_exponent = NGTCP2_DEFAULT_ACK_DELAY_EXPONENT;
2835
0
    break;
2836
0
  case NGTCP2_PKT_1RTT:
2837
0
    pktns = &conn->pktns;
2838
0
    ack_delay = conn_compute_ack_delay(conn);
2839
0
    ack_delay_exponent = conn->local.transport_params.ack_delay_exponent;
2840
0
    break;
2841
0
  default:
2842
0
    ngtcp2_unreachable();
2843
0
  }
2844
2845
0
  if (!pktns->crypto.tx.ckm) {
2846
0
    return 0;
2847
0
  }
2848
2849
0
  fr.ack.ranges = ack_ranges;
2850
0
  if (ngtcp2_acktr_create_ack_frame(&pktns->acktr, &fr.ack, type, ts, ack_delay,
2851
0
                                    ack_delay_exponent) != 0) {
2852
0
    return 0;
2853
0
  }
2854
2855
0
  spktlen = ngtcp2_conn_write_single_frame_pkt(
2856
0
    conn, pi, dest, destlen, type, NGTCP2_WRITE_PKT_FLAG_NONE,
2857
0
    &conn->dcid.current.cid, &fr, NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
2858
2859
0
  if (spktlen <= 0) {
2860
0
    return spktlen;
2861
0
  }
2862
2863
0
  conn->dcid.current.bytes_sent += (uint64_t)spktlen;
2864
2865
0
  return spktlen;
2866
0
}
2867
2868
static void conn_discard_pktns(ngtcp2_conn *conn, ngtcp2_pktns **ppktns,
2869
0
                               ngtcp2_tstamp ts) {
2870
0
  ngtcp2_pktns *pktns = *ppktns;
2871
0
  uint64_t bytes_in_flight;
2872
2873
0
  bytes_in_flight = pktns->rtb.cc_bytes_in_flight;
2874
2875
0
  assert(conn->cstat.bytes_in_flight >= bytes_in_flight);
2876
2877
0
  conn->cstat.bytes_in_flight -= bytes_in_flight;
2878
0
  conn->cstat.pto_count = 0;
2879
0
  conn->cstat.last_tx_pkt_ts[pktns->id] = UINT64_MAX;
2880
0
  conn->cstat.loss_time[pktns->id] = UINT64_MAX;
2881
2882
0
  conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.rx.ckm->aead_ctx);
2883
0
  conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.rx.hp_ctx);
2884
0
  conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
2885
0
  conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.tx.hp_ctx);
2886
2887
0
  pktns_del(pktns, conn->mem);
2888
0
  *ppktns = NULL;
2889
2890
0
  ngtcp2_conn_set_loss_detection_timer(conn, ts);
2891
0
}
2892
2893
0
void ngtcp2_conn_discard_initial_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2894
0
  if (!conn->in_pktns) {
2895
0
    return;
2896
0
  }
2897
2898
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
2899
0
                  "discarding Initial packet number space");
2900
2901
0
  conn_discard_pktns(conn, &conn->in_pktns, ts);
2902
2903
0
  conn_vneg_crypto_free(conn);
2904
2905
0
  memset(&conn->vneg.rx, 0, sizeof(conn->vneg.rx));
2906
0
  memset(&conn->vneg.tx, 0, sizeof(conn->vneg.tx));
2907
0
}
2908
2909
0
void ngtcp2_conn_discard_handshake_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2910
0
  if (!conn->hs_pktns) {
2911
0
    return;
2912
0
  }
2913
2914
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
2915
0
                  "discarding Handshake packet number space");
2916
2917
0
  conn_discard_pktns(conn, &conn->hs_pktns, ts);
2918
0
}
2919
2920
/*
2921
 * conn_discard_early_key discards early key.
2922
 */
2923
0
static void conn_discard_early_key(ngtcp2_conn *conn) {
2924
0
  assert(conn->early.ckm);
2925
2926
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "discarding early key");
2927
2928
0
  conn_call_delete_crypto_aead_ctx(conn, &conn->early.ckm->aead_ctx);
2929
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->early.hp_ctx);
2930
0
  conn->early.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
2931
2932
0
  ngtcp2_crypto_km_del(conn->early.ckm, conn->mem);
2933
0
  conn->early.ckm = NULL;
2934
0
}
2935
2936
/*
2937
 * conn_write_handshake_ack_pkts writes packets which contain ACK
2938
 * frame only.  This function writes at most 2 packets for each
2939
 * Initial and Handshake packet.
2940
 */
2941
static ngtcp2_ssize conn_write_handshake_ack_pkts(ngtcp2_conn *conn,
2942
                                                  ngtcp2_pkt_info *pi,
2943
                                                  uint8_t *dest, size_t destlen,
2944
0
                                                  ngtcp2_tstamp ts) {
2945
0
  ngtcp2_ssize res = 0, nwrite = 0;
2946
2947
  /* In the most cases, client sends ACK in conn_write_handshake_pkt.
2948
     This function is only called when it is CWND limited or pacing
2949
     limited.  It is not required for client to send ACK for server
2950
     Initial.  This is because once it gets server Initial, it gets
2951
     Handshake tx key and discards Initial key.  The only good reason
2952
     to send ACK is give server RTT measurement early. */
2953
0
  if (conn->server && conn->in_pktns) {
2954
0
    nwrite =
2955
0
      conn_write_ack_pkt(conn, pi, dest, destlen, NGTCP2_PKT_INITIAL, ts);
2956
0
    if (nwrite < 0) {
2957
0
      assert(nwrite != NGTCP2_ERR_NOBUF);
2958
0
      return nwrite;
2959
0
    }
2960
2961
0
    res += nwrite;
2962
0
    dest += nwrite;
2963
0
    destlen -= (size_t)nwrite;
2964
0
  }
2965
2966
0
  if (conn->hs_pktns->crypto.tx.ckm) {
2967
0
    nwrite =
2968
0
      conn_write_ack_pkt(conn, pi, dest, destlen, NGTCP2_PKT_HANDSHAKE, ts);
2969
0
    if (nwrite < 0) {
2970
0
      assert(nwrite != NGTCP2_ERR_NOBUF);
2971
0
      return nwrite;
2972
0
    }
2973
2974
0
    res += nwrite;
2975
2976
0
    if (!conn->server && nwrite) {
2977
0
      ngtcp2_conn_discard_initial_state(conn, ts);
2978
0
    }
2979
0
  }
2980
2981
0
  return res;
2982
0
}
2983
2984
/*
2985
 * conn_write_client_initial writes Initial packet in the buffer
2986
 * pointed by |dest| whose length is |destlen|.
2987
 *
2988
 * This function returns the number of bytes written in |dest| if it
2989
 * succeeds, or one of the following negative error codes:
2990
 *
2991
 * NGTCP2_ERR_NOMEM
2992
 *     Out of memory.
2993
 * NGTCP2_ERR_CALLBACK_FAILURE
2994
 *     User-defined callback function failed.
2995
 */
2996
static ngtcp2_ssize conn_write_client_initial(ngtcp2_conn *conn,
2997
                                              ngtcp2_pkt_info *pi,
2998
                                              uint8_t *dest, size_t destlen,
2999
                                              uint64_t early_datalen,
3000
0
                                              ngtcp2_tstamp ts) {
3001
0
  int rv;
3002
3003
0
  rv = conn_call_client_initial(conn);
3004
0
  if (rv != 0) {
3005
0
    return rv;
3006
0
  }
3007
3008
0
  return conn_write_handshake_pkt(
3009
0
    conn, pi, dest, destlen, 0, NGTCP2_PKT_INITIAL, NGTCP2_WRITE_PKT_FLAG_NONE,
3010
0
    early_datalen, ts);
3011
0
}
3012
3013
/*
3014
 * dcid_tx_left returns the maximum number of bytes that server is
3015
 * allowed to send to an unvalidated path associated to |dcid|.
3016
 */
3017
0
static uint64_t dcid_tx_left(ngtcp2_dcid *dcid) {
3018
0
  if (dcid->flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) {
3019
0
    return SIZE_MAX;
3020
0
  }
3021
  /* From QUIC spec: Prior to validating the client address, servers
3022
     MUST NOT send more than three times as many bytes as the number
3023
     of bytes they have received. */
3024
0
  assert(dcid->bytes_recv * 3 >= dcid->bytes_sent);
3025
3026
0
  return dcid->bytes_recv * 3 - dcid->bytes_sent;
3027
0
}
3028
3029
/*
3030
 * conn_server_tx_left returns the maximum number of bytes that server
3031
 * is allowed to send to an unvalidated path.
3032
 */
3033
0
static uint64_t conn_server_tx_left(ngtcp2_conn *conn, ngtcp2_dcid *dcid) {
3034
0
  assert(conn->server);
3035
3036
  /* If pv->dcid has the current path, use conn->dcid.current.  This
3037
     is because conn->dcid.current gets update for bytes_recv and
3038
     bytes_sent. */
3039
0
  if (ngtcp2_path_eq(&dcid->ps.path, &conn->dcid.current.ps.path)) {
3040
0
    return dcid_tx_left(&conn->dcid.current);
3041
0
  }
3042
3043
0
  return dcid_tx_left(dcid);
3044
0
}
3045
3046
/*
3047
 * conn_write_handshake_pkts writes Initial and Handshake packets in
3048
 * the buffer pointed by |dest| whose length is |destlen|.
3049
 *
3050
 * This function returns the number of bytes written in |dest| if it
3051
 * succeeds, or one of the following negative error codes:
3052
 *
3053
 * NGTCP2_ERR_NOMEM
3054
 *     Out of memory.
3055
 * NGTCP2_ERR_CALLBACK_FAILURE
3056
 *     User-defined callback function failed.
3057
 */
3058
static ngtcp2_ssize conn_write_handshake_pkts(ngtcp2_conn *conn,
3059
                                              ngtcp2_pkt_info *pi,
3060
                                              uint8_t *dest, size_t destlen,
3061
                                              uint64_t write_datalen,
3062
0
                                              ngtcp2_tstamp ts) {
3063
0
  ngtcp2_ssize nwrite;
3064
0
  ngtcp2_ssize res = 0;
3065
0
  ngtcp2_rtb_entry *rtbent;
3066
0
  uint8_t wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
3067
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
3068
0
  ngtcp2_ksl_it it;
3069
3070
  /* As a client, we would like to discard Initial packet number space
3071
     when sending the first Handshake packet.  When sending Handshake
3072
     packet, it should be one of 1) sending ACK, 2) sending PTO probe
3073
     packet, or 3) sending CRYPTO.  If we have pending acknowledgement
3074
     for Initial, then do not discard Initial packet number space.
3075
     Otherwise, if either 1) or 2) is satisfied, discard Initial
3076
     packet number space.  When sending Handshake CRYPTO, it indicates
3077
     that client has received Handshake CRYPTO from server.  Initial
3078
     packet number space is discarded because 1) is met.  If there is
3079
     pending Initial ACK, Initial packet number space is discarded
3080
     after writing the first Handshake packet.
3081
   */
3082
0
  if (!conn->server && conn->hs_pktns->crypto.tx.ckm && conn->in_pktns &&
3083
0
      !ngtcp2_acktr_require_active_ack(&conn->in_pktns->acktr,
3084
0
                                       /* max_ack_delay = */ 0, ts) &&
3085
0
      (ngtcp2_acktr_require_active_ack(&conn->hs_pktns->acktr,
3086
0
                                       /* max_ack_delay = */ 0, ts) ||
3087
0
       conn->hs_pktns->rtb.probe_pkt_left)) {
3088
    /* Discard Initial state here so that Handshake packet is not
3089
       padded. */
3090
0
    ngtcp2_conn_discard_initial_state(conn, ts);
3091
0
  } else if (conn->in_pktns) {
3092
0
    nwrite =
3093
0
      conn_write_handshake_pkt(conn, pi, dest, destlen, 0, NGTCP2_PKT_INITIAL,
3094
0
                               NGTCP2_WRITE_PKT_FLAG_NONE, write_datalen, ts);
3095
0
    if (nwrite < 0) {
3096
0
      assert(nwrite != NGTCP2_ERR_NOBUF);
3097
0
      return nwrite;
3098
0
    }
3099
3100
0
    if (nwrite == 0) {
3101
0
      if (conn->server &&
3102
0
          (conn->in_pktns->rtb.probe_pkt_left ||
3103
0
           !ngtcp2_strm_streamfrq_empty(&conn->in_pktns->crypto.strm))) {
3104
0
        if (cstat->loss_detection_timer != UINT64_MAX &&
3105
0
            conn_server_tx_left(conn, &conn->dcid.current) <
3106
0
              NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
3107
0
          ngtcp2_log_info(
3108
0
            &conn->log, NGTCP2_LOG_EVENT_LDC,
3109
0
            "loss detection timer canceled due to amplification limit");
3110
0
          ngtcp2_conn_cancel_loss_detection_timer(conn);
3111
0
        }
3112
3113
0
        return 0;
3114
0
      }
3115
0
    } else {
3116
0
      res += nwrite;
3117
0
      dest += nwrite;
3118
0
      destlen -= (size_t)nwrite;
3119
3120
0
      if (conn->server) {
3121
0
        it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
3122
0
        if (!ngtcp2_ksl_it_end(&it)) {
3123
0
          rtbent = ngtcp2_ksl_it_get(&it);
3124
0
          if (rtbent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
3125
0
            wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
3126
0
          }
3127
0
        }
3128
0
      } else {
3129
0
        wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
3130
0
      }
3131
0
    }
3132
0
  }
3133
3134
0
  nwrite =
3135
0
    conn_write_handshake_pkt(conn, pi, dest, destlen, (size_t)res,
3136
0
                             NGTCP2_PKT_HANDSHAKE, wflags, write_datalen, ts);
3137
0
  if (nwrite < 0) {
3138
0
    assert(nwrite != NGTCP2_ERR_NOBUF);
3139
0
    return nwrite;
3140
0
  }
3141
3142
0
  res += nwrite;
3143
3144
0
  if (!conn->server && conn->hs_pktns->crypto.tx.ckm && nwrite) {
3145
    /* We don't need to send further Initial packet if we have
3146
       Handshake key and sent something with it.  So discard initial
3147
       state here. */
3148
0
    ngtcp2_conn_discard_initial_state(conn, ts);
3149
0
  }
3150
3151
0
  return res;
3152
0
}
3153
3154
/*
3155
 * conn_initial_stream_rx_offset returns the initial maximum offset of
3156
 * data for a stream denoted by |stream_id|.
3157
 */
3158
static uint64_t conn_initial_stream_rx_offset(ngtcp2_conn *conn,
3159
0
                                              int64_t stream_id) {
3160
0
  int local_stream = conn_local_stream(conn, stream_id);
3161
3162
0
  if (bidi_stream(stream_id)) {
3163
0
    if (local_stream) {
3164
0
      return conn->local.transport_params.initial_max_stream_data_bidi_local;
3165
0
    }
3166
0
    return conn->local.transport_params.initial_max_stream_data_bidi_remote;
3167
0
  }
3168
3169
0
  if (local_stream) {
3170
0
    return 0;
3171
0
  }
3172
0
  return conn->local.transport_params.initial_max_stream_data_uni;
3173
0
}
3174
3175
/*
3176
 * conn_should_send_max_stream_data returns nonzero if MAX_STREAM_DATA
3177
 * frame should be send for |strm|.
3178
 */
3179
static int conn_should_send_max_stream_data(ngtcp2_conn *conn,
3180
0
                                            ngtcp2_strm *strm) {
3181
0
  uint64_t inc = strm->rx.unsent_max_offset - strm->rx.max_offset;
3182
0
  (void)conn;
3183
3184
0
  return strm->rx.window < 4 * inc;
3185
0
}
3186
3187
/*
3188
 * conn_should_send_max_data returns nonzero if MAX_DATA frame should
3189
 * be sent.
3190
 */
3191
0
static int conn_should_send_max_data(ngtcp2_conn *conn) {
3192
0
  uint64_t inc = conn->rx.unsent_max_offset - conn->rx.max_offset;
3193
3194
0
  return conn->rx.window < 4 * inc;
3195
0
}
3196
3197
/*
3198
 * conn_required_num_new_connection_id returns the number of
3199
 * additional connection ID the local endpoint has to provide to the
3200
 * remote endpoint.
3201
 */
3202
0
static size_t conn_required_num_new_connection_id(ngtcp2_conn *conn) {
3203
0
  uint64_t n;
3204
0
  size_t len = ngtcp2_ksl_len(&conn->scid.set);
3205
0
  size_t lim;
3206
3207
0
  if (len >= NGTCP2_MAX_SCID_POOL_SIZE) {
3208
0
    return 0;
3209
0
  }
3210
3211
0
  assert(NGTCP2_MAX_SCID_POOL_SIZE >= conn->scid.num_in_flight);
3212
3213
0
  lim = NGTCP2_MAX_SCID_POOL_SIZE - conn->scid.num_in_flight;
3214
0
  if (lim == 0) {
3215
0
    return 0;
3216
0
  }
3217
3218
0
  assert(conn->remote.transport_params);
3219
0
  assert(conn->remote.transport_params->active_connection_id_limit);
3220
3221
  /* len includes retired CID.  We don't provide extra CID if doing so
3222
     exceeds NGTCP2_MAX_SCID_POOL_SIZE. */
3223
3224
0
  n = conn->remote.transport_params->active_connection_id_limit +
3225
0
      conn->scid.num_retired;
3226
3227
0
  n = ngtcp2_min_uint64(NGTCP2_MAX_SCID_POOL_SIZE, n) - len;
3228
3229
0
  return (size_t)ngtcp2_min_uint64(lim, n);
3230
0
}
3231
3232
/*
3233
 * conn_enqueue_new_connection_id generates additional connection IDs
3234
 * and prepares to send them to the remote endpoint.
3235
 *
3236
 * This function returns 0 if it succeeds, or one of the following
3237
 * negative error codes:
3238
 *
3239
 * NGTCP2_ERR_NOMEM
3240
 *     Out of memory.
3241
 * NGTCP2_ERR_CALLBACK_FAILURE
3242
 *     User-defined callback function failed.
3243
 */
3244
0
static int conn_enqueue_new_connection_id(ngtcp2_conn *conn) {
3245
0
  size_t i, need = conn_required_num_new_connection_id(conn);
3246
0
  size_t cidlen = conn->oscid.datalen;
3247
0
  int rv;
3248
0
  ngtcp2_frame_chain *nfrc;
3249
0
  ngtcp2_pktns *pktns = &conn->pktns;
3250
0
  ngtcp2_scid *scid;
3251
0
  ngtcp2_ksl_it it;
3252
3253
0
  for (i = 0; i < need; ++i) {
3254
0
    rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3255
0
    if (rv != 0) {
3256
0
      return rv;
3257
0
    }
3258
3259
0
    nfrc->fr.new_connection_id.type = NGTCP2_FRAME_NEW_CONNECTION_ID;
3260
0
    nfrc->fr.new_connection_id.seq = ++conn->scid.last_seq;
3261
0
    nfrc->fr.new_connection_id.retire_prior_to = 0;
3262
3263
0
    rv = conn_call_get_new_connection_id(conn, &nfrc->fr.new_connection_id.cid,
3264
0
                                         &nfrc->fr.new_connection_id.token,
3265
0
                                         cidlen);
3266
0
    if (rv != 0) {
3267
0
      goto fail;
3268
0
    }
3269
3270
0
    if (nfrc->fr.new_connection_id.cid.datalen != cidlen) {
3271
0
      rv = NGTCP2_ERR_CALLBACK_FAILURE;
3272
0
      goto fail;
3273
0
    }
3274
3275
    /* Assert uniqueness */
3276
0
    it =
3277
0
      ngtcp2_ksl_lower_bound(&conn->scid.set, &nfrc->fr.new_connection_id.cid);
3278
0
    if (!ngtcp2_ksl_it_end(&it) &&
3279
0
        ngtcp2_cid_eq(ngtcp2_ksl_it_key(&it),
3280
0
                      &nfrc->fr.new_connection_id.cid)) {
3281
0
      rv = NGTCP2_ERR_CALLBACK_FAILURE;
3282
0
      goto fail;
3283
0
    }
3284
3285
0
    scid = ngtcp2_mem_malloc(conn->mem, sizeof(*scid));
3286
0
    if (scid == NULL) {
3287
0
      rv = NGTCP2_ERR_NOMEM;
3288
0
      goto fail;
3289
0
    }
3290
3291
0
    ngtcp2_scid_init(scid, nfrc->fr.new_connection_id.seq,
3292
0
                     &nfrc->fr.new_connection_id.cid);
3293
3294
0
    rv = ngtcp2_ksl_insert(&conn->scid.set, NULL, &scid->cid, scid);
3295
0
    if (rv != 0) {
3296
0
      ngtcp2_mem_free(conn->mem, scid);
3297
0
      goto fail;
3298
0
    }
3299
3300
0
    nfrc->next = pktns->tx.frq;
3301
0
    pktns->tx.frq = nfrc;
3302
3303
0
    assert(NGTCP2_MAX_SCID_POOL_SIZE > conn->scid.num_in_flight);
3304
3305
0
    ++conn->scid.num_in_flight;
3306
0
  }
3307
3308
0
  return 0;
3309
3310
0
fail:
3311
0
  ngtcp2_frame_chain_objalloc_del(nfrc, &conn->frc_objalloc, conn->mem);
3312
3313
0
  return rv;
3314
0
}
3315
3316
0
static int dcidtr_on_deactivate(const ngtcp2_dcid *dcid, void *user_data) {
3317
0
  return conn_call_deactivate_dcid(user_data, dcid);
3318
0
}
3319
3320
/*
3321
 * conn_remove_retired_connection_id removes the already retired
3322
 * connection ID.  It waits PTO before actually removing a connection
3323
 * ID after it receives RETIRE_CONNECTION_ID from peer to catch
3324
 * reordered packets.
3325
 *
3326
 * This function returns 0 if it succeeds, or one of the following
3327
 * negative error codes:
3328
 *
3329
 * NGTCP2_ERR_NOMEM
3330
 *     Out of memory.
3331
 * NGTCP2_ERR_CALLBACK_FAILURE
3332
 *     User-defined callback function failed.
3333
 */
3334
static int conn_remove_retired_connection_id(ngtcp2_conn *conn,
3335
                                             ngtcp2_duration pto,
3336
0
                                             ngtcp2_tstamp ts) {
3337
0
  ngtcp2_duration timeout = pto;
3338
0
  ngtcp2_scid *scid;
3339
0
  int rv;
3340
3341
0
  for (; !ngtcp2_pq_empty(&conn->scid.used);) {
3342
0
    scid = ngtcp2_struct_of(ngtcp2_pq_top(&conn->scid.used), ngtcp2_scid, pe);
3343
3344
0
    if (!ngtcp2_tstamp_elapsed(scid->retired_ts, timeout, ts)) {
3345
0
      break;
3346
0
    }
3347
3348
0
    assert(scid->flags & NGTCP2_SCID_FLAG_RETIRED);
3349
3350
0
    rv = conn_call_remove_connection_id(conn, &scid->cid);
3351
0
    if (rv != 0) {
3352
0
      return rv;
3353
0
    }
3354
3355
0
    ngtcp2_ksl_remove(&conn->scid.set, NULL, &scid->cid);
3356
0
    ngtcp2_pq_pop(&conn->scid.used);
3357
0
    ngtcp2_mem_free(conn->mem, scid);
3358
3359
0
    assert(conn->scid.num_retired);
3360
0
    --conn->scid.num_retired;
3361
0
  }
3362
3363
0
  rv = ngtcp2_dcidtr_remove_stale_retired_dcid(&conn->dcid.dtr, timeout, ts,
3364
0
                                               dcidtr_on_deactivate, conn);
3365
0
  if (rv != 0) {
3366
0
    return rv;
3367
0
  }
3368
3369
0
  return 0;
3370
0
}
3371
3372
/*
3373
 * conn_min_pktlen returns the minimum length of packet this endpoint
3374
 * sends.  It may underestimate the length because this does not take
3375
 * into account header protection sample.
3376
 */
3377
0
static size_t conn_min_pktlen(ngtcp2_conn *conn) {
3378
0
  return conn->oscid.datalen + NGTCP2_MIN_PKT_EXPANDLEN;
3379
0
}
3380
3381
/*
3382
 * conn_handle_unconfirmed_key_update_from_remote deals with key
3383
 * update which has not been confirmed yet and initiated by the remote
3384
 * endpoint.
3385
 *
3386
 * If key update was initiated by the remote endpoint, acknowledging a
3387
 * packet encrypted with the new key completes key update procedure.
3388
 */
3389
static void conn_handle_unconfirmed_key_update_from_remote(ngtcp2_conn *conn,
3390
                                                           int64_t largest_ack,
3391
0
                                                           ngtcp2_tstamp ts) {
3392
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED) ||
3393
0
      (conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_INITIATOR) ||
3394
0
      largest_ack < conn->pktns.crypto.rx.ckm->pkt_num) {
3395
0
    return;
3396
0
  }
3397
3398
0
  conn->flags &= (uint32_t)~NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED;
3399
0
  conn->crypto.key_update.confirmed_ts = ts;
3400
3401
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CRY, "key update confirmed");
3402
0
}
3403
3404
static uint64_t conn_tx_strmq_first_cycle(ngtcp2_conn *conn);
3405
3406
/*
3407
 * strm_should_send_stream_data_blocked returns nonzero if
3408
 * STREAM_DATA_BLOCKED frame should be sent to |strm|.
3409
 */
3410
0
static int strm_should_send_stream_data_blocked(ngtcp2_strm *strm) {
3411
0
  return strm->tx.offset == strm->tx.max_offset &&
3412
0
         strm->tx.last_blocked_offset != strm->tx.max_offset;
3413
0
}
3414
3415
/*
3416
 * conn_should_send_data_blocked returns nonzero if DATA_BLOCKED frame
3417
 * should be sent.
3418
 */
3419
0
static int conn_should_send_data_blocked(ngtcp2_conn *conn) {
3420
0
  return conn->tx.offset == conn->tx.max_offset &&
3421
0
         conn->tx.last_blocked_offset != conn->tx.max_offset;
3422
0
}
3423
3424
/*
3425
 * conn_reset_ppe_pending clears NGTCP2_CONN_FLAG_PPE_PENDING flag and
3426
 * nullifies conn->pkt.
3427
 */
3428
0
static void conn_reset_ppe_pending(ngtcp2_conn *conn) {
3429
0
  conn->flags &= (uint32_t)~NGTCP2_CONN_FLAG_PPE_PENDING;
3430
3431
0
  memset(&conn->pkt, 0, sizeof(conn->pkt));
3432
0
}
3433
3434
/*
3435
 * conn_write_pkt writes a protected packet in the buffer pointed by
3436
 * |dest| whose length if |destlen|.  |dgram_offset| is the offset in
3437
 * UDP datagram payload where this QUIC packet is positioned at.
3438
 * |type| specifies the type of packet.  It can be NGTCP2_PKT_1RTT or
3439
 * NGTCP2_PKT_0RTT.
3440
 *
3441
 * This function can send new stream data.  In order to send stream
3442
 * data, specify the underlying stream and parameters to
3443
 * |vmsg|->stream.  If |vmsg|->stream.fin is set to nonzero, it
3444
 * signals that the given data is the final portion of the stream.
3445
 * |vmsg|->stream.data vector of length |vmsg|->stream.datacnt
3446
 * specifies stream data to send.  The number of bytes sent to the
3447
 * stream is assigned to *|vmsg|->stream.pdatalen.  If 0 length STREAM
3448
 * data is sent, 0 is assigned to it.  The caller should initialize
3449
 * *|vmsg|->stream.pdatalen to -1.
3450
 *
3451
 * If |require_padding| is nonzero, padding bytes are added to occupy
3452
 * the remaining packet payload.
3453
 *
3454
 * This function returns the number of bytes written in |dest| if it
3455
 * succeeds, or one of the following negative error codes:
3456
 *
3457
 * NGTCP2_ERR_NOMEM
3458
 *     Out of memory.
3459
 * NGTCP2_ERR_CALLBACK_FAILURE
3460
 *     User-defined callback function failed.
3461
 * NGTCP2_ERR_STREAM_DATA_BLOCKED
3462
 *     Stream data could not be written because of flow control.
3463
 */
3464
static ngtcp2_ssize conn_write_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
3465
                                   uint8_t *dest, size_t destlen,
3466
                                   size_t dgram_offset, ngtcp2_vmsg *vmsg,
3467
                                   uint8_t type, uint8_t flags,
3468
0
                                   ngtcp2_tstamp ts) {
3469
0
  int rv = 0;
3470
0
  ngtcp2_crypto_cc *cc = &conn->pkt.cc;
3471
0
  ngtcp2_ppe *ppe = &conn->pkt.ppe;
3472
0
  ngtcp2_pkt_hd *hd = &conn->pkt.hd;
3473
0
  ngtcp2_ack_range ack_ranges[NGTCP2_MAX_ACK_RANGES];
3474
0
  ngtcp2_frame lfr;
3475
0
  ngtcp2_ssize nwrite;
3476
0
  ngtcp2_frame_chain **pfrc, *nfrc, *frc;
3477
0
  ngtcp2_rtb_entry *ent;
3478
0
  ngtcp2_strm *strm;
3479
0
  int pkt_empty = 1;
3480
0
  uint64_t ndatalen = 0;
3481
0
  uint64_t wdatalen;
3482
0
  int send_stream = 0;
3483
0
  int stream_blocked = 0;
3484
0
  int send_datagram = 0;
3485
0
  ngtcp2_pktns *pktns = &conn->pktns;
3486
0
  size_t left;
3487
0
  uint64_t datalen = 0;
3488
0
  ngtcp2_vec data[NGTCP2_MAX_STREAM_DATACNT];
3489
0
  size_t datacnt;
3490
0
  uint16_t rtb_entry_flags = NGTCP2_RTB_ENTRY_FLAG_NONE;
3491
0
  int hd_logged = 0;
3492
0
  ngtcp2_path_challenge_entry *pcent;
3493
0
  uint8_t hd_flags = NGTCP2_PKT_FLAG_NONE;
3494
0
  int require_padding = (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING) != 0;
3495
0
  int write_more = (flags & NGTCP2_WRITE_PKT_FLAG_MORE) != 0;
3496
0
  int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
3497
0
  size_t min_pktlen = conn_min_pktlen(conn);
3498
0
  int min_padded = 0;
3499
0
  int padded = 0;
3500
0
  uint64_t crypto_offset;
3501
0
  uint64_t stream_offset;
3502
0
  ngtcp2_ssize num_reclaimed;
3503
0
  uint64_t target_max_data;
3504
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
3505
0
  uint64_t delta;
3506
0
  const ngtcp2_cid *scid = NULL;
3507
0
  int keep_alive_expired = 0;
3508
0
  uint32_t version = 0;
3509
3510
  /* Return 0 if destlen is less than minimum packet length which can
3511
     trigger Stateless Reset */
3512
0
  if (destlen < min_pktlen) {
3513
0
    return 0;
3514
0
  }
3515
3516
0
  if (vmsg) {
3517
0
    switch (vmsg->type) {
3518
0
    case NGTCP2_VMSG_TYPE_STREAM:
3519
0
      datalen = ngtcp2_vec_len(vmsg->stream.data, vmsg->stream.datacnt);
3520
0
      ndatalen = conn_enforce_flow_control(conn, vmsg->stream.strm, datalen);
3521
      /* 0 length STREAM frame is allowed */
3522
0
      if (ndatalen || datalen == 0) {
3523
0
        send_stream = 1;
3524
0
      } else {
3525
0
        stream_blocked = 1;
3526
0
      }
3527
0
      break;
3528
0
    case NGTCP2_VMSG_TYPE_DATAGRAM:
3529
0
      datalen = ngtcp2_vec_len(vmsg->datagram.data, vmsg->datagram.datacnt);
3530
0
      send_datagram = 1;
3531
0
      break;
3532
0
    default:
3533
0
      break;
3534
0
    }
3535
0
  }
3536
3537
0
  if (!ppe_pending) {
3538
0
    switch (type) {
3539
0
    case NGTCP2_PKT_1RTT:
3540
0
      hd_flags = conn_pkt_flags_short(conn);
3541
0
      scid = NULL;
3542
0
      cc->aead = pktns->crypto.ctx.aead;
3543
0
      cc->hp = pktns->crypto.ctx.hp;
3544
0
      cc->ckm = pktns->crypto.tx.ckm;
3545
0
      cc->hp_ctx = pktns->crypto.tx.hp_ctx;
3546
3547
0
      assert(conn->negotiated_version);
3548
3549
0
      version = conn->negotiated_version;
3550
3551
      /* transport parameter is only valid after handshake completion
3552
         which means we don't know how many connection ID that remote
3553
         peer can accept before handshake completion.  Because server
3554
         can use remote transport parameters sending stream data in
3555
         0.5 RTT, it is also allowed to use remote transport
3556
         parameters here.  */
3557
0
      if (conn->oscid.datalen &&
3558
0
          (conn->server || conn_is_tls_handshake_completed(conn))) {
3559
0
        rv = conn_enqueue_new_connection_id(conn);
3560
0
        if (rv != 0) {
3561
0
          return rv;
3562
0
        }
3563
0
      }
3564
3565
0
      break;
3566
0
    case NGTCP2_PKT_0RTT:
3567
0
      assert(!conn->server);
3568
0
      if (!conn->early.ckm) {
3569
0
        return 0;
3570
0
      }
3571
0
      hd_flags = conn_pkt_flags_long(conn);
3572
0
      scid = &conn->oscid;
3573
0
      cc->aead = conn->early.ctx.aead;
3574
0
      cc->hp = conn->early.ctx.hp;
3575
0
      cc->ckm = conn->early.ckm;
3576
0
      cc->hp_ctx = conn->early.hp_ctx;
3577
0
      version = conn->client_chosen_version;
3578
0
      break;
3579
0
    default:
3580
      /* Unreachable */
3581
0
      ngtcp2_unreachable();
3582
0
    }
3583
3584
0
    cc->encrypt = conn->callbacks.encrypt;
3585
0
    cc->hp_mask = conn->callbacks.hp_mask;
3586
3587
0
    if (conn_should_send_max_data(conn)) {
3588
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3589
0
      if (rv != 0) {
3590
0
        return rv;
3591
0
      }
3592
3593
0
      if (conn->local.settings.max_window &&
3594
0
          conn->tx.last_max_data_ts != UINT64_MAX &&
3595
0
          ts - conn->tx.last_max_data_ts <
3596
0
            NGTCP2_FLOW_WINDOW_RTT_FACTOR * cstat->smoothed_rtt &&
3597
0
          conn->local.settings.max_window > conn->rx.window) {
3598
0
        target_max_data = NGTCP2_FLOW_WINDOW_SCALING_FACTOR * conn->rx.window;
3599
0
        if (target_max_data > conn->local.settings.max_window) {
3600
0
          target_max_data = conn->local.settings.max_window;
3601
0
        }
3602
3603
0
        delta = target_max_data - conn->rx.window;
3604
0
        if (conn->rx.unsent_max_offset + delta > NGTCP2_MAX_VARINT) {
3605
0
          delta = NGTCP2_MAX_VARINT - conn->rx.unsent_max_offset;
3606
0
        }
3607
3608
0
        conn->rx.window = target_max_data;
3609
0
      } else {
3610
0
        delta = 0;
3611
0
      }
3612
3613
0
      conn->tx.last_max_data_ts = ts;
3614
3615
0
      nfrc->fr.max_data = (ngtcp2_max_data){
3616
0
        .type = NGTCP2_FRAME_MAX_DATA,
3617
0
        .max_data = conn->rx.unsent_max_offset + delta,
3618
0
      };
3619
0
      nfrc->next = pktns->tx.frq;
3620
0
      pktns->tx.frq = nfrc;
3621
3622
0
      conn->rx.max_offset = conn->rx.unsent_max_offset =
3623
0
        nfrc->fr.max_data.max_data;
3624
0
    }
3625
3626
0
    rv = conn_handle_skip_pkt(conn, pktns, ts);
3627
0
    if (rv != 0) {
3628
0
      return rv;
3629
0
    }
3630
3631
0
    ngtcp2_pkt_hd_init(hd, hd_flags, type, &conn->dcid.current.cid, scid,
3632
0
                       pktns->tx.last_pkt_num + 1,
3633
0
                       pktns_select_pkt_numlen(pktns), version);
3634
3635
0
    ngtcp2_ppe_init(ppe, dest, destlen, dgram_offset, cc);
3636
3637
0
    rv = ngtcp2_ppe_encode_hd(ppe, hd);
3638
0
    if (rv != 0) {
3639
0
      assert(NGTCP2_ERR_NOBUF == rv);
3640
0
      return 0;
3641
0
    }
3642
3643
0
    if (!ngtcp2_ppe_ensure_hp_sample(ppe)) {
3644
0
      return 0;
3645
0
    }
3646
3647
0
    if (ngtcp2_ringbuf_len(&conn->rx.path_challenge.rb)) {
3648
0
      pcent = ngtcp2_ringbuf_get(&conn->rx.path_challenge.rb, 0);
3649
3650
      /* PATH_RESPONSE is bound to the path that the corresponding
3651
         PATH_CHALLENGE is received. */
3652
0
      if (ngtcp2_path_eq(&conn->dcid.current.ps.path, &pcent->ps.path)) {
3653
0
        lfr.path_response = (ngtcp2_path_response){
3654
0
          .type = NGTCP2_FRAME_PATH_RESPONSE,
3655
0
          .data = pcent->data,
3656
0
        };
3657
3658
0
        rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3659
0
        if (rv != 0) {
3660
0
          assert(NGTCP2_ERR_NOBUF == rv);
3661
0
        } else {
3662
0
          ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge.rb);
3663
3664
0
          pkt_empty = 0;
3665
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
3666
0
          require_padding = require_padding || !conn->server ||
3667
0
                            destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE;
3668
          /* We don't retransmit PATH_RESPONSE. */
3669
3670
          /* Include PING to make a packet non-probing as per
3671
             https://datatracker.ietf.org/doc/html/rfc9000#section-9.3.3
3672
3673
             An endpoint that receives a PATH_CHALLENGE on an active
3674
             path SHOULD send a non-probing packet in response. */
3675
0
          lfr.ping.type = NGTCP2_FRAME_PING;
3676
0
          rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3677
0
          if (rv != 0) {
3678
0
            assert(NGTCP2_ERR_NOBUF == rv);
3679
0
          }
3680
0
        }
3681
0
      }
3682
0
    }
3683
3684
0
    lfr.ack.ranges = ack_ranges;
3685
0
    if (ngtcp2_acktr_create_ack_frame(
3686
0
          &pktns->acktr, &lfr.ack, type, ts, conn_compute_ack_delay(conn),
3687
0
          conn->local.transport_params.ack_delay_exponent) == 0) {
3688
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3689
0
      if (rv != 0) {
3690
0
        assert(NGTCP2_ERR_NOBUF == rv);
3691
0
      } else {
3692
0
        ngtcp2_acktr_commit_ack(&pktns->acktr);
3693
0
        ngtcp2_acktr_add_ack(&pktns->acktr, hd->pkt_num, lfr.ack.largest_ack);
3694
0
        assert(NGTCP2_PKT_1RTT == type);
3695
0
        conn_handle_unconfirmed_key_update_from_remote(conn,
3696
0
                                                       lfr.ack.largest_ack, ts);
3697
0
        pkt_empty = 0;
3698
0
      }
3699
0
    }
3700
3701
0
  build_pkt:
3702
0
    for (pfrc = &pktns->tx.frq; *pfrc;) {
3703
0
      if ((*pfrc)->binder &&
3704
0
          ((*pfrc)->binder->flags & NGTCP2_FRAME_CHAIN_BINDER_FLAG_ACK)) {
3705
0
        frc = *pfrc;
3706
0
        *pfrc = (*pfrc)->next;
3707
0
        ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3708
0
        continue;
3709
0
      }
3710
3711
0
      switch ((*pfrc)->fr.hd.type) {
3712
0
      case NGTCP2_FRAME_RESET_STREAM:
3713
0
        strm =
3714
0
          ngtcp2_conn_find_stream(conn, (*pfrc)->fr.reset_stream.stream_id);
3715
0
        if (strm == NULL ||
3716
0
            !ngtcp2_strm_require_retransmit_reset_stream(strm)) {
3717
0
          frc = *pfrc;
3718
0
          *pfrc = (*pfrc)->next;
3719
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3720
0
          continue;
3721
0
        }
3722
0
        break;
3723
0
      case NGTCP2_FRAME_STOP_SENDING:
3724
0
        strm =
3725
0
          ngtcp2_conn_find_stream(conn, (*pfrc)->fr.stop_sending.stream_id);
3726
0
        if (strm == NULL ||
3727
0
            !ngtcp2_strm_require_retransmit_stop_sending(strm)) {
3728
0
          frc = *pfrc;
3729
0
          *pfrc = (*pfrc)->next;
3730
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3731
0
          continue;
3732
0
        }
3733
0
        break;
3734
0
      case NGTCP2_FRAME_STREAM:
3735
0
        ngtcp2_unreachable();
3736
0
      case NGTCP2_FRAME_MAX_STREAMS_BIDI:
3737
0
        if ((*pfrc)->fr.max_streams.max_streams <
3738
0
            conn->remote.bidi.max_streams) {
3739
0
          frc = *pfrc;
3740
0
          *pfrc = (*pfrc)->next;
3741
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3742
0
          continue;
3743
0
        }
3744
0
        break;
3745
0
      case NGTCP2_FRAME_MAX_STREAMS_UNI:
3746
0
        if ((*pfrc)->fr.max_streams.max_streams <
3747
0
            conn->remote.uni.max_streams) {
3748
0
          frc = *pfrc;
3749
0
          *pfrc = (*pfrc)->next;
3750
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3751
0
          continue;
3752
0
        }
3753
0
        break;
3754
0
      case NGTCP2_FRAME_MAX_STREAM_DATA:
3755
0
        strm =
3756
0
          ngtcp2_conn_find_stream(conn, (*pfrc)->fr.max_stream_data.stream_id);
3757
0
        if (strm == NULL || !ngtcp2_strm_require_retransmit_max_stream_data(
3758
0
                              strm, &(*pfrc)->fr.max_stream_data)) {
3759
0
          frc = *pfrc;
3760
0
          *pfrc = (*pfrc)->next;
3761
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3762
0
          continue;
3763
0
        }
3764
0
        break;
3765
0
      case NGTCP2_FRAME_MAX_DATA:
3766
0
        if ((*pfrc)->fr.max_data.max_data < conn->rx.max_offset) {
3767
0
          frc = *pfrc;
3768
0
          *pfrc = (*pfrc)->next;
3769
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3770
0
          continue;
3771
0
        }
3772
0
        break;
3773
0
      case NGTCP2_FRAME_STREAM_DATA_BLOCKED:
3774
0
        strm = ngtcp2_conn_find_stream(
3775
0
          conn, (*pfrc)->fr.stream_data_blocked.stream_id);
3776
0
        if (strm == NULL || !ngtcp2_strm_require_retransmit_stream_data_blocked(
3777
0
                              strm, &(*pfrc)->fr.stream_data_blocked)) {
3778
0
          frc = *pfrc;
3779
0
          *pfrc = (*pfrc)->next;
3780
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3781
0
          continue;
3782
0
        }
3783
0
        break;
3784
0
      case NGTCP2_FRAME_DATA_BLOCKED:
3785
0
        if ((*pfrc)->fr.data_blocked.offset != conn->tx.max_offset) {
3786
0
          frc = *pfrc;
3787
0
          *pfrc = (*pfrc)->next;
3788
0
          ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
3789
0
          continue;
3790
0
        }
3791
0
        break;
3792
0
      case NGTCP2_FRAME_CRYPTO:
3793
0
        ngtcp2_unreachable();
3794
0
      }
3795
3796
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &(*pfrc)->fr);
3797
0
      if (rv != 0) {
3798
0
        assert(NGTCP2_ERR_NOBUF == rv);
3799
0
        break;
3800
0
      }
3801
3802
0
      pkt_empty = 0;
3803
0
      rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3804
0
                         NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
3805
0
                         NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3806
0
      pfrc = &(*pfrc)->next;
3807
0
    }
3808
3809
0
    if (*pfrc == NULL) {
3810
0
      for (; !ngtcp2_strm_streamfrq_empty(&pktns->crypto.strm);) {
3811
0
        left = ngtcp2_ppe_left(ppe);
3812
3813
0
        crypto_offset =
3814
0
          ngtcp2_strm_streamfrq_unacked_offset(&pktns->crypto.strm);
3815
0
        if (crypto_offset == (uint64_t)-1) {
3816
0
          ngtcp2_strm_streamfrq_clear(&pktns->crypto.strm);
3817
0
          break;
3818
0
        }
3819
3820
0
        left = ngtcp2_pkt_crypto_max_datalen(crypto_offset, left, left);
3821
3822
0
        if (left == (size_t)-1) {
3823
0
          break;
3824
0
        }
3825
3826
0
        rv = ngtcp2_strm_streamfrq_pop(&pktns->crypto.strm, &nfrc, left);
3827
0
        if (rv != 0) {
3828
0
          assert(ngtcp2_err_is_fatal(rv));
3829
0
          return rv;
3830
0
        }
3831
3832
0
        if (nfrc == NULL) {
3833
0
          break;
3834
0
        }
3835
3836
0
        rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3837
0
        if (rv != 0) {
3838
0
          ngtcp2_unreachable();
3839
0
        }
3840
3841
0
        *pfrc = nfrc;
3842
0
        pfrc = &(*pfrc)->next;
3843
3844
0
        pkt_empty = 0;
3845
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3846
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
3847
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3848
0
      }
3849
0
    }
3850
3851
0
    if (*pfrc == NULL) {
3852
0
      for (; !ngtcp2_pq_empty(&conn->tx.strmq);) {
3853
0
        strm = ngtcp2_conn_tx_strmq_top(conn);
3854
3855
0
        if (strm->flags & NGTCP2_STRM_FLAG_SEND_RESET_STREAM) {
3856
0
          rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3857
0
          if (rv != 0) {
3858
0
            return rv;
3859
0
          }
3860
3861
0
          nfrc->fr.reset_stream = (ngtcp2_reset_stream){
3862
0
            .type = NGTCP2_FRAME_RESET_STREAM,
3863
0
            .stream_id = strm->stream_id,
3864
0
            .app_error_code = strm->tx.reset_stream_app_error_code,
3865
0
            .final_size = strm->tx.offset,
3866
0
          };
3867
0
          *pfrc = nfrc;
3868
3869
0
          strm->flags &= ~NGTCP2_STRM_FLAG_SEND_RESET_STREAM;
3870
3871
0
          rv =
3872
0
            conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3873
0
          if (rv != 0) {
3874
0
            assert(NGTCP2_ERR_NOBUF == rv);
3875
3876
0
            break;
3877
0
          }
3878
3879
0
          pkt_empty = 0;
3880
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3881
0
                             NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
3882
0
                             NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3883
0
          pfrc = &(*pfrc)->next;
3884
0
        }
3885
3886
0
        if (strm->flags & NGTCP2_STRM_FLAG_SEND_STOP_SENDING) {
3887
0
          if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
3888
0
              ngtcp2_strm_rx_offset(strm) == strm->rx.last_offset) {
3889
0
            strm->flags &= ~NGTCP2_STRM_FLAG_SEND_STOP_SENDING;
3890
0
          } else {
3891
0
            rv = conn_call_stream_stop_sending(
3892
0
              conn, strm->stream_id, strm->tx.stop_sending_app_error_code,
3893
0
              strm->stream_user_data);
3894
0
            if (rv != 0) {
3895
0
              assert(ngtcp2_err_is_fatal(rv));
3896
3897
0
              return rv;
3898
0
            }
3899
3900
0
            rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3901
0
            if (rv != 0) {
3902
0
              return rv;
3903
0
            }
3904
3905
0
            nfrc->fr.stop_sending = (ngtcp2_stop_sending){
3906
0
              .type = NGTCP2_FRAME_STOP_SENDING,
3907
0
              .stream_id = strm->stream_id,
3908
0
              .app_error_code = strm->tx.stop_sending_app_error_code,
3909
0
            };
3910
0
            *pfrc = nfrc;
3911
3912
0
            strm->flags &= ~NGTCP2_STRM_FLAG_SEND_STOP_SENDING;
3913
3914
0
            rv =
3915
0
              conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3916
0
            if (rv != 0) {
3917
0
              assert(NGTCP2_ERR_NOBUF == rv);
3918
3919
0
              break;
3920
0
            }
3921
3922
0
            pkt_empty = 0;
3923
0
            rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3924
0
                               NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
3925
0
                               NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3926
0
            pfrc = &(*pfrc)->next;
3927
0
          }
3928
0
        }
3929
3930
0
        if (!(strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) &&
3931
0
            strm_should_send_stream_data_blocked(strm)) {
3932
0
          rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3933
0
          if (rv != 0) {
3934
0
            return rv;
3935
0
          }
3936
3937
0
          nfrc->fr.stream_data_blocked = (ngtcp2_stream_data_blocked){
3938
0
            .type = NGTCP2_FRAME_STREAM_DATA_BLOCKED,
3939
0
            .stream_id = strm->stream_id,
3940
0
            .offset = strm->tx.max_offset,
3941
0
          };
3942
0
          *pfrc = nfrc;
3943
3944
0
          strm->tx.last_blocked_offset = strm->tx.max_offset;
3945
3946
0
          rv =
3947
0
            conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3948
0
          if (rv != 0) {
3949
0
            assert(NGTCP2_ERR_NOBUF == rv);
3950
3951
0
            break;
3952
0
          }
3953
3954
0
          pkt_empty = 0;
3955
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3956
0
                             NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
3957
0
                             NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3958
0
          pfrc = &(*pfrc)->next;
3959
0
        }
3960
3961
0
        if (!(strm->flags &
3962
0
              (NGTCP2_STRM_FLAG_SHUT_RD | NGTCP2_STRM_FLAG_STOP_SENDING)) &&
3963
0
            conn_should_send_max_stream_data(conn, strm)) {
3964
0
          rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
3965
0
          if (rv != 0) {
3966
0
            assert(ngtcp2_err_is_fatal(rv));
3967
0
            return rv;
3968
0
          }
3969
3970
0
          if (conn->local.settings.max_stream_window &&
3971
0
              strm->tx.last_max_stream_data_ts != UINT64_MAX &&
3972
0
              ts - strm->tx.last_max_stream_data_ts <
3973
0
                NGTCP2_FLOW_WINDOW_RTT_FACTOR * cstat->smoothed_rtt &&
3974
0
              conn->local.settings.max_stream_window > strm->rx.window) {
3975
0
            target_max_data =
3976
0
              NGTCP2_FLOW_WINDOW_SCALING_FACTOR * strm->rx.window;
3977
0
            if (target_max_data > conn->local.settings.max_stream_window) {
3978
0
              target_max_data = conn->local.settings.max_stream_window;
3979
0
            }
3980
3981
0
            delta = target_max_data - strm->rx.window;
3982
0
            if (strm->rx.unsent_max_offset + delta > NGTCP2_MAX_VARINT) {
3983
0
              delta = NGTCP2_MAX_VARINT - strm->rx.unsent_max_offset;
3984
0
            }
3985
3986
0
            strm->rx.window = target_max_data;
3987
0
          } else {
3988
0
            delta = 0;
3989
0
          }
3990
3991
0
          strm->tx.last_max_stream_data_ts = ts;
3992
3993
0
          nfrc->fr.max_stream_data = (ngtcp2_max_stream_data){
3994
0
            .type = NGTCP2_FRAME_MAX_STREAM_DATA,
3995
0
            .stream_id = strm->stream_id,
3996
0
            .max_stream_data = strm->rx.unsent_max_offset + delta,
3997
0
          };
3998
0
          *pfrc = nfrc;
3999
4000
0
          strm->rx.max_offset = strm->rx.unsent_max_offset =
4001
0
            nfrc->fr.max_stream_data.max_stream_data;
4002
4003
0
          rv =
4004
0
            conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4005
0
          if (rv != 0) {
4006
0
            assert(NGTCP2_ERR_NOBUF == rv);
4007
0
            break;
4008
0
          }
4009
4010
0
          pkt_empty = 0;
4011
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4012
0
                             NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4013
0
                             NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4014
0
          pfrc = &(*pfrc)->next;
4015
0
        }
4016
4017
0
        if (ngtcp2_strm_streamfrq_empty(strm)) {
4018
0
          ngtcp2_conn_tx_strmq_pop(conn);
4019
0
          continue;
4020
0
        }
4021
4022
0
        stream_offset = ngtcp2_strm_streamfrq_unacked_offset(strm);
4023
0
        if (stream_offset == (uint64_t)-1) {
4024
0
          ngtcp2_strm_streamfrq_clear(strm);
4025
0
          ngtcp2_conn_tx_strmq_pop(conn);
4026
0
          continue;
4027
0
        }
4028
4029
0
        left = ngtcp2_ppe_left(ppe);
4030
4031
0
        left = ngtcp2_pkt_stream_max_datalen(strm->stream_id, stream_offset,
4032
0
                                             left, left);
4033
4034
0
        if (left == (size_t)-1) {
4035
0
          break;
4036
0
        }
4037
4038
0
        rv = ngtcp2_strm_streamfrq_pop(strm, &nfrc, left);
4039
0
        if (rv != 0) {
4040
0
          assert(ngtcp2_err_is_fatal(rv));
4041
0
          return rv;
4042
0
        }
4043
4044
0
        if (nfrc == NULL) {
4045
          /* TODO Why? */
4046
0
          break;
4047
0
        }
4048
4049
0
        rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4050
0
        if (rv != 0) {
4051
0
          ngtcp2_unreachable();
4052
0
        }
4053
4054
0
        *pfrc = nfrc;
4055
0
        pfrc = &(*pfrc)->next;
4056
4057
0
        pkt_empty = 0;
4058
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4059
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4060
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4061
4062
0
        if (ngtcp2_strm_streamfrq_empty(strm)) {
4063
0
          ngtcp2_conn_tx_strmq_pop(conn);
4064
0
          continue;
4065
0
        }
4066
4067
0
        ngtcp2_conn_tx_strmq_pop(conn);
4068
0
        ++strm->cycle;
4069
0
        rv = ngtcp2_conn_tx_strmq_push(conn, strm);
4070
0
        if (rv != 0) {
4071
0
          assert(ngtcp2_err_is_fatal(rv));
4072
0
          return rv;
4073
0
        }
4074
0
      }
4075
0
    }
4076
4077
    /* Write MAX_STREAMS after RESET_STREAM so that we can extend
4078
       stream ID space in one packet. */
4079
0
    if (*pfrc == NULL &&
4080
0
        conn->remote.bidi.unsent_max_streams > conn->remote.bidi.max_streams) {
4081
0
      rv = conn_call_extend_max_remote_streams_bidi(
4082
0
        conn, conn->remote.bidi.unsent_max_streams);
4083
0
      if (rv != 0) {
4084
0
        assert(ngtcp2_err_is_fatal(rv));
4085
0
        return rv;
4086
0
      }
4087
4088
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4089
0
      if (rv != 0) {
4090
0
        assert(ngtcp2_err_is_fatal(rv));
4091
0
        return rv;
4092
0
      }
4093
0
      nfrc->fr.max_streams = (ngtcp2_max_streams){
4094
0
        .type = NGTCP2_FRAME_MAX_STREAMS_BIDI,
4095
0
        .max_streams = conn->remote.bidi.unsent_max_streams,
4096
0
      };
4097
0
      *pfrc = nfrc;
4098
4099
0
      conn->remote.bidi.max_streams = conn->remote.bidi.unsent_max_streams;
4100
4101
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &(*pfrc)->fr);
4102
0
      if (rv != 0) {
4103
0
        assert(NGTCP2_ERR_NOBUF == rv);
4104
0
      } else {
4105
0
        pkt_empty = 0;
4106
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4107
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4108
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4109
0
        pfrc = &(*pfrc)->next;
4110
0
      }
4111
0
    }
4112
4113
0
    if (*pfrc == NULL &&
4114
0
        conn->remote.uni.unsent_max_streams > conn->remote.uni.max_streams) {
4115
0
      rv = conn_call_extend_max_remote_streams_uni(
4116
0
        conn, conn->remote.uni.unsent_max_streams);
4117
0
      if (rv != 0) {
4118
0
        assert(ngtcp2_err_is_fatal(rv));
4119
0
        return rv;
4120
0
      }
4121
4122
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4123
0
      if (rv != 0) {
4124
0
        assert(ngtcp2_err_is_fatal(rv));
4125
0
        return rv;
4126
0
      }
4127
0
      nfrc->fr.max_streams = (ngtcp2_max_streams){
4128
0
        .type = NGTCP2_FRAME_MAX_STREAMS_UNI,
4129
0
        .max_streams = conn->remote.uni.unsent_max_streams,
4130
0
      };
4131
0
      *pfrc = nfrc;
4132
4133
0
      conn->remote.uni.max_streams = conn->remote.uni.unsent_max_streams;
4134
4135
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &(*pfrc)->fr);
4136
0
      if (rv != 0) {
4137
0
        assert(NGTCP2_ERR_NOBUF == rv);
4138
0
      } else {
4139
0
        pkt_empty = 0;
4140
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4141
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4142
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4143
0
        pfrc = &(*pfrc)->next;
4144
0
      }
4145
0
    }
4146
4147
0
    if (pktns->tx.frq == NULL && !send_stream && !send_datagram &&
4148
0
        !(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
4149
0
        pktns->rtb.num_retransmittable && pktns->rtb.probe_pkt_left) {
4150
0
      num_reclaimed = ngtcp2_rtb_reclaim_on_pto(&pktns->rtb, conn, pktns, 1);
4151
0
      if (num_reclaimed < 0) {
4152
0
        return num_reclaimed;
4153
0
      }
4154
0
      if (num_reclaimed) {
4155
0
        goto build_pkt;
4156
0
      }
4157
4158
      /* We had pktns->rtb.num_retransmittable > 0 but we were unable
4159
         to reclaim any frame.  In this case, we do not have to send
4160
         any probe packet. */
4161
0
      if (pktns->rtb.num_pto_eliciting == 0) {
4162
0
        pktns->rtb.probe_pkt_left = 0;
4163
0
        ngtcp2_conn_set_loss_detection_timer(conn, ts);
4164
4165
0
        if (pkt_empty && conn_cwnd_is_zero(conn) && !require_padding) {
4166
0
          return 0;
4167
0
        }
4168
0
      }
4169
0
    }
4170
0
  } else {
4171
0
    pfrc = conn->pkt.pfrc;
4172
0
    rtb_entry_flags |= conn->pkt.rtb_entry_flags;
4173
0
    pkt_empty = conn->pkt.pkt_empty;
4174
0
    hd_logged = conn->pkt.hd_logged;
4175
0
    require_padding = conn->pkt.require_padding;
4176
0
  }
4177
4178
0
  left = ngtcp2_ppe_left(ppe);
4179
4180
0
  if (*pfrc == NULL && send_stream && ngtcp2_pq_empty(&conn->tx.strmq) &&
4181
0
      (wdatalen = ngtcp2_pkt_stream_max_datalen(
4182
0
         vmsg->stream.strm->stream_id, vmsg->stream.strm->tx.offset, ndatalen,
4183
0
         left)) != (size_t)-1 &&
4184
0
      (wdatalen == ndatalen || wdatalen >= NGTCP2_MIN_STREAM_DATALEN) &&
4185
0
      (wdatalen || datalen == 0)) {
4186
0
    ndatalen = wdatalen;
4187
0
    datacnt = ngtcp2_vec_copy_at_most(data, NGTCP2_MAX_STREAM_DATACNT,
4188
0
                                      vmsg->stream.data, vmsg->stream.datacnt,
4189
0
                                      (size_t)ndatalen);
4190
0
    ndatalen = ngtcp2_vec_len(data, datacnt);
4191
4192
0
    assert((datacnt == 0 && datalen == 0) || (datacnt && datalen));
4193
4194
0
    rv = ngtcp2_frame_chain_stream_datacnt_objalloc_new(
4195
0
      &nfrc, datacnt, &conn->frc_objalloc, conn->mem);
4196
0
    if (rv != 0) {
4197
0
      assert(ngtcp2_err_is_fatal(rv));
4198
0
      return rv;
4199
0
    }
4200
4201
0
    nfrc->fr.stream.type = NGTCP2_FRAME_STREAM;
4202
0
    nfrc->fr.stream.flags = 0;
4203
0
    nfrc->fr.stream.fin = 0;
4204
0
    nfrc->fr.stream.stream_id = vmsg->stream.strm->stream_id;
4205
0
    nfrc->fr.stream.offset = vmsg->stream.strm->tx.offset;
4206
0
    nfrc->fr.stream.datacnt = datacnt;
4207
0
    ngtcp2_vec_copy(nfrc->fr.stream.data, data, datacnt);
4208
4209
0
    nfrc->fr.stream.fin = (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_FIN) &&
4210
0
                          ndatalen == datalen;
4211
4212
0
    rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4213
0
    if (rv != 0) {
4214
0
      ngtcp2_unreachable();
4215
0
    }
4216
4217
0
    *pfrc = nfrc;
4218
0
    pfrc = &(*pfrc)->next;
4219
4220
0
    pkt_empty = 0;
4221
0
    rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4222
0
                       NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4223
0
                       NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4224
4225
0
    vmsg->stream.strm->tx.offset += ndatalen;
4226
0
    conn->tx.offset += ndatalen;
4227
0
    vmsg->stream.strm->flags |= NGTCP2_STRM_FLAG_ANY_SENT;
4228
4229
0
    if (nfrc->fr.stream.fin) {
4230
0
      ngtcp2_strm_shutdown(vmsg->stream.strm, NGTCP2_STRM_FLAG_SHUT_WR);
4231
0
    }
4232
4233
0
    if (vmsg->stream.pdatalen) {
4234
0
      *vmsg->stream.pdatalen = (ngtcp2_ssize)ndatalen;
4235
0
    }
4236
0
  } else {
4237
0
    send_stream = 0;
4238
0
  }
4239
4240
0
  if (vmsg && vmsg->type == NGTCP2_VMSG_TYPE_STREAM &&
4241
0
      ((stream_blocked && *pfrc == NULL) ||
4242
0
       (send_stream &&
4243
0
        !(vmsg->stream.strm->flags & NGTCP2_STRM_FLAG_SHUT_WR)))) {
4244
0
    if (conn_should_send_data_blocked(conn)) {
4245
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4246
0
      if (rv != 0) {
4247
0
        assert(ngtcp2_err_is_fatal(rv));
4248
4249
0
        return rv;
4250
0
      }
4251
4252
0
      nfrc->fr.data_blocked = (ngtcp2_data_blocked){
4253
0
        .type = NGTCP2_FRAME_DATA_BLOCKED,
4254
0
        .offset = conn->tx.offset,
4255
0
      };
4256
4257
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4258
0
      if (rv != 0) {
4259
0
        assert(NGTCP2_ERR_NOBUF == rv);
4260
4261
        /* We cannot add nfrc to pktns->tx.frq here. */
4262
0
        ngtcp2_frame_chain_objalloc_del(nfrc, &conn->frc_objalloc, conn->mem);
4263
0
      } else {
4264
0
        *pfrc = nfrc;
4265
0
        pfrc = &(*pfrc)->next;
4266
4267
0
        pkt_empty = 0;
4268
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4269
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4270
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4271
4272
0
        conn->tx.last_blocked_offset = conn->tx.max_offset;
4273
0
      }
4274
0
    }
4275
4276
0
    strm = vmsg->stream.strm;
4277
4278
0
    if (strm_should_send_stream_data_blocked(strm)) {
4279
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4280
0
      if (rv != 0) {
4281
0
        assert(ngtcp2_err_is_fatal(rv));
4282
4283
0
        return rv;
4284
0
      }
4285
4286
0
      nfrc->fr.stream_data_blocked = (ngtcp2_stream_data_blocked){
4287
0
        .type = NGTCP2_FRAME_STREAM_DATA_BLOCKED,
4288
0
        .stream_id = strm->stream_id,
4289
0
        .offset = strm->tx.max_offset,
4290
0
      };
4291
4292
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4293
0
      if (rv != 0) {
4294
0
        assert(NGTCP2_ERR_NOBUF == rv);
4295
4296
        /* We cannot add nfrc to pktns->tx.frq here. */
4297
0
        ngtcp2_frame_chain_objalloc_del(nfrc, &conn->frc_objalloc, conn->mem);
4298
4299
0
        if (!ngtcp2_strm_is_tx_queued(strm)) {
4300
0
          strm->cycle = conn_tx_strmq_first_cycle(conn);
4301
0
          rv = ngtcp2_conn_tx_strmq_push(conn, strm);
4302
0
          if (rv != 0) {
4303
0
            return rv;
4304
0
          }
4305
0
        }
4306
0
      } else {
4307
0
        *pfrc = nfrc;
4308
0
        pfrc = &(*pfrc)->next;
4309
4310
0
        pkt_empty = 0;
4311
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4312
0
                           NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4313
0
                           NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
4314
4315
0
        strm->tx.last_blocked_offset = strm->tx.max_offset;
4316
0
      }
4317
0
    }
4318
0
  }
4319
4320
0
  if (*pfrc == NULL && send_datagram &&
4321
0
      left >= ngtcp2_pkt_datagram_framelen((size_t)datalen)) {
4322
0
    if (conn->callbacks.ack_datagram || conn->callbacks.lost_datagram) {
4323
0
      rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4324
0
      if (rv != 0) {
4325
0
        assert(ngtcp2_err_is_fatal(rv));
4326
0
        return rv;
4327
0
      }
4328
4329
0
      nfrc->fr.datagram.type = NGTCP2_FRAME_DATAGRAM_LEN;
4330
0
      nfrc->fr.datagram.dgram_id = vmsg->datagram.dgram_id;
4331
0
      nfrc->fr.datagram.datacnt = vmsg->datagram.datacnt;
4332
0
      nfrc->fr.datagram.data = (ngtcp2_vec *)vmsg->datagram.data;
4333
4334
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
4335
0
      assert(rv == 0);
4336
4337
      /* Because DATAGRAM will not be retransmitted, we do not use
4338
         data anymore.  Just nullify it.  The only reason to keep
4339
         track a frame is keep dgram_id to pass it to
4340
         ngtcp2_ack_datagram or ngtcp2_lost_datagram callbacks. */
4341
0
      nfrc->fr.datagram.datacnt = 0;
4342
0
      nfrc->fr.datagram.data = NULL;
4343
4344
0
      *pfrc = nfrc;
4345
0
      pfrc = &(*pfrc)->next;
4346
0
    } else {
4347
0
      lfr.datagram.type = NGTCP2_FRAME_DATAGRAM_LEN;
4348
0
      lfr.datagram.datacnt = vmsg->datagram.datacnt;
4349
0
      lfr.datagram.data = (ngtcp2_vec *)vmsg->datagram.data;
4350
4351
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
4352
0
      assert(rv == 0);
4353
0
    }
4354
4355
0
    pkt_empty = 0;
4356
0
    rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
4357
0
                       NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4358
0
                       NGTCP2_RTB_ENTRY_FLAG_DATAGRAM;
4359
4360
0
    if (vmsg->datagram.paccepted) {
4361
0
      *vmsg->datagram.paccepted = 1;
4362
0
    }
4363
0
  } else {
4364
0
    send_datagram = 0;
4365
0
  }
4366
4367
0
  if (pkt_empty) {
4368
0
    if (*pfrc == NULL && rv == 0 && stream_blocked &&
4369
0
        (write_more || !require_padding) &&
4370
0
        ngtcp2_conn_get_max_data_left(conn)) {
4371
0
      if (write_more) {
4372
0
        conn->pkt.pfrc = pfrc;
4373
0
        conn->pkt.pkt_empty = pkt_empty;
4374
0
        conn->pkt.rtb_entry_flags = rtb_entry_flags;
4375
0
        conn->pkt.hd_logged = hd_logged;
4376
0
        conn->pkt.require_padding = require_padding;
4377
0
        conn->flags |= NGTCP2_CONN_FLAG_PPE_PENDING;
4378
0
      }
4379
4380
0
      return NGTCP2_ERR_STREAM_DATA_BLOCKED;
4381
0
    }
4382
4383
0
    keep_alive_expired =
4384
0
      type == NGTCP2_PKT_1RTT && conn_keep_alive_expired(conn, ts);
4385
4386
0
    if (conn->pktns.rtb.probe_pkt_left == 0 && !keep_alive_expired &&
4387
0
        !require_padding) {
4388
0
      conn_reset_ppe_pending(conn);
4389
4390
0
      return 0;
4391
0
    }
4392
0
  } else if (write_more) {
4393
0
    conn->pkt.pfrc = pfrc;
4394
0
    conn->pkt.pkt_empty = pkt_empty;
4395
0
    conn->pkt.rtb_entry_flags = rtb_entry_flags;
4396
0
    conn->pkt.hd_logged = hd_logged;
4397
0
    conn->pkt.require_padding = require_padding;
4398
0
    conn->flags |= NGTCP2_CONN_FLAG_PPE_PENDING;
4399
4400
0
    assert(vmsg);
4401
4402
0
    switch (vmsg->type) {
4403
0
    case NGTCP2_VMSG_TYPE_STREAM:
4404
0
      if (send_stream) {
4405
0
        if (ngtcp2_ppe_left(ppe)) {
4406
0
          return NGTCP2_ERR_WRITE_MORE;
4407
0
        }
4408
0
        break;
4409
0
      }
4410
4411
0
      if (*pfrc == NULL && ngtcp2_conn_get_max_data_left(conn) &&
4412
0
          stream_blocked) {
4413
0
        return NGTCP2_ERR_STREAM_DATA_BLOCKED;
4414
0
      }
4415
0
      break;
4416
0
    case NGTCP2_VMSG_TYPE_DATAGRAM:
4417
0
      if (send_datagram && ngtcp2_ppe_left(ppe)) {
4418
0
        return NGTCP2_ERR_WRITE_MORE;
4419
0
      }
4420
      /* If DATAGRAM cannot be written due to insufficient space,
4421
         continue to create a packet with the hope that application
4422
         calls ngtcp2_conn_writev_datagram again. */
4423
0
      break;
4424
0
    default:
4425
0
      ngtcp2_unreachable();
4426
0
    }
4427
0
  }
4428
4429
0
  if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
4430
0
    if (ngtcp2_tstamp_elapsed(pktns->tx.non_ack_pkt_start_ts,
4431
0
                              cstat->smoothed_rtt, ts) ||
4432
0
        keep_alive_expired || conn->pktns.rtb.probe_pkt_left) {
4433
0
      lfr.ping.type = NGTCP2_FRAME_PING;
4434
4435
0
      rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
4436
0
      if (rv != 0) {
4437
0
        assert(rv == NGTCP2_ERR_NOBUF);
4438
        /* TODO If buffer is too small, PING cannot be written if
4439
           packet is still empty. */
4440
0
      } else {
4441
0
        rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
4442
0
        if (conn->pktns.rtb.probe_pkt_left) {
4443
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_PROBE;
4444
0
        } else {
4445
0
          rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING;
4446
0
        }
4447
0
        pktns->tx.non_ack_pkt_start_ts = UINT64_MAX;
4448
0
      }
4449
0
    } else if (pktns->tx.non_ack_pkt_start_ts == UINT64_MAX) {
4450
0
      pktns->tx.non_ack_pkt_start_ts = ts;
4451
0
    }
4452
0
  } else {
4453
0
    pktns->tx.non_ack_pkt_start_ts = UINT64_MAX;
4454
0
  }
4455
4456
  /* TODO Push STREAM frame back to ngtcp2_strm if there is an error
4457
     before ngtcp2_rtb_entry is safely created and added. */
4458
0
  if ((flags & (NGTCP2_WRITE_PKT_FLAG_PADDING_IF_NOT_EMPTY)) &&
4459
0
      (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
4460
0
    lfr.padding.len = ngtcp2_ppe_padding_size(ppe, destlen);
4461
0
  } else if (require_padding) {
4462
0
    lfr.padding.len = conn_dgram_padding(conn, ppe);
4463
0
  } else {
4464
0
    lfr.padding.len = ngtcp2_ppe_padding_size(ppe, min_pktlen);
4465
0
    min_padded = 1;
4466
0
  }
4467
4468
0
  if (lfr.padding.len) {
4469
0
    if (!min_padded ||
4470
0
        (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
4471
0
      padded = 1;
4472
0
    }
4473
0
    lfr.padding.type = NGTCP2_FRAME_PADDING;
4474
0
    ngtcp2_log_tx_fr(&conn->log, hd, &lfr);
4475
0
    ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
4476
0
  }
4477
4478
0
  nwrite = ngtcp2_ppe_final(ppe, NULL);
4479
0
  if (nwrite < 0) {
4480
0
    assert(ngtcp2_err_is_fatal((int)nwrite));
4481
0
    return nwrite;
4482
0
  }
4483
4484
0
  ++cc->ckm->use_count;
4485
4486
0
  ngtcp2_qlog_pkt_sent_end(&conn->qlog, hd, (size_t)nwrite);
4487
4488
  /* TODO ack-eliciting vs needs-tracking */
4489
  /* probe packet needs tracking but it does not need ACK, could be lost. */
4490
0
  if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) {
4491
0
    if (pi) {
4492
0
      conn_handle_tx_ecn(conn, pi, &rtb_entry_flags, pktns, hd, ts);
4493
0
    }
4494
4495
0
    rv =
4496
0
      ngtcp2_rtb_entry_objalloc_new(&ent, hd, NULL, ts, (size_t)nwrite,
4497
0
                                    rtb_entry_flags, &conn->rtb_entry_objalloc);
4498
0
    if (rv != 0) {
4499
0
      assert(ngtcp2_err_is_fatal(rv));
4500
0
      return rv;
4501
0
    }
4502
4503
0
    if (*pfrc != pktns->tx.frq) {
4504
0
      ent->frc = pktns->tx.frq;
4505
0
      pktns->tx.frq = *pfrc;
4506
0
      *pfrc = NULL;
4507
0
    }
4508
4509
0
    rv = conn_on_pkt_sent(conn, pktns, ent);
4510
0
    if (rv != 0) {
4511
0
      assert(ngtcp2_err_is_fatal(rv));
4512
0
      ngtcp2_rtb_entry_objalloc_del(ent, &conn->rtb_entry_objalloc,
4513
0
                                    &conn->frc_objalloc, conn->mem);
4514
0
      return rv;
4515
0
    }
4516
4517
0
    if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
4518
0
        (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE)) {
4519
0
      conn_restart_timer_on_write(conn, ts);
4520
0
    }
4521
0
  } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
4522
0
    conn_handle_tx_ecn(conn, pi, NULL, pktns, hd, ts);
4523
0
  }
4524
4525
0
  conn_reset_ppe_pending(conn);
4526
4527
0
  if (pktns->rtb.probe_pkt_left &&
4528
0
      (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
4529
0
    --pktns->rtb.probe_pkt_left;
4530
4531
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON, "probe pkt size=%td",
4532
0
                     nwrite);
4533
0
  }
4534
4535
0
  conn_update_keep_alive_last_ts(conn, ts);
4536
4537
0
  conn->dcid.current.bytes_sent += (uint64_t)nwrite;
4538
4539
0
  conn->tx.pacing.pktlen += (size_t)nwrite;
4540
4541
0
  ++conn->cstat.pkt_sent;
4542
0
  conn->cstat.bytes_sent += (uint64_t)nwrite;
4543
4544
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
4545
4546
0
  ++pktns->tx.last_pkt_num;
4547
4548
0
  return nwrite;
4549
0
}
4550
4551
ngtcp2_ssize ngtcp2_conn_write_single_frame_pkt(
4552
  ngtcp2_conn *conn, ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen,
4553
  uint8_t type, uint8_t flags, const ngtcp2_cid *dcid, ngtcp2_frame *fr,
4554
0
  uint16_t rtb_entry_flags, const ngtcp2_path *path, ngtcp2_tstamp ts) {
4555
0
  int rv;
4556
0
  ngtcp2_ppe ppe;
4557
0
  ngtcp2_pkt_hd hd;
4558
0
  ngtcp2_frame lfr;
4559
0
  ngtcp2_ssize nwrite;
4560
0
  ngtcp2_crypto_cc cc;
4561
0
  ngtcp2_pktns *pktns;
4562
0
  uint8_t hd_flags;
4563
0
  ngtcp2_rtb_entry *rtbent;
4564
0
  int padded = 0;
4565
0
  const ngtcp2_cid *scid;
4566
0
  uint32_t version;
4567
4568
0
  switch (type) {
4569
0
  case NGTCP2_PKT_INITIAL:
4570
0
    pktns = conn->in_pktns;
4571
0
    hd_flags = conn_pkt_flags_long(conn);
4572
0
    scid = &conn->oscid;
4573
0
    version = conn->negotiated_version ? conn->negotiated_version
4574
0
                                       : conn->client_chosen_version;
4575
0
    if (version == conn->client_chosen_version) {
4576
0
      cc.ckm = pktns->crypto.tx.ckm;
4577
0
      cc.hp_ctx = pktns->crypto.tx.hp_ctx;
4578
0
    } else {
4579
0
      assert(version == conn->vneg.version);
4580
4581
0
      cc.ckm = conn->vneg.tx.ckm;
4582
0
      cc.hp_ctx = conn->vneg.tx.hp_ctx;
4583
0
    }
4584
0
    break;
4585
0
  case NGTCP2_PKT_HANDSHAKE:
4586
0
    pktns = conn->hs_pktns;
4587
0
    hd_flags = conn_pkt_flags_long(conn);
4588
0
    scid = &conn->oscid;
4589
0
    version = conn->negotiated_version;
4590
0
    cc.ckm = pktns->crypto.tx.ckm;
4591
0
    cc.hp_ctx = pktns->crypto.tx.hp_ctx;
4592
0
    break;
4593
0
  case NGTCP2_PKT_1RTT:
4594
0
    pktns = &conn->pktns;
4595
0
    hd_flags = conn_pkt_flags_short(conn);
4596
0
    scid = NULL;
4597
0
    version = conn->negotiated_version;
4598
0
    cc.ckm = pktns->crypto.tx.ckm;
4599
0
    cc.hp_ctx = pktns->crypto.tx.hp_ctx;
4600
4601
0
    rv = conn_handle_skip_pkt(conn, pktns, ts);
4602
0
    if (rv != 0) {
4603
0
      return rv;
4604
0
    }
4605
4606
0
    break;
4607
0
  default:
4608
    /* We don't support 0-RTT packet in this function. */
4609
0
    ngtcp2_unreachable();
4610
0
  }
4611
4612
0
  cc.aead = pktns->crypto.ctx.aead;
4613
0
  cc.hp = pktns->crypto.ctx.hp;
4614
0
  cc.encrypt = conn->callbacks.encrypt;
4615
0
  cc.hp_mask = conn->callbacks.hp_mask;
4616
4617
0
  ngtcp2_pkt_hd_init(&hd, hd_flags, type, dcid, scid,
4618
0
                     pktns->tx.last_pkt_num + 1, pktns_select_pkt_numlen(pktns),
4619
0
                     version);
4620
4621
0
  ngtcp2_ppe_init(&ppe, dest, destlen, 0, &cc);
4622
4623
0
  rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
4624
0
  if (rv != 0) {
4625
0
    assert(NGTCP2_ERR_NOBUF == rv);
4626
0
    return 0;
4627
0
  }
4628
4629
0
  if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
4630
0
    return 0;
4631
0
  }
4632
4633
0
  ngtcp2_log_tx_pkt_hd(&conn->log, &hd);
4634
0
  ngtcp2_qlog_pkt_sent_start(&conn->qlog);
4635
4636
0
  rv = conn_ppe_write_frame(conn, &ppe, &hd, fr);
4637
0
  if (rv != 0) {
4638
0
    assert(NGTCP2_ERR_NOBUF == rv);
4639
0
    return 0;
4640
0
  }
4641
4642
0
  lfr.padding.type = NGTCP2_FRAME_PADDING;
4643
0
  if (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING_FULL) {
4644
0
    lfr.padding.len = ngtcp2_ppe_dgram_padding_size(&ppe, destlen);
4645
0
  } else if (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING) {
4646
0
    lfr.padding.len = conn_dgram_padding(conn, &ppe);
4647
0
  } else {
4648
0
    switch (fr->hd.type) {
4649
0
    case NGTCP2_FRAME_PATH_CHALLENGE:
4650
0
    case NGTCP2_FRAME_PATH_RESPONSE:
4651
0
      if (!conn->server || destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
4652
0
        lfr.padding.len = conn_dgram_padding(conn, &ppe);
4653
0
      } else {
4654
0
        lfr.padding.len = 0;
4655
0
      }
4656
0
      break;
4657
0
    default:
4658
0
      lfr.padding.len = ngtcp2_ppe_padding_size(&ppe, conn_min_pktlen(conn));
4659
0
    }
4660
0
  }
4661
0
  if (lfr.padding.len) {
4662
0
    padded = 1;
4663
0
    ngtcp2_log_tx_fr(&conn->log, &hd, &lfr);
4664
0
    ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
4665
0
  }
4666
4667
0
  nwrite = ngtcp2_ppe_final(&ppe, NULL);
4668
0
  if (nwrite < 0) {
4669
0
    return nwrite;
4670
0
  }
4671
4672
0
  if (type == NGTCP2_PKT_1RTT) {
4673
0
    ++cc.ckm->use_count;
4674
0
  }
4675
4676
0
  ngtcp2_qlog_pkt_sent_end(&conn->qlog, &hd, (size_t)nwrite);
4677
4678
  /* Do this when we are sure that there is no error. */
4679
0
  switch (fr->hd.type) {
4680
0
  case NGTCP2_FRAME_ACK:
4681
0
  case NGTCP2_FRAME_ACK_ECN:
4682
0
    ngtcp2_acktr_commit_ack(&pktns->acktr);
4683
0
    ngtcp2_acktr_add_ack(&pktns->acktr, hd.pkt_num, fr->ack.largest_ack);
4684
0
    if (type == NGTCP2_PKT_1RTT) {
4685
0
      conn_handle_unconfirmed_key_update_from_remote(conn, fr->ack.largest_ack,
4686
0
                                                     ts);
4687
0
    }
4688
4689
0
    if (!(flags & (NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING_FULL |
4690
0
                   NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING))) {
4691
0
      padded = 0;
4692
0
    }
4693
4694
0
    break;
4695
0
  case NGTCP2_FRAME_CONNECTION_CLOSE:
4696
0
  case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
4697
    /* Clear padded so that we never store the terminal packet in
4698
       ngtcp2_rtb. */
4699
0
    padded = 0;
4700
4701
0
    break;
4702
0
  }
4703
4704
0
  if (((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) &&
4705
0
      (!path || ngtcp2_path_eq(&conn->dcid.current.ps.path, path))) {
4706
0
    if (pi && (conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE ||
4707
0
               !(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_PMTUD_PROBE))) {
4708
0
      conn_handle_tx_ecn(conn, pi, &rtb_entry_flags, pktns, &hd, ts);
4709
0
    }
4710
4711
0
    rv =
4712
0
      ngtcp2_rtb_entry_objalloc_new(&rtbent, &hd, NULL, ts, (size_t)nwrite,
4713
0
                                    rtb_entry_flags, &conn->rtb_entry_objalloc);
4714
0
    if (rv != 0) {
4715
0
      return rv;
4716
0
    }
4717
4718
0
    rv = conn_on_pkt_sent(conn, pktns, rtbent);
4719
0
    if (rv != 0) {
4720
0
      ngtcp2_rtb_entry_objalloc_del(rtbent, &conn->rtb_entry_objalloc,
4721
0
                                    &conn->frc_objalloc, conn->mem);
4722
0
      return rv;
4723
0
    }
4724
4725
0
    if (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
4726
0
      if (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE) {
4727
0
        conn_restart_timer_on_write(conn, ts);
4728
0
      }
4729
4730
0
      if (pktns->rtb.probe_pkt_left && path &&
4731
0
          ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
4732
0
        --pktns->rtb.probe_pkt_left;
4733
4734
0
        ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON, "probe pkt size=%td",
4735
0
                         nwrite);
4736
0
      }
4737
0
    }
4738
0
  } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
4739
0
    conn_handle_tx_ecn(conn, pi, NULL, pktns, &hd, ts);
4740
0
  }
4741
4742
0
  if (path && ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
4743
0
    conn_update_keep_alive_last_ts(conn, ts);
4744
0
  }
4745
4746
0
  if (!padded) {
4747
0
    switch (fr->hd.type) {
4748
0
    case NGTCP2_FRAME_ACK:
4749
0
    case NGTCP2_FRAME_ACK_ECN:
4750
0
      break;
4751
0
    default:
4752
0
      conn->tx.pacing.pktlen += (size_t)nwrite;
4753
0
    }
4754
0
  } else {
4755
0
    conn->tx.pacing.pktlen += (size_t)nwrite;
4756
0
  }
4757
4758
0
  ++conn->cstat.pkt_sent;
4759
0
  conn->cstat.bytes_sent += (uint64_t)nwrite;
4760
4761
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
4762
4763
0
  ++pktns->tx.last_pkt_num;
4764
4765
0
  return nwrite;
4766
0
}
4767
4768
/*
4769
 * conn_process_early_rtb makes any pending 0RTT packet 1RTT packet.
4770
 */
4771
0
static void conn_process_early_rtb(ngtcp2_conn *conn) {
4772
0
  ngtcp2_rtb_entry *ent;
4773
0
  ngtcp2_rtb *rtb = &conn->pktns.rtb;
4774
0
  ngtcp2_ksl_it it;
4775
4776
0
  for (it = ngtcp2_rtb_head(rtb); !ngtcp2_ksl_it_end(&it);
4777
0
       ngtcp2_ksl_it_next(&it)) {
4778
0
    ent = ngtcp2_ksl_it_get(&it);
4779
4780
0
    if ((ent->hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) == 0 ||
4781
0
        ent->hd.type != NGTCP2_PKT_0RTT) {
4782
0
      continue;
4783
0
    }
4784
4785
    /*  0-RTT packet is retransmitted as a 1RTT packet. */
4786
0
    ent->hd.flags &= (uint8_t)~NGTCP2_PKT_FLAG_LONG_FORM;
4787
0
    ent->hd.type = NGTCP2_PKT_1RTT;
4788
0
  }
4789
0
}
4790
4791
/*
4792
 * conn_handshake_remnants_left returns nonzero if there may be
4793
 * handshake packets the local endpoint has to send, including new
4794
 * packets and lost ones.
4795
 */
4796
0
static int conn_handshake_remnants_left(ngtcp2_conn *conn) {
4797
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
4798
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
4799
4800
0
  return !conn_is_tls_handshake_completed(conn) ||
4801
0
         (in_pktns && (in_pktns->rtb.num_pto_eliciting ||
4802
0
                       !ngtcp2_strm_streamfrq_empty(&in_pktns->crypto.strm))) ||
4803
0
         (hs_pktns && (hs_pktns->rtb.num_pto_eliciting ||
4804
0
                       !ngtcp2_strm_streamfrq_empty(&hs_pktns->crypto.strm)));
4805
0
}
4806
4807
/*
4808
 * conn_enqueue_retire_connection_id enqueues RETIRE_CONNECTION_ID
4809
 * frame with |seq|.
4810
 *
4811
 * This function returns 0 if it succeeds, or one of the following
4812
 * negative error codes:
4813
 *
4814
 * NGTCP2_ERR_NOMEM
4815
 *     Out of memory.
4816
 */
4817
0
static int conn_enqueue_retire_connection_id(ngtcp2_conn *conn, uint64_t seq) {
4818
0
  ngtcp2_pktns *pktns = &conn->pktns;
4819
0
  ngtcp2_frame_chain *nfrc;
4820
0
  int rv;
4821
4822
0
  rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
4823
0
  if (rv != 0) {
4824
0
    return rv;
4825
0
  }
4826
4827
0
  nfrc->fr.retire_connection_id = (ngtcp2_retire_connection_id){
4828
0
    .type = NGTCP2_FRAME_RETIRE_CONNECTION_ID,
4829
0
    .seq = seq,
4830
0
  };
4831
0
  nfrc->next = pktns->tx.frq;
4832
0
  pktns->tx.frq = nfrc;
4833
4834
0
  return 0;
4835
0
}
4836
4837
0
static int dcidtr_on_retire(const ngtcp2_dcid *dcid, void *user_data) {
4838
0
  return conn_enqueue_retire_connection_id(user_data, dcid->seq);
4839
0
}
4840
4841
/*
4842
 * conn_retire_active_dcid retires the activated |dcid|.
4843
 *
4844
 * This function returns 0 if it succeeds, or one of the following
4845
 * negative error codes:
4846
 *
4847
 * NGTCP2_ERR_NOMEM
4848
 *     Out of memory
4849
 */
4850
static int conn_retire_active_dcid(ngtcp2_conn *conn, const ngtcp2_dcid *dcid,
4851
0
                                   ngtcp2_tstamp ts) {
4852
0
  int rv;
4853
4854
0
  assert(dcid->cid.datalen);
4855
4856
0
  rv = ngtcp2_dcidtr_retire_active_dcid(&conn->dcid.dtr, dcid, ts,
4857
0
                                        dcidtr_on_deactivate, conn);
4858
0
  if (rv != 0) {
4859
0
    return rv;
4860
0
  }
4861
4862
0
  return conn_enqueue_retire_connection_id(conn, dcid->seq);
4863
0
}
4864
4865
/*
4866
 * conn_bind_dcid stores the DCID to |*pdcid| bound to |path|.  If
4867
 * such DCID is not found, bind the new DCID to |path| and stores it
4868
 * to |*pdcid|.  If a remote endpoint uses zero-length connection ID,
4869
 * the pointer to conn->dcid.current is assigned to |*pdcid|.
4870
 *
4871
 * This function returns 0 if it succeeds, or one of the following
4872
 * negative error codes:
4873
 *
4874
 * NGTCP2_ERR_CONN_ID_BLOCKED
4875
 *     No unused DCID is available
4876
 * NGTCP2_ERR_NOMEM
4877
 *     Out of memory
4878
 */
4879
static int conn_bind_dcid(ngtcp2_conn *conn, ngtcp2_dcid **pdcid,
4880
0
                          const ngtcp2_path *path, ngtcp2_tstamp ts) {
4881
0
  assert(!ngtcp2_path_eq(&conn->dcid.current.ps.path, path));
4882
0
  assert(!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path));
4883
0
  assert(!conn->pv || !(conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) ||
4884
0
         !ngtcp2_path_eq(&conn->pv->fallback_dcid.ps.path, path));
4885
4886
0
  *pdcid = ngtcp2_dcidtr_find_bound_dcid(&conn->dcid.dtr, path);
4887
0
  if (*pdcid) {
4888
0
    return 0;
4889
0
  }
4890
4891
0
  if (conn->dcid.current.cid.datalen == 0) {
4892
0
    *pdcid = ngtcp2_dcidtr_bind_zerolen_dcid(&conn->dcid.dtr, path);
4893
4894
0
    return 0;
4895
0
  }
4896
4897
0
  if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
4898
0
    return NGTCP2_ERR_CONN_ID_BLOCKED;
4899
0
  }
4900
4901
0
  return ngtcp2_dcidtr_bind_dcid(&conn->dcid.dtr, pdcid, path, ts,
4902
0
                                 dcidtr_on_retire, conn);
4903
0
}
4904
4905
0
static int conn_start_pmtud(ngtcp2_conn *conn) {
4906
0
  int rv;
4907
0
  size_t hard_max_udp_payload_size;
4908
4909
0
  assert(!conn->local.settings.no_pmtud);
4910
0
  assert(!conn->pmtud);
4911
0
  assert(conn_is_tls_handshake_completed(conn));
4912
0
  assert(conn->remote.transport_params);
4913
0
  assert(conn->remote.transport_params->max_udp_payload_size >=
4914
0
         NGTCP2_MAX_UDP_PAYLOAD_SIZE);
4915
4916
0
  hard_max_udp_payload_size = (size_t)ngtcp2_min_uint64(
4917
0
    conn->remote.transport_params->max_udp_payload_size,
4918
0
    (uint64_t)conn->local.settings.max_tx_udp_payload_size);
4919
4920
0
  rv =
4921
0
    ngtcp2_pmtud_new(&conn->pmtud, conn->dcid.current.max_udp_payload_size,
4922
0
                     hard_max_udp_payload_size, conn->pktns.tx.last_pkt_num + 1,
4923
0
                     conn->local.settings.pmtud_probes,
4924
0
                     conn->local.settings.pmtud_probeslen, conn->mem);
4925
0
  if (rv != 0) {
4926
0
    return rv;
4927
0
  }
4928
4929
0
  if (ngtcp2_pmtud_finished(conn->pmtud)) {
4930
0
    ngtcp2_conn_stop_pmtud(conn);
4931
0
  }
4932
4933
0
  return 0;
4934
0
}
4935
4936
0
int ngtcp2_conn_start_pmtud(ngtcp2_conn *conn) {
4937
0
  return conn_start_pmtud(conn);
4938
0
}
4939
4940
0
void ngtcp2_conn_stop_pmtud(ngtcp2_conn *conn) {
4941
0
  if (!conn->pmtud) {
4942
0
    return;
4943
0
  }
4944
4945
0
  ngtcp2_pmtud_del(conn->pmtud);
4946
4947
0
  conn->pmtud = NULL;
4948
0
}
4949
4950
static ngtcp2_ssize conn_write_pmtud_probe(ngtcp2_conn *conn,
4951
                                           ngtcp2_pkt_info *pi, uint8_t *dest,
4952
0
                                           size_t destlen, ngtcp2_tstamp ts) {
4953
0
  size_t probelen;
4954
0
  ngtcp2_ssize nwrite;
4955
0
  ngtcp2_frame lfr;
4956
4957
0
  assert(conn->pmtud);
4958
0
  assert(!ngtcp2_pmtud_finished(conn->pmtud));
4959
4960
0
  if (!ngtcp2_pmtud_require_probe(conn->pmtud)) {
4961
0
    return 0;
4962
0
  }
4963
4964
0
  probelen = ngtcp2_pmtud_probelen(conn->pmtud);
4965
0
  if (probelen > destlen) {
4966
0
    return 0;
4967
0
  }
4968
4969
0
  ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
4970
0
                   "sending PMTUD probe packet len=%zu", probelen);
4971
4972
0
  lfr.ping.type = NGTCP2_FRAME_PING;
4973
4974
0
  nwrite = ngtcp2_conn_write_single_frame_pkt(
4975
0
    conn, pi, dest, probelen, NGTCP2_PKT_1RTT,
4976
0
    NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING_FULL, &conn->dcid.current.cid, &lfr,
4977
0
    NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING | NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING |
4978
0
      NGTCP2_RTB_ENTRY_FLAG_PMTUD_PROBE,
4979
0
    NULL, ts);
4980
0
  if (nwrite < 0) {
4981
0
    return nwrite;
4982
0
  }
4983
4984
0
  assert(nwrite);
4985
4986
0
  ngtcp2_pmtud_probe_sent(conn->pmtud, conn_compute_pto(conn, &conn->pktns),
4987
0
                          ts);
4988
4989
0
  return nwrite;
4990
0
}
4991
4992
/*
4993
 * conn_stop_pv stops the path validation which is currently running.
4994
 * This function does nothing if no path validation is currently being
4995
 * performed.
4996
 *
4997
 * This function returns 0 if it succeeds, or one of the following
4998
 * negative error codes:
4999
 *
5000
 * NGTCP2_ERR_NOMEM
5001
 *     Out of memory
5002
 */
5003
0
static int conn_stop_pv(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
5004
0
  int rv = 0;
5005
0
  ngtcp2_pv *pv = conn->pv;
5006
5007
0
  if (pv == NULL) {
5008
0
    return 0;
5009
0
  }
5010
5011
0
  if (pv->dcid.cid.datalen && pv->dcid.seq != conn->dcid.current.seq) {
5012
0
    rv = conn_retire_active_dcid(conn, &pv->dcid, ts);
5013
0
    if (rv != 0) {
5014
0
      goto fin;
5015
0
    }
5016
0
  }
5017
5018
0
  if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
5019
0
      pv->fallback_dcid.cid.datalen &&
5020
0
      pv->fallback_dcid.seq != conn->dcid.current.seq &&
5021
0
      pv->fallback_dcid.seq != pv->dcid.seq) {
5022
0
    rv = conn_retire_active_dcid(conn, &pv->fallback_dcid, ts);
5023
0
    if (rv != 0) {
5024
0
      goto fin;
5025
0
    }
5026
0
  }
5027
5028
0
fin:
5029
0
  ngtcp2_pv_del(pv);
5030
0
  conn->pv = NULL;
5031
5032
0
  return rv;
5033
0
}
5034
5035
/*
5036
 * conn_abort_pv aborts the current path validation and frees
5037
 * resources allocated for it.  This function assumes that conn->pv is
5038
 * not NULL.
5039
 *
5040
 * This function returns 0 if it succeeds, or one of the following
5041
 * negative error codes:
5042
 *
5043
 * NGTCP2_ERR_NOMEM
5044
 *     Out of memory
5045
 * NGTCP2_ERR_CALLBACK_FAILURE
5046
 *     User-defined callback function failed.
5047
 */
5048
0
static int conn_abort_pv(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
5049
0
  ngtcp2_pv *pv = conn->pv;
5050
0
  int rv;
5051
5052
0
  assert(pv);
5053
5054
0
  if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
5055
0
    rv = conn_call_path_validation(conn, pv,
5056
0
                                   NGTCP2_PATH_VALIDATION_RESULT_ABORTED);
5057
0
    if (rv != 0) {
5058
0
      return rv;
5059
0
    }
5060
0
  }
5061
5062
0
  return conn_stop_pv(conn, ts);
5063
0
}
5064
5065
static size_t conn_shape_udp_payload(ngtcp2_conn *conn, const ngtcp2_dcid *dcid,
5066
0
                                     size_t payloadlen) {
5067
0
  if (conn->remote.transport_params &&
5068
0
      conn->remote.transport_params->max_udp_payload_size) {
5069
0
    assert(conn->remote.transport_params->max_udp_payload_size >=
5070
0
           NGTCP2_MAX_UDP_PAYLOAD_SIZE);
5071
5072
0
    payloadlen = (size_t)ngtcp2_min_uint64(
5073
0
      (uint64_t)payloadlen,
5074
0
      conn->remote.transport_params->max_udp_payload_size);
5075
0
  }
5076
5077
0
  payloadlen =
5078
0
    ngtcp2_min_size(payloadlen, conn->local.settings.max_tx_udp_payload_size);
5079
5080
0
  if (conn->local.settings.no_tx_udp_payload_size_shaping) {
5081
0
    return payloadlen;
5082
0
  }
5083
5084
0
  return ngtcp2_min_size(payloadlen, dcid->max_udp_payload_size);
5085
0
}
5086
5087
static void conn_reset_congestion_state(ngtcp2_conn *conn, ngtcp2_tstamp ts);
5088
5089
/*
5090
 * conn_on_path_validation_failed is called when path validation
5091
 * fails.  This function may delete |pv|.
5092
 *
5093
 * This function returns 0 if it succeeds, or one of the following
5094
 * negative error codes:
5095
 *
5096
 * NGTCP2_ERR_NOMEM
5097
 *     Out of memory
5098
 * NGTCP2_ERR_CALLBACK_FAILURE
5099
 *     User-defined callback function failed.
5100
 */
5101
static int conn_on_path_validation_failed(ngtcp2_conn *conn, ngtcp2_pv *pv,
5102
0
                                          ngtcp2_tstamp ts) {
5103
0
  int rv;
5104
5105
0
  if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
5106
0
    rv = conn_call_path_validation(conn, pv,
5107
0
                                   NGTCP2_PATH_VALIDATION_RESULT_FAILURE);
5108
0
    if (rv != 0) {
5109
0
      return rv;
5110
0
    }
5111
0
  }
5112
5113
0
  if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
5114
0
    ngtcp2_dcid_copy(&conn->dcid.current, &pv->fallback_dcid);
5115
0
    conn_reset_congestion_state(conn, ts);
5116
0
  }
5117
5118
0
  return conn_stop_pv(conn, ts);
5119
0
}
5120
5121
/*
5122
 * conn_write_path_challenge writes a packet which includes
5123
 * PATH_CHALLENGE frame into |dest| of length |destlen|.
5124
 *
5125
 * This function returns the number of bytes written to |dest|, or one
5126
 * of the following negative error codes:
5127
 *
5128
 * NGTCP2_ERR_NOMEM
5129
 *     Out of memory
5130
 * NGTCP2_ERR_CALLBACK_FAILURE
5131
 *     User-defined callback function failed.
5132
 */
5133
static ngtcp2_ssize conn_write_path_challenge(ngtcp2_conn *conn,
5134
                                              ngtcp2_path *path,
5135
                                              ngtcp2_pkt_info *pi,
5136
                                              uint8_t *dest, size_t destlen,
5137
0
                                              ngtcp2_tstamp ts) {
5138
0
  ngtcp2_ssize nwrite;
5139
0
  ngtcp2_tstamp expiry;
5140
0
  ngtcp2_pv *pv = conn->pv;
5141
0
  ngtcp2_frame lfr;
5142
0
  ngtcp2_duration timeout, initial_pto;
5143
0
  uint8_t flags;
5144
0
  uint64_t tx_left;
5145
0
  int rv;
5146
5147
0
  if (ngtcp2_pv_validation_timed_out(pv, ts)) {
5148
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
5149
0
                    "path validation was timed out");
5150
0
    rv = conn_on_path_validation_failed(conn, pv, ts);
5151
0
    if (rv != 0) {
5152
0
      return rv;
5153
0
    }
5154
5155
    /* We might set path to the one which we just failed validate.
5156
       Set it to the current path here. */
5157
0
    if (path) {
5158
0
      ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
5159
0
    }
5160
5161
0
    return 0;
5162
0
  }
5163
5164
0
  ngtcp2_pv_handle_entry_expiry(pv, ts);
5165
5166
0
  if (!ngtcp2_pv_should_send_probe(pv)) {
5167
0
    return 0;
5168
0
  }
5169
5170
0
  rv = conn_call_get_path_challenge_data(conn, &lfr.path_challenge.data);
5171
0
  if (rv != 0) {
5172
0
    return rv;
5173
0
  }
5174
5175
0
  lfr.path_challenge.type = NGTCP2_FRAME_PATH_CHALLENGE;
5176
5177
0
  initial_pto = conn_compute_initial_pto(conn, &conn->pktns);
5178
0
  timeout = conn_compute_pto(conn, &conn->pktns);
5179
0
  timeout = ngtcp2_max_uint64(timeout, initial_pto);
5180
0
  expiry = ts + timeout * (1ULL << pv->round);
5181
5182
0
  destlen = ngtcp2_min_size(destlen, NGTCP2_MAX_UDP_PAYLOAD_SIZE);
5183
5184
0
  if (conn->server) {
5185
0
    if (!(pv->dcid.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
5186
0
      tx_left = conn_server_tx_left(conn, &pv->dcid);
5187
0
      destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, tx_left);
5188
0
      if (destlen == 0) {
5189
0
        return 0;
5190
0
      }
5191
0
    }
5192
5193
0
    if (destlen < NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
5194
0
      flags = NGTCP2_PV_ENTRY_FLAG_UNDERSIZED;
5195
0
    } else {
5196
0
      flags = NGTCP2_PV_ENTRY_FLAG_NONE;
5197
0
    }
5198
0
  } else {
5199
0
    flags = NGTCP2_PV_ENTRY_FLAG_NONE;
5200
0
  }
5201
5202
0
  ngtcp2_pv_add_entry(pv, &lfr.path_challenge.data, expiry, flags, ts);
5203
5204
0
  nwrite = ngtcp2_conn_write_single_frame_pkt(
5205
0
    conn, pi, dest, destlen, NGTCP2_PKT_1RTT, NGTCP2_WRITE_PKT_FLAG_NONE,
5206
0
    &pv->dcid.cid, &lfr,
5207
0
    NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING | NGTCP2_RTB_ENTRY_FLAG_PTO_ELICITING,
5208
0
    &pv->dcid.ps.path, ts);
5209
0
  if (nwrite <= 0) {
5210
0
    return nwrite;
5211
0
  }
5212
5213
0
  if (path) {
5214
0
    ngtcp2_path_copy(path, &pv->dcid.ps.path);
5215
0
  }
5216
5217
0
  if (ngtcp2_path_eq(&pv->dcid.ps.path, &conn->dcid.current.ps.path)) {
5218
0
    conn->dcid.current.bytes_sent += (uint64_t)nwrite;
5219
0
  } else {
5220
0
    pv->dcid.bytes_sent += (uint64_t)nwrite;
5221
0
  }
5222
5223
0
  return nwrite;
5224
0
}
5225
5226
/*
5227
 * conn_write_path_response writes a packet which includes
5228
 * PATH_RESPONSE frame into |dest| of length |destlen|.
5229
 *
5230
 * This function returns the number of bytes written to |dest|, or one
5231
 * of the following negative error codes:
5232
 *
5233
 * NGTCP2_ERR_NOMEM
5234
 *     Out of memory
5235
 * NGTCP2_ERR_CALLBACK_FAILURE
5236
 *     User-defined callback function failed.
5237
 */
5238
static ngtcp2_ssize conn_write_path_response(ngtcp2_conn *conn,
5239
                                             ngtcp2_path *path,
5240
                                             ngtcp2_pkt_info *pi, uint8_t *dest,
5241
0
                                             size_t destlen, ngtcp2_tstamp ts) {
5242
0
  ngtcp2_pv *pv = conn->pv;
5243
0
  ngtcp2_path_challenge_entry *pcent = NULL;
5244
0
  ngtcp2_dcid *dcid = NULL;
5245
0
  ngtcp2_frame lfr;
5246
0
  ngtcp2_ssize nwrite;
5247
0
  int rv;
5248
0
  uint64_t tx_left;
5249
5250
0
  for (; ngtcp2_ringbuf_len(&conn->rx.path_challenge.rb);) {
5251
0
    pcent = ngtcp2_ringbuf_get(&conn->rx.path_challenge.rb, 0);
5252
5253
0
    if (ngtcp2_path_eq(&conn->dcid.current.ps.path, &pcent->ps.path)) {
5254
      /* Send PATH_RESPONSE from conn_write_pkt. */
5255
0
      return 0;
5256
0
    }
5257
5258
0
    if (pv) {
5259
0
      if (ngtcp2_path_eq(&pv->dcid.ps.path, &pcent->ps.path)) {
5260
0
        dcid = &pv->dcid;
5261
0
        break;
5262
0
      }
5263
0
      if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
5264
0
          ngtcp2_path_eq(&pv->fallback_dcid.ps.path, &pcent->ps.path)) {
5265
0
        dcid = &pv->fallback_dcid;
5266
0
        break;
5267
0
      }
5268
0
    }
5269
5270
0
    if (conn->server) {
5271
0
      break;
5272
0
    }
5273
5274
    /* Client does not expect to respond to path validation against
5275
       unknown path */
5276
0
    ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge.rb);
5277
0
    pcent = NULL;
5278
0
  }
5279
5280
0
  if (pcent == NULL) {
5281
0
    return 0;
5282
0
  }
5283
5284
0
  if (dcid == NULL) {
5285
    /* client is expected to have |path| in conn->dcid.current or
5286
       conn->pv. */
5287
0
    assert(conn->server);
5288
5289
0
    rv = conn_bind_dcid(conn, &dcid, &pcent->ps.path, ts);
5290
0
    if (rv != 0) {
5291
0
      if (ngtcp2_err_is_fatal(rv)) {
5292
0
        return rv;
5293
0
      }
5294
0
      return 0;
5295
0
    }
5296
0
  }
5297
5298
0
  destlen = ngtcp2_min_size(destlen, NGTCP2_MAX_UDP_PAYLOAD_SIZE);
5299
5300
0
  if (conn->server && !(dcid->flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
5301
0
    tx_left = conn_server_tx_left(conn, dcid);
5302
0
    destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, tx_left);
5303
0
    if (destlen == 0) {
5304
0
      return 0;
5305
0
    }
5306
0
  }
5307
5308
0
  lfr.path_response = (ngtcp2_path_response){
5309
0
    .type = NGTCP2_FRAME_PATH_RESPONSE,
5310
0
    .data = pcent->data,
5311
0
  };
5312
5313
0
  nwrite = ngtcp2_conn_write_single_frame_pkt(
5314
0
    conn, pi, dest, destlen, NGTCP2_PKT_1RTT, NGTCP2_WRITE_PKT_FLAG_NONE,
5315
0
    &dcid->cid, &lfr, NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING, &pcent->ps.path, ts);
5316
0
  if (nwrite <= 0) {
5317
0
    return nwrite;
5318
0
  }
5319
5320
0
  if (path) {
5321
0
    ngtcp2_path_copy(path, &pcent->ps.path);
5322
0
  }
5323
5324
0
  ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge.rb);
5325
5326
0
  dcid->bytes_sent += (uint64_t)nwrite;
5327
5328
0
  return nwrite;
5329
0
}
5330
5331
ngtcp2_ssize ngtcp2_conn_write_pkt_versioned(ngtcp2_conn *conn,
5332
                                             ngtcp2_path *path,
5333
                                             int pkt_info_version,
5334
                                             ngtcp2_pkt_info *pi, uint8_t *dest,
5335
0
                                             size_t destlen, ngtcp2_tstamp ts) {
5336
0
  return ngtcp2_conn_writev_stream_versioned(
5337
0
    conn, path, pkt_info_version, pi, dest, destlen,
5338
0
    /* pdatalen = */ NULL, NGTCP2_WRITE_STREAM_FLAG_NONE,
5339
0
    /* stream_id = */ -1,
5340
0
    /* datav = */ NULL, /* datavcnt = */ 0, ts);
5341
0
}
5342
5343
/*
5344
 * conn_on_version_negotiation is called when Version Negotiation
5345
 * packet is received.  The function decodes the data in the buffer
5346
 * pointed by |payload| whose length is |payloadlen| as Version
5347
 * Negotiation packet payload.  The packet header is given in |hd|.
5348
 *
5349
 * This function returns 0 if it succeeds, or one of the following
5350
 * negative error codes:
5351
 *
5352
 * NGTCP2_ERR_NOMEM
5353
 *     Out of memory.
5354
 * NGTCP2_ERR_CALLBACK_FAILURE
5355
 *     User-defined callback function failed.
5356
 * NGTCP2_ERR_INVALID_ARGUMENT
5357
 *     Packet payload is badly formatted.
5358
 */
5359
static int conn_on_version_negotiation(ngtcp2_conn *conn,
5360
                                       const ngtcp2_pkt_hd *hd,
5361
                                       const uint8_t *payload,
5362
0
                                       size_t payloadlen) {
5363
0
  uint32_t sv[16];
5364
0
  uint32_t *p;
5365
0
  int rv = 0;
5366
0
  size_t nsv;
5367
0
  size_t i;
5368
5369
0
  if (payloadlen % sizeof(uint32_t)) {
5370
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
5371
0
  }
5372
5373
  /* Version Negotiation packet is ignored if client has reacted upon
5374
     Version Negotiation packet. */
5375
0
  if (conn->local.settings.original_version != conn->client_chosen_version) {
5376
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
5377
0
  }
5378
5379
0
  if (payloadlen > sizeof(sv)) {
5380
0
    p = ngtcp2_mem_malloc(conn->mem, payloadlen);
5381
0
    if (p == NULL) {
5382
0
      return NGTCP2_ERR_NOMEM;
5383
0
    }
5384
0
  } else {
5385
0
    p = sv;
5386
0
  }
5387
5388
0
  nsv = ngtcp2_pkt_decode_version_negotiation(p, payload, payloadlen);
5389
5390
0
  ngtcp2_log_rx_vn(&conn->log, hd, p, nsv);
5391
5392
0
  ngtcp2_qlog_version_negotiation_pkt_received(&conn->qlog, hd, p, nsv);
5393
5394
0
  if (!ngtcp2_is_reserved_version(conn->local.settings.original_version)) {
5395
0
    for (i = 0; i < nsv; ++i) {
5396
0
      if (p[i] == conn->local.settings.original_version) {
5397
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5398
0
                        "ignore Version Negotiation because it contains the "
5399
0
                        "original version");
5400
5401
0
        rv = NGTCP2_ERR_INVALID_ARGUMENT;
5402
0
        goto fin;
5403
0
      }
5404
0
    }
5405
0
  }
5406
5407
0
  rv = conn_call_recv_version_negotiation(conn, hd, p, nsv);
5408
0
  if (rv != 0) {
5409
0
    goto fin;
5410
0
  }
5411
5412
0
fin:
5413
0
  if (p != sv) {
5414
0
    ngtcp2_mem_free(conn->mem, p);
5415
0
  }
5416
5417
0
  return rv;
5418
0
}
5419
5420
0
static uint64_t conn_tx_strmq_first_cycle(ngtcp2_conn *conn) {
5421
0
  ngtcp2_strm *strm;
5422
5423
0
  if (ngtcp2_pq_empty(&conn->tx.strmq)) {
5424
0
    return 0;
5425
0
  }
5426
5427
0
  strm = ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
5428
0
  return strm->cycle;
5429
0
}
5430
5431
0
uint64_t ngtcp2_conn_tx_strmq_first_cycle(ngtcp2_conn *conn) {
5432
0
  ngtcp2_strm *strm;
5433
5434
0
  if (ngtcp2_pq_empty(&conn->tx.strmq)) {
5435
0
    return 0;
5436
0
  }
5437
5438
0
  strm = ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
5439
0
  return strm->cycle;
5440
0
}
5441
5442
/*
5443
 * conn_on_retry is called when Retry packet is received.  The
5444
 * function decodes the data in the buffer pointed by |pkt| whose
5445
 * length is |pktlen| as Retry packet.  The length of long packet
5446
 * header is given in |hdpktlen|.  |pkt| includes packet header.
5447
 *
5448
 * This function returns 0 if it succeeds, or one of the following
5449
 * negative error codes:
5450
 *
5451
 * NGTCP2_ERR_NOMEM
5452
 *     Out of memory.
5453
 * NGTCP2_ERR_CALLBACK_FAILURE
5454
 *     User-defined callback function failed.
5455
 * NGTCP2_ERR_INVALID_ARGUMENT
5456
 *     Packet payload is badly formatted.
5457
 * NGTCP2_ERR_PROTO
5458
 *     ODCID does not match; or Token is empty.
5459
 */
5460
static int conn_on_retry(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd,
5461
                         size_t hdpktlen, const uint8_t *pkt, size_t pktlen,
5462
0
                         ngtcp2_tstamp ts) {
5463
0
  int rv;
5464
0
  ngtcp2_pkt_retry retry;
5465
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
5466
0
  ngtcp2_rtb *rtb = &conn->pktns.rtb;
5467
0
  ngtcp2_rtb *in_rtb;
5468
0
  char cidbuf[sizeof(retry.odcid.data) * 2 + 1];
5469
0
  uint8_t *token;
5470
5471
0
  if (!in_pktns || (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY)) {
5472
0
    return NGTCP2_ERR_DISCARD_PKT;
5473
0
  }
5474
5475
0
  in_rtb = &in_pktns->rtb;
5476
5477
0
  rv = ngtcp2_pkt_decode_retry(&retry, pkt + hdpktlen, pktlen - hdpktlen);
5478
0
  if (rv != 0) {
5479
0
    return rv;
5480
0
  }
5481
5482
0
  retry.odcid = conn->dcid.current.cid;
5483
5484
0
  rv = ngtcp2_pkt_verify_retry_tag(
5485
0
    conn->client_chosen_version, &retry, pkt, pktlen, conn->callbacks.encrypt,
5486
0
    &conn->crypto.retry_aead, &conn->crypto.retry_aead_ctx);
5487
0
  if (rv != 0) {
5488
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5489
0
                    "unable to verify Retry packet integrity");
5490
0
    return rv;
5491
0
  }
5492
5493
0
  ngtcp2_log_infof(
5494
0
    &conn->log, NGTCP2_LOG_EVENT_PKT, "odcid=0x%s",
5495
0
    ngtcp2_encode_hex_cstr(cidbuf, retry.odcid.data, retry.odcid.datalen));
5496
5497
0
  if (retry.tokenlen == 0) {
5498
0
    return NGTCP2_ERR_PROTO;
5499
0
  }
5500
5501
0
  if (ngtcp2_cid_eq(&conn->dcid.current.cid, &hd->scid)) {
5502
0
    return 0;
5503
0
  }
5504
5505
0
  ngtcp2_qlog_retry_pkt_received(&conn->qlog, hd, &retry);
5506
5507
  /* DCID must be updated before invoking callback because client
5508
     generates new initial keys there. */
5509
0
  conn->dcid.current.cid = hd->scid;
5510
0
  conn->retry_scid = hd->scid;
5511
5512
0
  conn->flags |= NGTCP2_CONN_FLAG_RECV_RETRY;
5513
5514
0
  rv = conn_call_recv_retry(conn, hd);
5515
0
  if (rv != 0) {
5516
0
    return rv;
5517
0
  }
5518
5519
0
  conn->state = NGTCP2_CS_CLIENT_INITIAL;
5520
5521
  /* Just freeing memory is dangerous because we might free twice. */
5522
5523
0
  rv = ngtcp2_rtb_reclaim_on_retry(rtb, conn, &conn->pktns, &conn->cstat);
5524
0
  if (rv != 0) {
5525
0
    return rv;
5526
0
  }
5527
5528
0
  rv = ngtcp2_rtb_reclaim_on_retry(in_rtb, conn, in_pktns, &conn->cstat);
5529
0
  if (rv != 0) {
5530
0
    return rv;
5531
0
  }
5532
5533
0
  ngtcp2_mem_free(conn->mem, (uint8_t *)conn->local.settings.token);
5534
0
  conn->local.settings.token = NULL;
5535
0
  conn->local.settings.tokenlen = 0;
5536
5537
0
  token = ngtcp2_mem_malloc(conn->mem, retry.tokenlen);
5538
0
  if (token == NULL) {
5539
0
    return NGTCP2_ERR_NOMEM;
5540
0
  }
5541
5542
0
  ngtcp2_cpymem(token, retry.token, retry.tokenlen);
5543
5544
0
  conn->local.settings.token = token;
5545
0
  conn->local.settings.tokenlen = retry.tokenlen;
5546
5547
0
  reset_conn_stat_recovery(&conn->cstat);
5548
0
  conn_reset_congestion_state(conn, ts);
5549
0
  conn_reset_ecn_validation_state(conn);
5550
5551
0
  return 0;
5552
0
}
5553
5554
int ngtcp2_conn_detect_lost_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
5555
0
                                ngtcp2_conn_stat *cstat, ngtcp2_tstamp ts) {
5556
0
  return ngtcp2_rtb_detect_lost_pkt(&pktns->rtb, conn, pktns, cstat, ts);
5557
0
}
5558
5559
/*
5560
 * conn_recv_ack processes received ACK frame |fr|.  |pkt_ts| is the
5561
 * timestamp when packet is received.  |ts| should be the current
5562
 * time.  Usually they are the same, but for buffered packets,
5563
 * |pkt_ts| would be earlier than |ts|.  This function needs to be
5564
 * called after |fr| is validated by ngtcp2_pkt_validate_ack.
5565
 *
5566
 * This function returns 0 if it succeeds, or one of the following
5567
 * negative error codes:
5568
 *
5569
 * NGTCP2_ERR_NOMEM
5570
 *     Out of memory
5571
 * NGTCP2_ERR_PROTO
5572
 *     |fr| acknowledges a packet this endpoint has not sent.
5573
 * NGTCP2_ERR_CALLBACK_FAILURE
5574
 *     User callback failed.
5575
 */
5576
static int conn_recv_ack(ngtcp2_conn *conn, ngtcp2_pktns *pktns, ngtcp2_ack *fr,
5577
0
                         ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
5578
0
  ngtcp2_ssize num_acked;
5579
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
5580
5581
0
  if (pktns->tx.last_pkt_num < fr->largest_ack) {
5582
0
    return NGTCP2_ERR_PROTO;
5583
0
  }
5584
5585
0
  ngtcp2_acktr_recv_ack(&pktns->acktr, fr);
5586
5587
0
  num_acked =
5588
0
    ngtcp2_rtb_recv_ack(&pktns->rtb, fr, &conn->cstat, conn, pktns, pkt_ts, ts);
5589
0
  if (num_acked <= 0) {
5590
0
    return (int)num_acked;
5591
0
  }
5592
5593
0
  pktns->rtb.probe_pkt_left = 0;
5594
5595
0
  if (cstat->pto_count &&
5596
0
      (conn->server || (conn->flags & NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED))) {
5597
    /* Reset PTO count but no less than 2 to avoid frequent probe
5598
       packet transmission. */
5599
0
    cstat->pto_count = ngtcp2_min_size(cstat->pto_count, 2);
5600
0
  }
5601
5602
0
  ngtcp2_conn_set_loss_detection_timer(conn, ts);
5603
5604
0
  return 0;
5605
0
}
5606
5607
/*
5608
 * conn_assign_recved_ack_delay_unscaled assigns
5609
 * fr->ack_delay_unscaled.
5610
 */
5611
static void assign_recved_ack_delay_unscaled(ngtcp2_ack *fr,
5612
0
                                             uint64_t ack_delay_exponent) {
5613
0
  const ngtcp2_tstamp max_ack_delay = ((1 << 14) - 1) * NGTCP2_MILLISECONDS;
5614
0
  uint64_t exp = (1ULL << ack_delay_exponent) * NGTCP2_MICROSECONDS;
5615
5616
0
  if (fr->ack_delay > max_ack_delay / exp) {
5617
0
    fr->ack_delay_unscaled = max_ack_delay;
5618
0
    return;
5619
0
  }
5620
5621
0
  fr->ack_delay_unscaled = fr->ack_delay * exp;
5622
0
}
5623
5624
/*
5625
 * conn_recv_max_stream_data processes received MAX_STREAM_DATA frame
5626
 * |fr|.
5627
 *
5628
 * This function returns 0 if it succeeds, or one of the following
5629
 * negative error codes:
5630
 *
5631
 * NGTCP2_ERR_STREAM_STATE
5632
 *     Stream ID indicates that it is a local stream, and the local
5633
 *     endpoint has not initiated it; or stream is peer initiated
5634
 *     unidirectional stream.
5635
 * NGTCP2_ERR_STREAM_LIMIT
5636
 *     Stream ID exceeds allowed limit.
5637
 * NGTCP2_ERR_NOMEM
5638
 *     Out of memory.
5639
 * NGTCP2_ERR_INTERNAL
5640
 *     Suspicious remote endpoint activity exceeded threshold.
5641
 */
5642
static int conn_recv_max_stream_data(ngtcp2_conn *conn,
5643
                                     const ngtcp2_max_stream_data *fr,
5644
0
                                     ngtcp2_tstamp ts) {
5645
0
  ngtcp2_strm *strm;
5646
0
  ngtcp2_idtr *idtr;
5647
0
  int local_stream = conn_local_stream(conn, fr->stream_id);
5648
0
  int bidi = bidi_stream(fr->stream_id);
5649
0
  int rv;
5650
5651
0
  if (bidi) {
5652
0
    if (local_stream) {
5653
0
      if (conn->local.bidi.next_stream_id <= fr->stream_id) {
5654
0
        return NGTCP2_ERR_STREAM_STATE;
5655
0
      }
5656
0
    } else if (conn->remote.bidi.max_streams <
5657
0
               ngtcp2_ord_stream_id(fr->stream_id)) {
5658
0
      return NGTCP2_ERR_STREAM_LIMIT;
5659
0
    }
5660
5661
0
    idtr = &conn->remote.bidi.idtr;
5662
0
  } else {
5663
0
    if (!local_stream || conn->local.uni.next_stream_id <= fr->stream_id) {
5664
0
      return NGTCP2_ERR_STREAM_STATE;
5665
0
    }
5666
5667
0
    idtr = &conn->remote.uni.idtr;
5668
0
  }
5669
5670
0
  strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
5671
0
  if (strm == NULL) {
5672
0
    if (local_stream) {
5673
      /* Stream has been closed. */
5674
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
5675
0
        return NGTCP2_ERR_INTERNAL;
5676
0
      }
5677
5678
0
      return 0;
5679
0
    }
5680
5681
0
    rv = ngtcp2_idtr_open(idtr, fr->stream_id);
5682
0
    if (rv != 0) {
5683
0
      if (ngtcp2_err_is_fatal(rv)) {
5684
0
        return rv;
5685
0
      }
5686
0
      assert(rv == NGTCP2_ERR_STREAM_IN_USE);
5687
      /* Stream has been closed. */
5688
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
5689
0
        return NGTCP2_ERR_INTERNAL;
5690
0
      }
5691
5692
0
      return 0;
5693
0
    }
5694
5695
0
    strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
5696
0
    if (strm == NULL) {
5697
0
      return NGTCP2_ERR_NOMEM;
5698
0
    }
5699
0
    rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
5700
0
    if (rv != 0) {
5701
0
      ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
5702
0
      return rv;
5703
0
    }
5704
5705
0
    rv = conn_call_stream_open(conn, strm);
5706
0
    if (rv != 0) {
5707
0
      return rv;
5708
0
    }
5709
0
  }
5710
5711
0
  if (strm->tx.max_offset >= fr->max_stream_data) {
5712
0
    if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
5713
0
      return NGTCP2_ERR_INTERNAL;
5714
0
    }
5715
5716
0
    return 0;
5717
0
  }
5718
5719
0
  strm->tx.max_offset = fr->max_stream_data;
5720
5721
  /* Don't call callback if stream is half-closed local */
5722
0
  if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
5723
0
    if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
5724
0
      return NGTCP2_ERR_INTERNAL;
5725
0
    }
5726
5727
0
    return 0;
5728
0
  }
5729
5730
0
  rv = conn_call_extend_max_stream_data(conn, strm, fr->stream_id,
5731
0
                                        fr->max_stream_data);
5732
0
  if (rv != 0) {
5733
0
    return rv;
5734
0
  }
5735
5736
0
  return 0;
5737
0
}
5738
5739
/*
5740
 * conn_recv_max_data processes received MAX_DATA frame |fr|.
5741
 */
5742
0
static void conn_recv_max_data(ngtcp2_conn *conn, const ngtcp2_max_data *fr) {
5743
0
  conn->tx.max_offset = ngtcp2_max_uint64(conn->tx.max_offset, fr->max_data);
5744
0
}
5745
5746
/*
5747
 * should_buffer_1rtt_pkt returns nonzero if 1RTT packet |pkt| of
5748
 * length |pktlen| should be buffered.
5749
 */
5750
0
static int should_buffer_1rtt_pkt(const uint8_t *pkt, size_t pktlen) {
5751
  /* A packet starting with 21 bytes zeros are most likely padding
5752
     bytes. */
5753
0
  return pktlen >= NGTCP2_MIN_QUIC_PKTLEN &&
5754
0
         (pkt[0] != 0 || memcmp(pkt, pkt + 1, NGTCP2_MIN_QUIC_PKTLEN - 1) != 0);
5755
0
}
5756
5757
/*
5758
 * conn_buffer_pkt buffers |pkt| of length |pktlen|, chaining it from
5759
 * |*ppc|.
5760
 *
5761
 * This function returns 0 if it succeeds, or one of the following
5762
 * negative error codes:
5763
 *
5764
 * NGTCP2_ERR_NOMEM
5765
 *     Out of memory.
5766
 */
5767
static int conn_buffer_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
5768
                           const ngtcp2_path *path, const ngtcp2_pkt_info *pi,
5769
                           const uint8_t *pkt, size_t pktlen, size_t dgramlen,
5770
0
                           ngtcp2_tstamp ts) {
5771
0
  int rv;
5772
0
  ngtcp2_pkt_chain **ppc = &pktns->rx.buffed_pkts, *pc;
5773
0
  size_t i;
5774
0
  for (i = 0; *ppc && i < NGTCP2_MAX_NUM_BUFFED_RX_PKTS;
5775
0
       ppc = &(*ppc)->next, ++i)
5776
0
    ;
5777
5778
0
  if (i == NGTCP2_MAX_NUM_BUFFED_RX_PKTS) {
5779
0
    return 0;
5780
0
  }
5781
5782
0
  rv =
5783
0
    ngtcp2_pkt_chain_new(&pc, path, pi, pkt, pktlen, dgramlen, ts, conn->mem);
5784
0
  if (rv != 0) {
5785
0
    return rv;
5786
0
  }
5787
5788
0
  *ppc = pc;
5789
5790
0
  return 0;
5791
0
}
5792
5793
static int ensure_decrypt_buffer(ngtcp2_vec *vec, size_t n, size_t initial,
5794
0
                                 const ngtcp2_mem *mem) {
5795
0
  uint8_t *nbuf;
5796
0
  size_t len;
5797
5798
0
  if (vec->len >= n) {
5799
0
    return 0;
5800
0
  }
5801
5802
0
  len = vec->len == 0 ? initial : vec->len * 2;
5803
0
  for (; len < n; len *= 2)
5804
0
    ;
5805
0
  nbuf = ngtcp2_mem_realloc(mem, vec->base, len);
5806
0
  if (nbuf == NULL) {
5807
0
    return NGTCP2_ERR_NOMEM;
5808
0
  }
5809
0
  vec->base = nbuf;
5810
0
  vec->len = len;
5811
5812
0
  return 0;
5813
0
}
5814
5815
/*
5816
 * conn_ensure_decrypt_hp_buffer ensures that
5817
 * conn->crypto.decrypt_hp_buf has at least |n| bytes space.
5818
 *
5819
 * This function returns 0 if it succeeds, or one of the following
5820
 * negative error codes:
5821
 *
5822
 * NGTCP2_ERR_NOMEM
5823
 *     Out of memory.
5824
 */
5825
0
static int conn_ensure_decrypt_hp_buffer(ngtcp2_conn *conn, size_t n) {
5826
0
  return ensure_decrypt_buffer(&conn->crypto.decrypt_hp_buf, n, 256, conn->mem);
5827
0
}
5828
5829
/*
5830
 * conn_ensure_decrypt_buffer ensures that conn->crypto.decrypt_buf
5831
 * has at least |n| bytes space.
5832
 *
5833
 * This function returns 0 if it succeeds, or one of the following
5834
 * negative error codes:
5835
 *
5836
 * NGTCP2_ERR_NOMEM
5837
 *     Out of memory.
5838
 */
5839
0
static int conn_ensure_decrypt_buffer(ngtcp2_conn *conn, size_t n) {
5840
0
  return ensure_decrypt_buffer(&conn->crypto.decrypt_buf, n, 2048, conn->mem);
5841
0
}
5842
5843
/*
5844
 * decrypt_pkt decrypts the data pointed by |payload| whose length is
5845
 * |payloadlen|, and writes plaintext data to the buffer pointed by
5846
 * |dest|.  The buffer pointed by |aad| is the Additional
5847
 * Authenticated Data, and its length is |aadlen|.  |pkt_num| is used
5848
 * to create a nonce.  |ckm| is the cryptographic key, and iv to use.
5849
 * |decrypt| is a callback function which actually decrypts a packet.
5850
 *
5851
 * This function returns the number of bytes written in |dest| if it
5852
 * succeeds, or one of the following negative error codes:
5853
 *
5854
 * NGTCP2_ERR_CALLBACK_FAILURE
5855
 *     User callback failed.
5856
 * NGTCP2_ERR_DECRYPT
5857
 *     Failed to decrypt a packet.
5858
 */
5859
static ngtcp2_ssize decrypt_pkt(uint8_t *dest, const ngtcp2_crypto_aead *aead,
5860
                                const uint8_t *payload, size_t payloadlen,
5861
                                const uint8_t *aad, size_t aadlen,
5862
                                int64_t pkt_num, ngtcp2_crypto_km *ckm,
5863
0
                                ngtcp2_decrypt decrypt) {
5864
  /* TODO nonce is limited to 64 bytes. */
5865
0
  uint8_t nonce[64];
5866
0
  int rv;
5867
5868
0
  assert(sizeof(nonce) >= ckm->iv.len);
5869
5870
0
  ngtcp2_crypto_create_nonce(nonce, ckm->iv.base, ckm->iv.len, pkt_num);
5871
5872
0
  rv = decrypt(dest, aead, &ckm->aead_ctx, payload, payloadlen, nonce,
5873
0
               ckm->iv.len, aad, aadlen);
5874
5875
0
  if (rv != 0) {
5876
0
    if (rv == NGTCP2_ERR_DECRYPT) {
5877
0
      return rv;
5878
0
    }
5879
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
5880
0
  }
5881
5882
0
  assert(payloadlen >= aead->max_overhead);
5883
5884
0
  return (ngtcp2_ssize)(payloadlen - aead->max_overhead);
5885
0
}
5886
5887
/*
5888
 * decrypt_hp decryptes packet header.  The packet number starts at
5889
 * |pkt| + |pkt_num_offset|.  The entire plaintext QUIC packet header
5890
 * will be written to the buffer pointed by |dest| whose capacity is
5891
 * |destlen|.
5892
 *
5893
 * This function returns the number of bytes written to |dest|, or one
5894
 * of the following negative error codes:
5895
 *
5896
 * NGTCP2_ERR_PROTO
5897
 *     Packet is badly formatted
5898
 * NGTCP2_ERR_CALLBACK_FAILURE
5899
 *     User-defined callback function failed; or it does not return
5900
 *     expected result.
5901
 */
5902
static ngtcp2_ssize
5903
decrypt_hp(ngtcp2_pkt_hd *hd, uint8_t *dest, const ngtcp2_crypto_cipher *hp,
5904
           const uint8_t *pkt, size_t pktlen, size_t pkt_num_offset,
5905
0
           const ngtcp2_crypto_cipher_ctx *hp_ctx, ngtcp2_hp_mask hp_mask) {
5906
0
  size_t sample_offset;
5907
0
  uint8_t *p = dest;
5908
0
  uint8_t mask[NGTCP2_HP_SAMPLELEN];
5909
0
  size_t i;
5910
0
  int rv;
5911
5912
0
  assert(hp_mask);
5913
5914
0
  if (pkt_num_offset + 4 + NGTCP2_HP_SAMPLELEN > pktlen) {
5915
0
    return NGTCP2_ERR_PROTO;
5916
0
  }
5917
5918
0
  p = ngtcp2_cpymem(p, pkt, pkt_num_offset);
5919
5920
0
  sample_offset = pkt_num_offset + 4;
5921
5922
0
  rv = hp_mask(mask, hp, hp_ctx, pkt + sample_offset);
5923
0
  if (rv != 0) {
5924
0
    return NGTCP2_ERR_CALLBACK_FAILURE;
5925
0
  }
5926
5927
0
  if (hd->flags & NGTCP2_PKT_FLAG_LONG_FORM) {
5928
0
    dest[0] = (uint8_t)(dest[0] ^ (mask[0] & 0x0F));
5929
0
  } else {
5930
0
    dest[0] = (uint8_t)(dest[0] ^ (mask[0] & 0x1F));
5931
0
    if (dest[0] & NGTCP2_SHORT_KEY_PHASE_BIT) {
5932
0
      hd->flags |= NGTCP2_PKT_FLAG_KEY_PHASE;
5933
0
    }
5934
0
  }
5935
5936
0
  hd->pkt_numlen = (size_t)((dest[0] & NGTCP2_PKT_NUMLEN_MASK) + 1);
5937
5938
0
  for (i = 0; i < 4; ++i) {
5939
0
    *p++ = *(pkt + pkt_num_offset + i) ^ mask[i + 1];
5940
0
  }
5941
5942
0
  p -= 4;
5943
0
  hd->pkt_num = ngtcp2_get_pkt_num(p, hd->pkt_numlen);
5944
0
  p += hd->pkt_numlen;
5945
5946
0
  return p - dest;
5947
0
}
5948
5949
/*
5950
 * conn_emit_pending_crypto_data delivers pending stream data to the
5951
 * application due to packet reordering.
5952
 *
5953
 * This function returns 0 if it succeeds, or one of the following
5954
 * negative error codes:
5955
 *
5956
 * NGTCP2_ERR_CALLBACK_FAILURE
5957
 *     User callback failed
5958
 * NGTCP2_ERR_CRYPTO
5959
 *     TLS backend reported error
5960
 */
5961
static int
5962
conn_emit_pending_crypto_data(ngtcp2_conn *conn,
5963
                              ngtcp2_encryption_level encryption_level,
5964
0
                              ngtcp2_strm *strm, uint64_t rx_offset) {
5965
0
  size_t datalen;
5966
0
  const uint8_t *data;
5967
0
  int rv;
5968
0
  uint64_t offset;
5969
5970
0
  if (!strm->rx.rob) {
5971
0
    return 0;
5972
0
  }
5973
5974
0
  for (;;) {
5975
0
    datalen = ngtcp2_rob_data_at(strm->rx.rob, &data, rx_offset);
5976
0
    if (datalen == 0) {
5977
0
      assert(rx_offset == ngtcp2_strm_rx_offset(strm));
5978
0
      return 0;
5979
0
    }
5980
5981
0
    offset = rx_offset;
5982
0
    rx_offset += datalen;
5983
5984
0
    rv =
5985
0
      conn_call_recv_crypto_data(conn, encryption_level, offset, data, datalen);
5986
0
    if (rv != 0) {
5987
0
      return rv;
5988
0
    }
5989
5990
0
    ngtcp2_rob_pop(strm->rx.rob, rx_offset - datalen, datalen);
5991
0
  }
5992
0
}
5993
5994
/*
5995
 * conn_recv_connection_close is called when CONNECTION_CLOSE or
5996
 * APPLICATION_CLOSE frame is received.
5997
 */
5998
static int conn_recv_connection_close(ngtcp2_conn *conn,
5999
0
                                      ngtcp2_connection_close *fr) {
6000
0
  ngtcp2_ccerr *ccerr = &conn->rx.ccerr;
6001
6002
0
  conn->state = NGTCP2_CS_DRAINING;
6003
0
  if (fr->type == NGTCP2_FRAME_CONNECTION_CLOSE) {
6004
0
    ccerr->type = NGTCP2_CCERR_TYPE_TRANSPORT;
6005
0
  } else {
6006
0
    ccerr->type = NGTCP2_CCERR_TYPE_APPLICATION;
6007
0
  }
6008
0
  ccerr->error_code = fr->error_code;
6009
0
  ccerr->frame_type = fr->frame_type;
6010
6011
0
  if (!fr->reasonlen) {
6012
0
    ccerr->reasonlen = 0;
6013
6014
0
    return 0;
6015
0
  }
6016
6017
0
  if (ccerr->reason == NULL) {
6018
0
    ccerr->reason = ngtcp2_mem_malloc(conn->mem, NGTCP2_CCERR_MAX_REASONLEN);
6019
0
    if (ccerr->reason == NULL) {
6020
0
      return NGTCP2_ERR_NOMEM;
6021
0
    }
6022
0
  }
6023
6024
0
  ccerr->reasonlen = ngtcp2_min_size(fr->reasonlen, NGTCP2_CCERR_MAX_REASONLEN);
6025
0
  ngtcp2_cpymem((uint8_t *)ccerr->reason, fr->reason, ccerr->reasonlen);
6026
6027
0
  return 0;
6028
0
}
6029
6030
static void conn_recv_path_challenge(ngtcp2_conn *conn, const ngtcp2_path *path,
6031
0
                                     ngtcp2_path_challenge *fr) {
6032
0
  ngtcp2_path_challenge_entry *ent;
6033
6034
  /* client only responds to PATH_CHALLENGE from the current path or
6035
     path which client is migrating to. */
6036
0
  if (!conn->server && !ngtcp2_path_eq(&conn->dcid.current.ps.path, path) &&
6037
0
      (!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path))) {
6038
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
6039
0
                    "discard PATH_CHALLENGE from the path which is not current "
6040
0
                    "or endpoint is migrating to");
6041
0
    return;
6042
0
  }
6043
6044
0
  ent = ngtcp2_ringbuf_push_front(&conn->rx.path_challenge.rb);
6045
0
  ngtcp2_path_challenge_entry_init(ent, path, &fr->data);
6046
0
}
6047
6048
/*
6049
 * conn_reset_congestion_state resets congestion state.
6050
 */
6051
0
static void conn_reset_congestion_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
6052
0
  conn_reset_conn_stat_cc(conn, &conn->cstat);
6053
6054
0
  if (conn->cc.reset) {
6055
0
    conn->cc.reset(&conn->cc, &conn->cstat, ts);
6056
0
  }
6057
6058
0
  if (conn->hs_pktns) {
6059
0
    ngtcp2_rtb_reset_cc_state(&conn->hs_pktns->rtb,
6060
0
                              conn->hs_pktns->tx.last_pkt_num + 1);
6061
0
  }
6062
0
  ngtcp2_rtb_reset_cc_state(&conn->pktns.rtb, conn->pktns.tx.last_pkt_num + 1);
6063
0
  ngtcp2_rst_reset(&conn->rst);
6064
6065
0
  conn->tx.pacing.next_ts = UINT64_MAX;
6066
0
  conn->tx.pacing.compensation = 0;
6067
0
}
6068
6069
/*
6070
 * conn_server_preferred_addr_migration returns nonzero if
6071
 * |local_addr| equals to one of the preferred addresses.
6072
 */
6073
static int conn_server_preferred_addr_migration(const ngtcp2_conn *conn,
6074
0
                                                const ngtcp2_addr *local_addr) {
6075
0
  const ngtcp2_preferred_addr *paddr;
6076
6077
0
  assert(conn->server);
6078
6079
0
  if (!conn->local.transport_params.preferred_addr_present) {
6080
0
    return 0;
6081
0
  }
6082
6083
0
  paddr = &conn->local.transport_params.preferred_addr;
6084
6085
0
  switch (local_addr->addr->sa_family) {
6086
0
  case NGTCP2_AF_INET:
6087
0
    if (!paddr->ipv4_present) {
6088
0
      return 0;
6089
0
    }
6090
6091
0
    return ngtcp2_sockaddr_eq((const ngtcp2_sockaddr *)&paddr->ipv4,
6092
0
                              local_addr->addr);
6093
0
  case NGTCP2_AF_INET6:
6094
0
    if (!paddr->ipv6_present) {
6095
0
      return 0;
6096
0
    }
6097
6098
0
    return ngtcp2_sockaddr_eq((const ngtcp2_sockaddr *)&paddr->ipv6,
6099
0
                              local_addr->addr);
6100
0
  }
6101
6102
0
  return 0;
6103
0
}
6104
6105
static int conn_recv_path_response(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd,
6106
0
                                   ngtcp2_path_response *fr, ngtcp2_tstamp ts) {
6107
0
  int rv;
6108
0
  ngtcp2_pv *pv = conn->pv, *npv = NULL;
6109
0
  uint8_t ent_flags;
6110
6111
0
  if (!pv) {
6112
0
    return 0;
6113
0
  }
6114
6115
0
  rv = ngtcp2_pv_validate(pv, &ent_flags, &fr->data);
6116
0
  if (rv != 0) {
6117
0
    assert(!ngtcp2_err_is_fatal(rv));
6118
6119
0
    return 0;
6120
0
  }
6121
6122
0
  if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
6123
0
    if (pv->dcid.seq != conn->dcid.current.seq ||
6124
0
        !ngtcp2_path_eq(&pv->dcid.ps.path, &conn->dcid.current.ps.path)) {
6125
0
      if (conn->dcid.current.cid.datalen &&
6126
0
          pv->dcid.seq != conn->dcid.current.seq) {
6127
0
        rv = conn_retire_active_dcid(conn, &conn->dcid.current, ts);
6128
0
        if (rv != 0) {
6129
0
          return rv;
6130
0
        }
6131
0
      }
6132
6133
0
      if (conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) {
6134
0
        ngtcp2_conn_add_path_history(conn, &conn->dcid.current, ts);
6135
0
      }
6136
6137
0
      ngtcp2_dcid_copy(&conn->dcid.current, &pv->dcid);
6138
6139
0
      conn_reset_congestion_state(conn, ts);
6140
0
      conn_reset_ecn_validation_state(conn);
6141
6142
0
      if (conn->server && conn->rx.preferred_addr.pkt_num == -1 &&
6143
0
          conn_server_preferred_addr_migration(
6144
0
            conn, &conn->dcid.current.ps.path.local)) {
6145
0
        conn->rx.preferred_addr.pkt_num = hd->pkt_num;
6146
0
      }
6147
0
    }
6148
6149
0
    assert(ngtcp2_path_eq(&pv->dcid.ps.path, &conn->dcid.current.ps.path));
6150
6151
0
    conn->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
6152
6153
0
    if (!conn->local.settings.no_pmtud) {
6154
0
      ngtcp2_conn_stop_pmtud(conn);
6155
6156
0
      if (!(ent_flags & NGTCP2_PV_ENTRY_FLAG_UNDERSIZED)) {
6157
0
        rv = conn_start_pmtud(conn);
6158
0
        if (rv != 0) {
6159
0
          return rv;
6160
0
        }
6161
0
      }
6162
0
    }
6163
6164
0
    if (!(ent_flags & NGTCP2_PV_ENTRY_FLAG_UNDERSIZED)) {
6165
0
      rv = conn_call_path_validation(conn, pv,
6166
0
                                     NGTCP2_PATH_VALIDATION_RESULT_SUCCESS);
6167
0
      if (rv != 0) {
6168
0
        return rv;
6169
0
      }
6170
0
    }
6171
0
  }
6172
6173
0
  if (ent_flags & NGTCP2_PV_ENTRY_FLAG_UNDERSIZED) {
6174
0
    assert(conn->server);
6175
6176
    /* Validate path again */
6177
0
    rv = ngtcp2_pv_new(&npv, &pv->dcid, conn_compute_pv_timeout(conn),
6178
0
                       NGTCP2_PV_FLAG_NONE, &conn->log, conn->mem);
6179
0
    if (rv != 0) {
6180
0
      return rv;
6181
0
    }
6182
6183
0
    npv->dcid.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
6184
6185
0
    if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
6186
0
      ngtcp2_pv_set_fallback(npv, &pv->fallback_dcid, pv->fallback_pto);
6187
0
    }
6188
0
  } else if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
6189
0
    rv = ngtcp2_pv_new(&npv, &pv->fallback_dcid,
6190
0
                       conn_compute_pv_timeout_pto(conn, pv->fallback_pto),
6191
0
                       NGTCP2_PV_FLAG_DONT_CARE, &conn->log, conn->mem);
6192
0
    if (rv != 0) {
6193
0
      return rv;
6194
0
    }
6195
0
  }
6196
6197
0
  if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) {
6198
    /* Unset the flag bit so that conn_stop_pv does not retire
6199
       DCID. */
6200
0
    pv->flags &= (uint8_t)~NGTCP2_PV_FLAG_FALLBACK_PRESENT;
6201
0
  }
6202
6203
0
  rv = conn_stop_pv(conn, ts);
6204
0
  if (rv != 0) {
6205
0
    ngtcp2_pv_del(npv);
6206
0
    return rv;
6207
0
  }
6208
6209
0
  conn->pv = npv;
6210
6211
0
  return conn_call_begin_path_validation(conn, conn->pv);
6212
0
}
6213
6214
/*
6215
 * pktns_pkt_num_is_duplicate returns nonzero if |pkt_num| is
6216
 * duplicated packet number.
6217
 */
6218
0
static int pktns_pkt_num_is_duplicate(ngtcp2_pktns *pktns, int64_t pkt_num) {
6219
0
  return ngtcp2_gaptr_is_pushed(&pktns->rx.pngap, (uint64_t)pkt_num, 1);
6220
0
}
6221
6222
/*
6223
 * pktns_commit_recv_pkt_num marks packet number |pkt_num| as
6224
 * received.  It stores |pkt_num| and its reception timestamp |ts| in
6225
 * order to send its ACK.  It also increase ECN counts from |pi|.
6226
 * |require_ack| is nonzero if the received packet is ack-eliciting.
6227
 *
6228
 * It returns 0 if it succeeds, or one of the following negative error
6229
 * codes:
6230
 *
6231
 * NGTCP2_ERR_NOMEM
6232
 *     Out of memory
6233
 * NGTCP2_ERR_PROTO
6234
 *     Same packet number has already been added.
6235
 */
6236
static int pktns_commit_recv_pkt_num(ngtcp2_pktns *pktns, int64_t pkt_num,
6237
                                     const ngtcp2_pkt_info *pi, int require_ack,
6238
0
                                     ngtcp2_tstamp ts) {
6239
0
  ngtcp2_acktr *acktr = &pktns->acktr;
6240
0
  ngtcp2_range r;
6241
0
  int rv;
6242
6243
0
  rv = ngtcp2_gaptr_push(&pktns->rx.pngap, (uint64_t)pkt_num, 1);
6244
0
  if (rv != 0) {
6245
0
    return rv;
6246
0
  }
6247
6248
0
  if (ngtcp2_ksl_len(&pktns->rx.pngap.gap) > 256) {
6249
0
    ngtcp2_gaptr_drop_first_gap(&pktns->rx.pngap);
6250
0
  }
6251
6252
0
  if (require_ack) {
6253
0
    if (pktns->rx.max_ack_eliciting_pkt_num != -1) {
6254
0
      if (pkt_num < pktns->rx.max_ack_eliciting_pkt_num) {
6255
0
        ngtcp2_acktr_immediate_ack(&pktns->acktr);
6256
0
      } else if (pkt_num != pktns->rx.max_ack_eliciting_pkt_num + 1) {
6257
0
        r = ngtcp2_gaptr_get_first_gap_after(
6258
0
          &pktns->rx.pngap, (uint64_t)pktns->rx.max_ack_eliciting_pkt_num);
6259
6260
0
        if (r.begin < (uint64_t)pkt_num) {
6261
0
          ngtcp2_acktr_immediate_ack(&pktns->acktr);
6262
0
        }
6263
0
      }
6264
0
    }
6265
6266
0
    if (pktns->rx.max_ack_eliciting_pkt_num < pkt_num) {
6267
0
      pktns->rx.max_ack_eliciting_pkt_num = pkt_num;
6268
0
    }
6269
0
  }
6270
6271
0
  ngtcp2_acktr_increase_ecn_counts(acktr, pi);
6272
6273
0
  rv = ngtcp2_acktr_add(acktr, pkt_num, require_ack, ts);
6274
0
  if (rv != 0) {
6275
0
    assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
6276
0
    return rv;
6277
0
  }
6278
6279
0
  return 0;
6280
0
}
6281
6282
/*
6283
 * verify_token verifies |hd| contains |token| in its token field.  It
6284
 * returns 0 if it succeeds, or NGTCP2_ERR_PROTO.
6285
 */
6286
static int verify_token(const uint8_t *token, size_t tokenlen,
6287
0
                        const ngtcp2_pkt_hd *hd) {
6288
0
  if (tokenlen == hd->tokenlen && ngtcp2_cmemeq(token, hd->token, tokenlen)) {
6289
0
    return 0;
6290
0
  }
6291
0
  return NGTCP2_ERR_PROTO;
6292
0
}
6293
6294
/*
6295
 * vneg_available_versions_includes returns nonzero if
6296
 * |available_versions| of length |available_versionslen| includes
6297
 * |version|.  |available_versions| is the wire image of
6298
 * available_versions field of version_information transport
6299
 * parameter, and each version is encoded in network byte order.
6300
 */
6301
static int vneg_available_versions_includes(const uint8_t *available_versions,
6302
                                            size_t available_versionslen,
6303
0
                                            uint32_t version) {
6304
0
  size_t i;
6305
0
  uint32_t v;
6306
6307
0
  assert(!(available_versionslen & 0x3));
6308
6309
0
  if (available_versionslen == 0) {
6310
0
    return 0;
6311
0
  }
6312
6313
0
  for (i = 0; i < available_versionslen; i += sizeof(uint32_t)) {
6314
0
    available_versions = ngtcp2_get_uint32be(&v, available_versions);
6315
6316
0
    if (version == v) {
6317
0
      return 1;
6318
0
    }
6319
0
  }
6320
6321
0
  return 0;
6322
0
}
6323
6324
/*
6325
 * conn_verify_fixed_bit verifies that fixed bit in |hd| is
6326
 * acceptable.
6327
 *
6328
 * This function returns 0 if it succeeds, or one of the following
6329
 * negative error codes:
6330
 *
6331
 * NGTCP2_ERR_INVALID_ARGUMENT
6332
 *     Clearing fixed bit is not permitted.
6333
 */
6334
0
static int conn_verify_fixed_bit(ngtcp2_conn *conn, ngtcp2_pkt_hd *hd) {
6335
0
  if (!(hd->flags & NGTCP2_PKT_FLAG_FIXED_BIT_CLEAR)) {
6336
0
    return 0;
6337
0
  }
6338
6339
0
  if (conn->server) {
6340
0
    switch (hd->type) {
6341
0
    case NGTCP2_PKT_INITIAL:
6342
0
    case NGTCP2_PKT_0RTT:
6343
0
    case NGTCP2_PKT_HANDSHAKE:
6344
      /* RFC 9287 requires that a token from NEW_TOKEN. */
6345
0
      if (!(conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) &&
6346
0
          (conn->local.settings.token_type != NGTCP2_TOKEN_TYPE_NEW_TOKEN ||
6347
0
           !conn->local.settings.tokenlen)) {
6348
0
        return NGTCP2_ERR_INVALID_ARGUMENT;
6349
0
      }
6350
6351
0
      break;
6352
0
    }
6353
0
  }
6354
6355
  /* TODO we have no information that we enabled grease_quic_bit in
6356
     the previous connection. */
6357
0
  if (!conn->local.transport_params.grease_quic_bit) {
6358
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
6359
0
  }
6360
6361
0
  return 0;
6362
0
}
6363
6364
static int conn_recv_crypto(ngtcp2_conn *conn,
6365
                            ngtcp2_encryption_level encryption_level,
6366
                            ngtcp2_strm *strm, const ngtcp2_stream *fr,
6367
                            ngtcp2_tstamp ts);
6368
6369
static ngtcp2_ssize conn_recv_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
6370
                                  const ngtcp2_pkt_info *pi, const uint8_t *pkt,
6371
                                  size_t pktlen, size_t dgramlen,
6372
                                  ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts);
6373
6374
static int conn_process_buffered_protected_pkt(ngtcp2_conn *conn,
6375
                                               ngtcp2_pktns *pktns,
6376
                                               ngtcp2_tstamp ts);
6377
6378
/*
6379
 * conn_recv_handshake_pkt processes received packet |pkt| whose
6380
 * length is |pktlen| during handshake period.  The buffer pointed by
6381
 * |pkt| might contain multiple packets.  This function only processes
6382
 * one packet.  |pkt_ts| is the timestamp when packet is received.
6383
 * |ts| should be the current time.  Usually they are the same, but
6384
 * for buffered packets, |pkt_ts| would be earlier than |ts|.
6385
 *
6386
 * This function returns the number of bytes it reads if it succeeds,
6387
 * or one of the following negative error codes:
6388
 *
6389
 * NGTCP2_ERR_RECV_VERSION_NEGOTIATION
6390
 *     Version Negotiation packet is received.
6391
 * NGTCP2_ERR_NOMEM
6392
 *     Out of memory.
6393
 * NGTCP2_ERR_CALLBACK_FAILURE
6394
 *     User-defined callback function failed.
6395
 * NGTCP2_ERR_DISCARD_PKT
6396
 *     Packet was discarded because plain text header was malformed;
6397
 *     or its payload could not be decrypted.
6398
 * NGTCP2_ERR_FRAME_FORMAT
6399
 *     Frame is badly formatted
6400
 * NGTCP2_ERR_ACK_FRAME
6401
 *     ACK frame is malformed.
6402
 * NGTCP2_ERR_CRYPTO
6403
 *     TLS stack reported error.
6404
 * NGTCP2_ERR_PROTO
6405
 *     Generic QUIC protocol error.
6406
 * NGTCP2_ERR_INTERNAL
6407
 *     Suspicious remote endpoint activity exceeded threshold.
6408
 *
6409
 * In addition to the above error codes, error codes returned from
6410
 * conn_recv_pkt are also returned.
6411
 */
6412
static ngtcp2_ssize
6413
conn_recv_handshake_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
6414
                        const ngtcp2_pkt_info *pi, const uint8_t *pkt,
6415
                        size_t pktlen, size_t dgramlen, ngtcp2_tstamp pkt_ts,
6416
0
                        ngtcp2_tstamp ts) {
6417
0
  ngtcp2_ssize nread;
6418
0
  ngtcp2_pkt_hd hd;
6419
0
  ngtcp2_frame_decoder frd;
6420
0
  ngtcp2_frame fr;
6421
0
  int rv;
6422
0
  int require_ack = 0;
6423
0
  size_t hdpktlen;
6424
0
  const uint8_t *payload;
6425
0
  size_t payloadlen;
6426
0
  ngtcp2_ssize nwrite;
6427
0
  ngtcp2_crypto_aead *aead;
6428
0
  ngtcp2_crypto_cipher *hp;
6429
0
  ngtcp2_crypto_km *ckm;
6430
0
  ngtcp2_crypto_cipher_ctx *hp_ctx;
6431
0
  ngtcp2_hp_mask hp_mask;
6432
0
  ngtcp2_decrypt decrypt;
6433
0
  ngtcp2_pktns *pktns;
6434
0
  ngtcp2_strm *crypto;
6435
0
  ngtcp2_encryption_level encryption_level;
6436
0
  int invalid_reserved_bits = 0;
6437
0
  size_t num_ack_processed = 0;
6438
6439
0
  if (!(pkt[0] & NGTCP2_HEADER_FORM_BIT)) {
6440
    /* Ignore 1RTT packet unless server's first Handshake packet has
6441
       been transmitted. */
6442
0
    if (conn->state == NGTCP2_CS_SERVER_INITIAL ||
6443
0
        !should_buffer_1rtt_pkt(pkt, pktlen)) {
6444
0
      return (ngtcp2_ssize)pktlen;
6445
0
    }
6446
6447
0
    if (conn->pktns.crypto.rx.ckm) {
6448
0
      return 0;
6449
0
    }
6450
6451
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
6452
0
                     "buffering 1RTT packet len=%zu", pktlen);
6453
6454
0
    rv =
6455
0
      conn_buffer_pkt(conn, &conn->pktns, path, pi, pkt, pktlen, dgramlen, ts);
6456
0
    if (rv != 0) {
6457
0
      assert(ngtcp2_err_is_fatal(rv));
6458
0
      return rv;
6459
0
    }
6460
0
    return (ngtcp2_ssize)pktlen;
6461
0
  }
6462
6463
0
  nread = ngtcp2_pkt_decode_hd_long(&hd, pkt, pktlen);
6464
0
  if (nread < 0) {
6465
0
    return NGTCP2_ERR_DISCARD_PKT;
6466
0
  }
6467
6468
0
  switch (hd.type) {
6469
0
  case NGTCP2_PKT_VERSION_NEGOTIATION:
6470
0
    hdpktlen = (size_t)nread;
6471
6472
0
    ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
6473
6474
0
    if (conn->server) {
6475
0
      return NGTCP2_ERR_DISCARD_PKT;
6476
0
    }
6477
6478
    /* Receiving Version Negotiation packet after getting Handshake
6479
       packet from server is invalid. */
6480
0
    if (conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) {
6481
0
      return NGTCP2_ERR_DISCARD_PKT;
6482
0
    }
6483
6484
0
    if (!ngtcp2_cid_eq(&conn->oscid, &hd.dcid)) {
6485
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6486
0
                      "packet was ignored because of mismatched DCID");
6487
0
      return NGTCP2_ERR_DISCARD_PKT;
6488
0
    }
6489
6490
0
    if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
6491
      /* Just discard invalid Version Negotiation packet */
6492
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6493
0
                      "packet was ignored because of mismatched SCID");
6494
0
      return NGTCP2_ERR_DISCARD_PKT;
6495
0
    }
6496
0
    rv =
6497
0
      conn_on_version_negotiation(conn, &hd, pkt + hdpktlen, pktlen - hdpktlen);
6498
0
    if (rv != 0) {
6499
0
      if (ngtcp2_err_is_fatal(rv)) {
6500
0
        return rv;
6501
0
      }
6502
0
      return NGTCP2_ERR_DISCARD_PKT;
6503
0
    }
6504
0
    return NGTCP2_ERR_RECV_VERSION_NEGOTIATION;
6505
0
  case NGTCP2_PKT_RETRY:
6506
0
    hdpktlen = (size_t)nread;
6507
6508
0
    ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
6509
6510
0
    if (conn->server) {
6511
0
      return NGTCP2_ERR_DISCARD_PKT;
6512
0
    }
6513
6514
0
    if (conn_verify_fixed_bit(conn, &hd) != 0) {
6515
0
      return NGTCP2_ERR_DISCARD_PKT;
6516
0
    }
6517
6518
    /* Receiving Retry packet after getting Initial packet from server
6519
       is invalid. */
6520
0
    if (conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) {
6521
0
      return NGTCP2_ERR_DISCARD_PKT;
6522
0
    }
6523
6524
0
    if (conn->client_chosen_version != hd.version) {
6525
0
      return NGTCP2_ERR_DISCARD_PKT;
6526
0
    }
6527
6528
0
    rv = conn_on_retry(conn, &hd, hdpktlen, pkt, pktlen, ts);
6529
0
    if (rv != 0) {
6530
0
      if (ngtcp2_err_is_fatal(rv)) {
6531
0
        return rv;
6532
0
      }
6533
0
      return NGTCP2_ERR_DISCARD_PKT;
6534
0
    }
6535
0
    return (ngtcp2_ssize)pktlen;
6536
0
  }
6537
6538
0
  if (pktlen < (size_t)nread + hd.len) {
6539
0
    return NGTCP2_ERR_DISCARD_PKT;
6540
0
  }
6541
6542
0
  pktlen = (size_t)nread + hd.len;
6543
6544
0
  if (!ngtcp2_is_supported_version(hd.version)) {
6545
0
    return NGTCP2_ERR_DISCARD_PKT;
6546
0
  }
6547
6548
0
  if (conn->server) {
6549
0
    if (hd.version != conn->client_chosen_version &&
6550
0
        (!conn->negotiated_version || hd.version != conn->negotiated_version)) {
6551
0
      return NGTCP2_ERR_DISCARD_PKT;
6552
0
    }
6553
0
  } else if (hd.version != conn->client_chosen_version &&
6554
0
             conn->negotiated_version &&
6555
0
             hd.version != conn->negotiated_version) {
6556
0
    return NGTCP2_ERR_DISCARD_PKT;
6557
0
  }
6558
6559
0
  if (conn_verify_fixed_bit(conn, &hd) != 0) {
6560
0
    return NGTCP2_ERR_DISCARD_PKT;
6561
0
  }
6562
6563
  /* Quoted from spec: if subsequent packets of those types include a
6564
     different Source Connection ID, they MUST be discarded. */
6565
0
  if ((conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) &&
6566
0
      !ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
6567
0
    ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
6568
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6569
0
                    "packet was ignored because of mismatched SCID");
6570
0
    return NGTCP2_ERR_DISCARD_PKT;
6571
0
  }
6572
6573
0
  switch (hd.type) {
6574
0
  case NGTCP2_PKT_0RTT:
6575
0
    if (!conn->server) {
6576
0
      return NGTCP2_ERR_DISCARD_PKT;
6577
0
    }
6578
6579
0
    if (hd.version != conn->client_chosen_version) {
6580
0
      return NGTCP2_ERR_DISCARD_PKT;
6581
0
    }
6582
6583
0
    if (conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) {
6584
0
      if (conn->early.ckm) {
6585
0
        ngtcp2_ssize nread2;
6586
        /* TODO Avoid to parse header twice. */
6587
0
        nread2 =
6588
0
          conn_recv_pkt(conn, path, pi, pkt, pktlen, dgramlen, pkt_ts, ts);
6589
0
        if (nread2 < 0) {
6590
0
          return nread2;
6591
0
        }
6592
0
      }
6593
6594
      /* Discard 0-RTT packet if we don't have a key to decrypt it. */
6595
0
      return (ngtcp2_ssize)pktlen;
6596
0
    }
6597
6598
    /* Buffer re-ordered 0-RTT packet. */
6599
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
6600
0
                     "buffering 0-RTT packet len=%zu", pktlen);
6601
6602
0
    rv = conn_buffer_pkt(conn, conn->in_pktns, path, pi, pkt, pktlen, dgramlen,
6603
0
                         ts);
6604
0
    if (rv != 0) {
6605
0
      assert(ngtcp2_err_is_fatal(rv));
6606
0
      return rv;
6607
0
    }
6608
6609
0
    return (ngtcp2_ssize)pktlen;
6610
0
  case NGTCP2_PKT_INITIAL:
6611
0
    if (!conn->in_pktns) {
6612
0
      ngtcp2_log_info(
6613
0
        &conn->log, NGTCP2_LOG_EVENT_PKT,
6614
0
        "Initial packet is discarded because keys have been discarded");
6615
0
      return (ngtcp2_ssize)pktlen;
6616
0
    }
6617
6618
0
    assert(conn->in_pktns);
6619
6620
0
    if (conn->server) {
6621
0
      if (dgramlen < NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
6622
0
        ngtcp2_log_infof(
6623
0
          &conn->log, NGTCP2_LOG_EVENT_PKT,
6624
0
          "Initial packet was ignored because it is included in UDP datagram "
6625
0
          "less than %d bytes: %zu bytes",
6626
0
          NGTCP2_MAX_UDP_PAYLOAD_SIZE, dgramlen);
6627
0
        return NGTCP2_ERR_DISCARD_PKT;
6628
0
      }
6629
0
      if (conn->local.settings.tokenlen) {
6630
0
        rv = verify_token(conn->local.settings.token,
6631
0
                          conn->local.settings.tokenlen, &hd);
6632
0
        if (rv != 0) {
6633
0
          ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6634
0
                          "packet was ignored because token is invalid");
6635
0
          return NGTCP2_ERR_DISCARD_PKT;
6636
0
        }
6637
0
      }
6638
0
      if ((conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) == 0) {
6639
        /* Set rcid here so that it is available to callback.  If this
6640
           packet is discarded later in this function and no packet is
6641
           processed in this connection attempt so far, connection
6642
           will be dropped. */
6643
0
        conn->rcid = hd.dcid;
6644
6645
0
        rv = conn_call_recv_client_initial(conn, &hd.dcid);
6646
0
        if (rv != 0) {
6647
0
          return rv;
6648
0
        }
6649
0
      }
6650
0
    } else {
6651
0
      if (hd.tokenlen != 0) {
6652
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6653
0
                        "packet was ignored because token is not empty");
6654
0
        return NGTCP2_ERR_DISCARD_PKT;
6655
0
      }
6656
6657
0
      if (hd.version != conn->client_chosen_version &&
6658
0
          !conn->negotiated_version && conn->vneg.version != hd.version) {
6659
0
        if (!vneg_available_versions_includes(conn->vneg.available_versions,
6660
0
                                              conn->vneg.available_versionslen,
6661
0
                                              hd.version)) {
6662
0
          return NGTCP2_ERR_DISCARD_PKT;
6663
0
        }
6664
6665
        /* Install new Initial keys using QUIC version = hd.version */
6666
0
        rv = conn_call_version_negotiation(
6667
0
          conn, hd.version,
6668
0
          (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) ? &conn->dcid.current.cid
6669
0
                                                      : &conn->rcid);
6670
0
        if (rv != 0) {
6671
0
          return rv;
6672
0
        }
6673
6674
0
        assert(conn->vneg.version == hd.version);
6675
0
      }
6676
0
    }
6677
6678
0
    pktns = conn->in_pktns;
6679
0
    crypto = &pktns->crypto.strm;
6680
0
    encryption_level = NGTCP2_ENCRYPTION_LEVEL_INITIAL;
6681
6682
0
    if (hd.version == conn->client_chosen_version) {
6683
0
      ckm = pktns->crypto.rx.ckm;
6684
0
      hp_ctx = &pktns->crypto.rx.hp_ctx;
6685
0
    } else {
6686
0
      assert(conn->vneg.version == hd.version);
6687
6688
0
      ckm = conn->vneg.rx.ckm;
6689
0
      hp_ctx = &conn->vneg.rx.hp_ctx;
6690
0
    }
6691
6692
0
    break;
6693
0
  case NGTCP2_PKT_HANDSHAKE:
6694
0
    if (hd.version != conn->negotiated_version) {
6695
0
      return NGTCP2_ERR_DISCARD_PKT;
6696
0
    }
6697
6698
0
    if (!conn->hs_pktns->crypto.rx.ckm) {
6699
0
      if (conn->server) {
6700
0
        ngtcp2_log_info(
6701
0
          &conn->log, NGTCP2_LOG_EVENT_PKT,
6702
0
          "Handshake packet at this point is unexpected and discarded");
6703
0
        return (ngtcp2_ssize)pktlen;
6704
0
      }
6705
0
      ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
6706
0
                       "buffering Handshake packet len=%zu", pktlen);
6707
6708
0
      rv = conn_buffer_pkt(conn, conn->hs_pktns, path, pi, pkt, pktlen,
6709
0
                           dgramlen, ts);
6710
0
      if (rv != 0) {
6711
0
        assert(ngtcp2_err_is_fatal(rv));
6712
0
        return rv;
6713
0
      }
6714
0
      return (ngtcp2_ssize)pktlen;
6715
0
    }
6716
6717
0
    pktns = conn->hs_pktns;
6718
0
    crypto = &pktns->crypto.strm;
6719
0
    encryption_level = NGTCP2_ENCRYPTION_LEVEL_HANDSHAKE;
6720
0
    ckm = pktns->crypto.rx.ckm;
6721
0
    hp_ctx = &pktns->crypto.rx.hp_ctx;
6722
6723
0
    break;
6724
0
  default:
6725
0
    ngtcp2_unreachable();
6726
0
  }
6727
6728
0
  hp_mask = conn->callbacks.hp_mask;
6729
0
  decrypt = conn->callbacks.decrypt;
6730
0
  aead = &pktns->crypto.ctx.aead;
6731
0
  hp = &pktns->crypto.ctx.hp;
6732
6733
0
  assert(ckm);
6734
0
  assert(hp_mask);
6735
0
  assert(decrypt);
6736
6737
0
  rv = conn_ensure_decrypt_hp_buffer(conn, (size_t)nread + 4);
6738
0
  if (rv != 0) {
6739
0
    return rv;
6740
0
  }
6741
6742
0
  nwrite = decrypt_hp(&hd, conn->crypto.decrypt_hp_buf.base, hp, pkt, pktlen,
6743
0
                      (size_t)nread, hp_ctx, hp_mask);
6744
0
  if (nwrite < 0) {
6745
0
    if (ngtcp2_err_is_fatal((int)nwrite)) {
6746
0
      return nwrite;
6747
0
    }
6748
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6749
0
                    "could not decrypt packet number");
6750
0
    return NGTCP2_ERR_DISCARD_PKT;
6751
0
  }
6752
6753
0
  hdpktlen = (size_t)nwrite;
6754
0
  payload = pkt + hdpktlen;
6755
0
  payloadlen = hd.len - hd.pkt_numlen;
6756
6757
0
  hd.pkt_num = ngtcp2_pkt_adjust_pkt_num(pktns->acktr.max_pkt_num, hd.pkt_num,
6758
0
                                         hd.pkt_numlen);
6759
0
  if (hd.pkt_num > NGTCP2_MAX_PKT_NUM) {
6760
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_PKT,
6761
0
                     "pkn=%" PRId64 " is greater than maximum pkn", hd.pkt_num);
6762
0
    return NGTCP2_ERR_DISCARD_PKT;
6763
0
  }
6764
6765
0
  ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
6766
6767
0
  rv = ngtcp2_pkt_verify_reserved_bits(conn->crypto.decrypt_hp_buf.base[0]);
6768
0
  if (rv != 0) {
6769
0
    invalid_reserved_bits = 1;
6770
6771
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6772
0
                    "packet has incorrect reserved bits");
6773
6774
    /* Will return error after decrypting payload */
6775
0
  }
6776
6777
0
  if (pktns_pkt_num_is_duplicate(pktns, hd.pkt_num)) {
6778
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6779
0
                    "packet was discarded because of duplicated packet number");
6780
0
    return NGTCP2_ERR_DISCARD_PKT;
6781
0
  }
6782
6783
0
  rv = conn_ensure_decrypt_buffer(conn, payloadlen);
6784
0
  if (rv != 0) {
6785
0
    return rv;
6786
0
  }
6787
6788
0
  nwrite = decrypt_pkt(conn->crypto.decrypt_buf.base, aead, payload, payloadlen,
6789
0
                       conn->crypto.decrypt_hp_buf.base, hdpktlen, hd.pkt_num,
6790
0
                       ckm, decrypt);
6791
0
  if (nwrite < 0) {
6792
0
    if (ngtcp2_err_is_fatal((int)nwrite)) {
6793
0
      return nwrite;
6794
0
    }
6795
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6796
0
                    "could not decrypt packet payload");
6797
0
    return NGTCP2_ERR_DISCARD_PKT;
6798
0
  }
6799
6800
0
  if (invalid_reserved_bits) {
6801
0
    return NGTCP2_ERR_PROTO;
6802
0
  }
6803
6804
0
  if (!conn->server && hd.version != conn->client_chosen_version &&
6805
0
      !conn->negotiated_version) {
6806
0
    conn->negotiated_version = hd.version;
6807
6808
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
6809
0
                     "the negotiated version is 0x%08x",
6810
0
                     conn->negotiated_version);
6811
0
  }
6812
6813
0
  payload = conn->crypto.decrypt_buf.base;
6814
0
  payloadlen = (size_t)nwrite;
6815
6816
0
  switch (hd.type) {
6817
0
  case NGTCP2_PKT_INITIAL:
6818
0
    if (!conn->server ||
6819
0
        ((conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED) &&
6820
0
         !ngtcp2_cid_eq(&conn->rcid, &hd.dcid))) {
6821
0
      rv = conn_verify_dcid(conn, NULL, &hd);
6822
0
      if (rv != 0) {
6823
0
        if (ngtcp2_err_is_fatal(rv)) {
6824
0
          return rv;
6825
0
        }
6826
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6827
0
                        "packet was ignored because of mismatched DCID");
6828
0
        return NGTCP2_ERR_DISCARD_PKT;
6829
0
      }
6830
0
    }
6831
0
    break;
6832
0
  case NGTCP2_PKT_HANDSHAKE:
6833
0
    rv = conn_verify_dcid(conn, NULL, &hd);
6834
0
    if (rv != 0) {
6835
0
      if (ngtcp2_err_is_fatal(rv)) {
6836
0
        return rv;
6837
0
      }
6838
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6839
0
                      "packet was ignored because of mismatched DCID");
6840
0
      return NGTCP2_ERR_DISCARD_PKT;
6841
0
    }
6842
0
    break;
6843
0
  default:
6844
0
    ngtcp2_unreachable();
6845
0
  }
6846
6847
0
  if (payloadlen == 0) {
6848
    /* QUIC packet must contain at least one frame */
6849
0
    if (hd.type == NGTCP2_PKT_INITIAL) {
6850
0
      return NGTCP2_ERR_DISCARD_PKT;
6851
0
    }
6852
0
    return NGTCP2_ERR_PROTO;
6853
0
  }
6854
6855
0
  if (hd.type == NGTCP2_PKT_INITIAL &&
6856
0
      !(conn->flags & NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED)) {
6857
0
    conn->flags |= NGTCP2_CONN_FLAG_INITIAL_PKT_PROCESSED;
6858
0
    if (!conn->server) {
6859
0
      conn->dcid.current.cid = hd.scid;
6860
0
    }
6861
0
  }
6862
6863
0
  ngtcp2_qlog_pkt_received_start(&conn->qlog);
6864
6865
0
  for (; payloadlen;) {
6866
0
    nread = ngtcp2_frame_decoder_decode(&frd, &fr, payload, payloadlen);
6867
0
    if (nread < 0) {
6868
0
      return nread;
6869
0
    }
6870
6871
0
    payload += nread;
6872
0
    payloadlen -= (size_t)nread;
6873
6874
0
    switch (fr.hd.type) {
6875
0
    case NGTCP2_FRAME_ACK:
6876
0
    case NGTCP2_FRAME_ACK_ECN:
6877
0
      fr.ack.ack_delay = 0;
6878
0
      fr.ack.ack_delay_unscaled = 0;
6879
6880
0
      rv =
6881
0
        ngtcp2_pkt_validate_ack(&fr.ack, conn->local.settings.initial_pkt_num);
6882
0
      if (rv != 0) {
6883
0
        return rv;
6884
0
      }
6885
6886
0
      break;
6887
0
    }
6888
6889
0
    ngtcp2_log_rx_fr(&conn->log, &hd, &fr);
6890
6891
0
    switch (fr.hd.type) {
6892
0
    case NGTCP2_FRAME_ACK:
6893
0
    case NGTCP2_FRAME_ACK_ECN:
6894
0
      if (num_ack_processed >= NGTCP2_MAX_ACK_PER_PKT) {
6895
0
        break;
6896
0
      }
6897
0
      if (!conn->server && hd.type == NGTCP2_PKT_HANDSHAKE) {
6898
0
        conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
6899
0
      }
6900
0
      rv = conn_recv_ack(conn, pktns, &fr.ack, pkt_ts, ts);
6901
0
      if (rv != 0) {
6902
0
        return rv;
6903
0
      }
6904
0
      ++num_ack_processed;
6905
0
      break;
6906
0
    case NGTCP2_FRAME_PADDING:
6907
0
      break;
6908
0
    case NGTCP2_FRAME_CRYPTO:
6909
0
      if (!conn->server && !conn->negotiated_version &&
6910
0
          ngtcp2_vec_len(fr.stream.data, fr.stream.datacnt)) {
6911
0
        conn->negotiated_version = hd.version;
6912
6913
0
        ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
6914
0
                         "the negotiated version is 0x%08x",
6915
0
                         conn->negotiated_version);
6916
0
      }
6917
6918
0
      rv = conn_recv_crypto(conn, encryption_level, crypto, &fr.stream, ts);
6919
0
      if (rv != 0) {
6920
0
        return rv;
6921
0
      }
6922
0
      require_ack = 1;
6923
0
      break;
6924
0
    case NGTCP2_FRAME_CONNECTION_CLOSE:
6925
0
      rv = conn_recv_connection_close(conn, &fr.connection_close);
6926
0
      if (rv != 0) {
6927
0
        return rv;
6928
0
      }
6929
0
      break;
6930
0
    case NGTCP2_FRAME_PING:
6931
0
      ++conn->cstat.ping_recv;
6932
0
      require_ack = 1;
6933
0
      break;
6934
0
    default:
6935
0
      return NGTCP2_ERR_PROTO;
6936
0
    }
6937
6938
0
    ngtcp2_qlog_write_frame(&conn->qlog, &fr);
6939
0
  }
6940
6941
0
  if (hd.type == NGTCP2_PKT_HANDSHAKE) {
6942
    /* Successful processing of Handshake packet from a remote
6943
       endpoint validates its source address. */
6944
0
    conn->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
6945
0
  }
6946
6947
0
  ngtcp2_qlog_pkt_received_end(&conn->qlog, &hd, pktlen);
6948
6949
0
  rv = pktns_commit_recv_pkt_num(pktns, hd.pkt_num, pi, require_ack, pkt_ts);
6950
0
  if (rv != 0) {
6951
0
    return rv;
6952
0
  }
6953
6954
  /* Initial and Handshake are always acknowledged without delay.  No
6955
     need to call ngtcp2_acktr_immediate_ack(). */
6956
6957
0
  conn_restart_timer_on_read(conn, ts);
6958
6959
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
6960
6961
0
  return conn->state == NGTCP2_CS_DRAINING ? NGTCP2_ERR_DRAINING
6962
0
                                           : (ngtcp2_ssize)pktlen;
6963
0
}
6964
6965
0
static int is_unrecoverable_error(int liberr) {
6966
0
  switch (liberr) {
6967
0
  case NGTCP2_ERR_CRYPTO:
6968
0
  case NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM:
6969
0
  case NGTCP2_ERR_MALFORMED_TRANSPORT_PARAM:
6970
0
  case NGTCP2_ERR_TRANSPORT_PARAM:
6971
0
  case NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE:
6972
0
  case NGTCP2_ERR_INTERNAL:
6973
0
    return 1;
6974
0
  }
6975
6976
0
  return 0;
6977
0
}
6978
6979
/*
6980
 * conn_recv_handshake_cpkt processes compound packet during
6981
 * handshake.  The buffer pointed by |pkt| might contain multiple
6982
 * packets.  The 1RTT packet must be the last one because it does not
6983
 * have payload length field.
6984
 *
6985
 * This function returns the same error code returned by
6986
 * conn_recv_handshake_pkt.
6987
 */
6988
static ngtcp2_ssize conn_recv_handshake_cpkt(ngtcp2_conn *conn,
6989
                                             const ngtcp2_path *path,
6990
                                             const ngtcp2_pkt_info *pi,
6991
                                             const uint8_t *pkt, size_t pktlen,
6992
0
                                             ngtcp2_tstamp ts) {
6993
0
  ngtcp2_ssize nread;
6994
0
  size_t dgramlen = pktlen;
6995
0
  const uint8_t *origpkt = pkt;
6996
0
  uint32_t version;
6997
6998
0
  if (pktlen == 0) {
6999
0
    return 0;
7000
0
  }
7001
7002
0
  if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
7003
0
    conn->dcid.current.bytes_recv += dgramlen;
7004
0
  }
7005
7006
0
  while (pktlen) {
7007
0
    nread =
7008
0
      conn_recv_handshake_pkt(conn, path, pi, pkt, pktlen, dgramlen, ts, ts);
7009
0
    if (nread < 0) {
7010
0
      if (ngtcp2_err_is_fatal((int)nread)) {
7011
0
        return nread;
7012
0
      }
7013
7014
0
      if (nread == NGTCP2_ERR_DRAINING) {
7015
0
        return NGTCP2_ERR_DRAINING;
7016
0
      }
7017
7018
0
      if ((pkt[0] & NGTCP2_HEADER_FORM_BIT) && pktlen > 4) {
7019
        /* Not a Version Negotiation packet */
7020
0
        ngtcp2_get_uint32be(&version, &pkt[1]);
7021
0
        if (ngtcp2_pkt_get_type_long(version, pkt[0]) == NGTCP2_PKT_INITIAL) {
7022
0
          if (conn->server) {
7023
0
            if (is_unrecoverable_error((int)nread)) {
7024
              /* If server gets crypto error from TLS stack, it is
7025
                 unrecoverable, therefore drop connection. */
7026
0
              return nread;
7027
0
            }
7028
7029
0
            ++conn->cstat.pkt_discarded;
7030
7031
            /* If server discards first Initial, then drop connection
7032
               state.  This is because SCID in packet might be corrupted
7033
               and the current connection state might wrongly discard
7034
               valid packet and prevent the handshake from
7035
               completing. */
7036
0
            if (conn->in_pktns && conn->in_pktns->acktr.max_pkt_num == -1) {
7037
0
              return NGTCP2_ERR_DROP_CONN;
7038
0
            }
7039
7040
0
            return (ngtcp2_ssize)dgramlen;
7041
0
          }
7042
          /* client */
7043
0
          if (is_unrecoverable_error((int)nread)) {
7044
            /* If client gets crypto error from TLS stack, it is
7045
               unrecoverable, therefore drop connection. */
7046
0
            return nread;
7047
0
          }
7048
7049
0
          ++conn->cstat.pkt_discarded;
7050
7051
0
          return (ngtcp2_ssize)dgramlen;
7052
0
        }
7053
0
      }
7054
7055
0
      if (nread == NGTCP2_ERR_DISCARD_PKT) {
7056
0
        ++conn->cstat.pkt_discarded;
7057
0
        return (ngtcp2_ssize)dgramlen;
7058
0
      }
7059
7060
0
      return nread;
7061
0
    }
7062
7063
0
    if (nread == 0) {
7064
0
      assert(!(pkt[0] & NGTCP2_HEADER_FORM_BIT));
7065
0
      return pkt - origpkt;
7066
0
    }
7067
7068
0
    assert(pktlen >= (size_t)nread);
7069
0
    pkt += nread;
7070
0
    pktlen -= (size_t)nread;
7071
7072
0
    ++conn->cstat.pkt_recv;
7073
0
    conn->cstat.bytes_recv += (uint64_t)nread;
7074
7075
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_PKT,
7076
0
                     "read packet %td left %zu", nread, pktlen);
7077
0
  }
7078
7079
0
  return (ngtcp2_ssize)dgramlen;
7080
0
}
7081
7082
int ngtcp2_conn_init_stream(ngtcp2_conn *conn, ngtcp2_strm *strm,
7083
0
                            int64_t stream_id, void *stream_user_data) {
7084
0
  int rv;
7085
0
  uint64_t max_rx_offset;
7086
0
  uint64_t max_tx_offset;
7087
0
  int local_stream = conn_local_stream(conn, stream_id);
7088
7089
0
  assert(conn->remote.transport_params);
7090
7091
0
  if (bidi_stream(stream_id)) {
7092
0
    if (local_stream) {
7093
0
      max_rx_offset =
7094
0
        conn->local.transport_params.initial_max_stream_data_bidi_local;
7095
0
      max_tx_offset =
7096
0
        conn->remote.transport_params->initial_max_stream_data_bidi_remote;
7097
0
    } else {
7098
0
      max_rx_offset =
7099
0
        conn->local.transport_params.initial_max_stream_data_bidi_remote;
7100
0
      max_tx_offset =
7101
0
        conn->remote.transport_params->initial_max_stream_data_bidi_local;
7102
0
    }
7103
0
  } else if (local_stream) {
7104
0
    max_rx_offset = 0;
7105
0
    max_tx_offset = conn->remote.transport_params->initial_max_stream_data_uni;
7106
0
  } else {
7107
0
    max_rx_offset = conn->local.transport_params.initial_max_stream_data_uni;
7108
0
    max_tx_offset = 0;
7109
0
  }
7110
7111
0
  ngtcp2_strm_init(strm, stream_id, NGTCP2_STRM_FLAG_NONE, max_rx_offset,
7112
0
                   max_tx_offset, stream_user_data, &conn->frc_objalloc,
7113
0
                   conn->mem);
7114
7115
0
  rv =
7116
0
    ngtcp2_map_insert(&conn->strms, (ngtcp2_map_key_type)strm->stream_id, strm);
7117
0
  if (rv != 0) {
7118
0
    assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
7119
0
    goto fail;
7120
0
  }
7121
7122
0
  return 0;
7123
7124
0
fail:
7125
0
  ngtcp2_strm_free(strm);
7126
0
  return rv;
7127
0
}
7128
7129
/*
7130
 * conn_emit_pending_stream_data passes buffered ordered stream data
7131
 * to the application.  |rx_offset| is the first offset to deliver to
7132
 * the application.  This function assumes that the data up to
7133
 * |rx_offset| has been delivered already.  This function only passes
7134
 * the ordered data without any gap.  If there is a gap, it stops
7135
 * providing the data to the application, and returns.
7136
 *
7137
 * This function returns 0 if it succeeds, or one of the following
7138
 * negative error codes:
7139
 *
7140
 * NGTCP2_ERR_CALLBACK_FAILURE
7141
 *     User callback failed.
7142
 * NGTCP2_ERR_NOMEM
7143
 *     Out of memory.
7144
 */
7145
static int conn_emit_pending_stream_data(ngtcp2_conn *conn, ngtcp2_strm *strm,
7146
0
                                         uint64_t rx_offset) {
7147
0
  size_t datalen;
7148
0
  const uint8_t *data;
7149
0
  int rv;
7150
0
  uint64_t offset;
7151
0
  uint32_t sdflags;
7152
0
  int handshake_completed = conn_is_tls_handshake_completed(conn);
7153
7154
0
  if (!strm->rx.rob) {
7155
0
    return 0;
7156
0
  }
7157
7158
0
  for (;;) {
7159
    /* Stop calling callback if application has called
7160
       ngtcp2_conn_shutdown_stream_read() inside the callback.
7161
       Because it doubly counts connection window. */
7162
0
    if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
7163
0
      return 0;
7164
0
    }
7165
7166
0
    datalen = ngtcp2_rob_data_at(strm->rx.rob, &data, rx_offset);
7167
0
    if (datalen == 0) {
7168
0
      assert(rx_offset == ngtcp2_strm_rx_offset(strm));
7169
0
      return 0;
7170
0
    }
7171
7172
0
    offset = rx_offset;
7173
0
    rx_offset += datalen;
7174
7175
0
    sdflags = NGTCP2_STREAM_DATA_FLAG_NONE;
7176
0
    if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
7177
0
        rx_offset == strm->rx.last_offset) {
7178
0
      sdflags |= NGTCP2_STREAM_DATA_FLAG_FIN;
7179
0
    }
7180
0
    if (!handshake_completed) {
7181
0
      sdflags |= NGTCP2_STREAM_DATA_FLAG_0RTT;
7182
0
    }
7183
7184
0
    rv = conn_call_recv_stream_data(conn, strm, sdflags, offset, data, datalen);
7185
0
    if (rv != 0) {
7186
0
      return rv;
7187
0
    }
7188
7189
    /* ngtcp2_conn_shutdown_stream_read from a callback will free
7190
       strm->rx.rob. */
7191
0
    if (!strm->rx.rob) {
7192
0
      return 0;
7193
0
    }
7194
7195
0
    ngtcp2_rob_pop(strm->rx.rob, rx_offset - datalen, datalen);
7196
0
  }
7197
0
}
7198
7199
/*
7200
 * conn_recv_crypto is called when CRYPTO frame |fr| is received.
7201
 * |rx_offset_base| is the offset in the entire TLS handshake stream.
7202
 * fr->offset specifies the offset in each encryption level.
7203
 * |max_rx_offset| is, if it is nonzero, the maximum offset in the
7204
 * entire TLS handshake stream that |fr| can carry.
7205
 * |encryption_level| is the encryption level where this data is
7206
 * received.
7207
 *
7208
 * This function returns 0 if it succeeds, or one of the following
7209
 * negative error codes:
7210
 *
7211
 * NGTCP2_ERR_PROTO
7212
 *     CRYPTO frame has invalid offset.
7213
 * NGTCP2_ERR_NOMEM
7214
 *     Out of memory.
7215
 * NGTCP2_ERR_CRYPTO
7216
 *     TLS stack reported error.
7217
 * NGTCP2_ERR_FRAME_ENCODING
7218
 *     The end offset exceeds the maximum value.
7219
 * NGTCP2_ERR_CALLBACK_FAILURE
7220
 *     User-defined callback function failed.
7221
 * NGTCP2_ERR_INTERNAL
7222
 *     Suspicious remote endpoint activity exceeded threshold.
7223
 */
7224
static int conn_recv_crypto(ngtcp2_conn *conn,
7225
                            ngtcp2_encryption_level encryption_level,
7226
                            ngtcp2_strm *crypto, const ngtcp2_stream *fr,
7227
0
                            ngtcp2_tstamp ts) {
7228
0
  uint64_t fr_end_offset;
7229
0
  uint64_t rx_offset;
7230
0
  int rv;
7231
0
  ngtcp2_ssize nwrite;
7232
7233
0
  if (fr->datacnt == 0) {
7234
0
    if (encryption_level != NGTCP2_ENCRYPTION_LEVEL_INITIAL &&
7235
0
        ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7236
0
      return NGTCP2_ERR_INTERNAL;
7237
0
    }
7238
7239
0
    return 0;
7240
0
  }
7241
7242
0
  fr_end_offset = fr->offset + fr->data[0].len;
7243
7244
0
  if (NGTCP2_MAX_VARINT < fr_end_offset) {
7245
0
    return NGTCP2_ERR_FRAME_ENCODING;
7246
0
  }
7247
7248
0
  rx_offset = ngtcp2_strm_rx_offset(crypto);
7249
7250
0
  if (fr_end_offset <= rx_offset) {
7251
0
    if (encryption_level != NGTCP2_ENCRYPTION_LEVEL_INITIAL &&
7252
0
        ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7253
0
      return NGTCP2_ERR_INTERNAL;
7254
0
    }
7255
7256
0
    if (conn->server &&
7257
0
        !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_EARLY_RETRANSMIT) &&
7258
0
        encryption_level == NGTCP2_ENCRYPTION_LEVEL_INITIAL) {
7259
      /* https://datatracker.ietf.org/doc/html/rfc9002#section-6.2.3:
7260
         Speeding Up Handshake Completion
7261
7262
         When a server receives an Initial packet containing duplicate
7263
         CRYPTO data, it can assume the client did not receive all of
7264
         the server's CRYPTO data sent in Initial packets, or the
7265
         client's estimated RTT is too small.  ...  To speed up
7266
         handshake completion under these conditions, an endpoint MAY
7267
         send a packet containing unacknowledged CRYPTO data earlier
7268
         than the PTO expiry, subject to address validation limits;
7269
         ... */
7270
0
      conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_EARLY_RETRANSMIT;
7271
0
      conn->in_pktns->rtb.probe_pkt_left = 1;
7272
0
      conn->hs_pktns->rtb.probe_pkt_left = 1;
7273
0
    }
7274
0
    return 0;
7275
0
  }
7276
7277
0
  crypto->rx.last_offset =
7278
0
    ngtcp2_max_uint64(crypto->rx.last_offset, fr_end_offset);
7279
7280
  /* TODO Before dispatching incoming data to TLS stack, make sure
7281
     that previous data in previous encryption level has been
7282
     completely sent to TLS stack.  Usually, if data is left, it is an
7283
     error because key is generated after consuming all data in the
7284
     previous encryption level. */
7285
0
  if (fr->offset <= rx_offset) {
7286
0
    size_t ncut = (size_t)(rx_offset - fr->offset);
7287
0
    const uint8_t *data = fr->data[0].base + ncut;
7288
0
    size_t datalen = fr->data[0].len - ncut;
7289
0
    uint64_t offset = rx_offset;
7290
7291
0
    rx_offset += datalen;
7292
0
    ngtcp2_strm_update_rx_offset(crypto, rx_offset);
7293
7294
0
    rv =
7295
0
      conn_call_recv_crypto_data(conn, encryption_level, offset, data, datalen);
7296
0
    if (rv != 0) {
7297
0
      return rv;
7298
0
    }
7299
7300
0
    rv =
7301
0
      conn_emit_pending_crypto_data(conn, encryption_level, crypto, rx_offset);
7302
0
    if (rv != 0) {
7303
0
      return rv;
7304
0
    }
7305
7306
0
    return 0;
7307
0
  }
7308
7309
0
  if (fr_end_offset - rx_offset > NGTCP2_MAX_REORDERED_CRYPTO_DATA) {
7310
0
    return NGTCP2_ERR_CRYPTO_BUFFER_EXCEEDED;
7311
0
  }
7312
7313
0
  nwrite = ngtcp2_strm_recv_reordering(crypto, fr->data[0].base,
7314
0
                                       fr->data[0].len, fr->offset);
7315
0
  if (nwrite < 0) {
7316
0
    return (int)nwrite;
7317
0
  }
7318
7319
0
  if (encryption_level != NGTCP2_ENCRYPTION_LEVEL_INITIAL && nwrite == 0 &&
7320
0
      ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7321
0
    return NGTCP2_ERR_INTERNAL;
7322
0
  }
7323
7324
0
  return 0;
7325
0
}
7326
7327
/*
7328
 * conn_max_data_violated returns nonzero if receiving |datalen|
7329
 * violates connection flow control on local endpoint.
7330
 */
7331
0
static int conn_max_data_violated(ngtcp2_conn *conn, uint64_t datalen) {
7332
0
  return conn->rx.max_offset - conn->rx.offset < datalen;
7333
0
}
7334
7335
/*
7336
 * conn_recv_stream is called when STREAM frame |fr| is received.
7337
 *
7338
 * This function returns 0 if it succeeds, or one of the following
7339
 * negative error codes:
7340
 *
7341
 * NGTCP2_ERR_STREAM_STATE
7342
 *     STREAM frame is received for a local stream which is not
7343
 *     initiated; or STREAM frame is received for a local
7344
 *     unidirectional stream
7345
 * NGTCP2_ERR_STREAM_LIMIT
7346
 *     STREAM frame has remote stream ID which is strictly greater
7347
 *     than the allowed limit.
7348
 * NGTCP2_ERR_NOMEM
7349
 *     Out of memory.
7350
 * NGTCP2_ERR_CALLBACK_FAILURE
7351
 *     User-defined callback function failed.
7352
 * NGTCP2_ERR_FLOW_CONTROL
7353
 *     Flow control limit is violated; or the end offset of stream
7354
 *     data is beyond the NGTCP2_MAX_VARINT.
7355
 * NGTCP2_ERR_FINAL_SIZE
7356
 *     STREAM frame has strictly larger end offset than it is
7357
 *     permitted.
7358
 * NGTCP2_ERR_INTERNAL
7359
 *     Suspicious remote endpoint activity exceeded threshold.
7360
 */
7361
static int conn_recv_stream(ngtcp2_conn *conn, const ngtcp2_stream *fr,
7362
0
                            ngtcp2_tstamp ts) {
7363
0
  int rv;
7364
0
  ngtcp2_strm *strm;
7365
0
  ngtcp2_idtr *idtr;
7366
0
  uint64_t rx_offset, fr_end_offset;
7367
0
  int local_stream;
7368
0
  int bidi;
7369
0
  uint64_t datalen = ngtcp2_vec_len(fr->data, fr->datacnt);
7370
0
  uint32_t sdflags = NGTCP2_STREAM_DATA_FLAG_NONE;
7371
0
  ngtcp2_ssize nwrite;
7372
0
  int new_strm = 0;
7373
7374
0
  local_stream = conn_local_stream(conn, fr->stream_id);
7375
0
  bidi = bidi_stream(fr->stream_id);
7376
7377
0
  if (bidi) {
7378
0
    if (local_stream) {
7379
0
      if (conn->local.bidi.next_stream_id <= fr->stream_id) {
7380
0
        return NGTCP2_ERR_STREAM_STATE;
7381
0
      }
7382
0
    } else if (conn->remote.bidi.max_streams <
7383
0
               ngtcp2_ord_stream_id(fr->stream_id)) {
7384
0
      return NGTCP2_ERR_STREAM_LIMIT;
7385
0
    }
7386
7387
0
    idtr = &conn->remote.bidi.idtr;
7388
0
  } else {
7389
0
    if (local_stream) {
7390
0
      return NGTCP2_ERR_STREAM_STATE;
7391
0
    }
7392
0
    if (conn->remote.uni.max_streams < ngtcp2_ord_stream_id(fr->stream_id)) {
7393
0
      return NGTCP2_ERR_STREAM_LIMIT;
7394
0
    }
7395
7396
0
    idtr = &conn->remote.uni.idtr;
7397
0
  }
7398
7399
0
  if (NGTCP2_MAX_VARINT - datalen < fr->offset) {
7400
0
    return NGTCP2_ERR_FLOW_CONTROL;
7401
0
  }
7402
7403
0
  strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
7404
0
  if (strm == NULL) {
7405
0
    if (local_stream) {
7406
      /* The stream has been closed. */
7407
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7408
0
        return NGTCP2_ERR_INTERNAL;
7409
0
      }
7410
7411
0
      return 0;
7412
0
    }
7413
7414
0
    rv = ngtcp2_idtr_open(idtr, fr->stream_id);
7415
0
    if (rv != 0) {
7416
0
      if (ngtcp2_err_is_fatal(rv)) {
7417
0
        return rv;
7418
0
      }
7419
0
      assert(rv == NGTCP2_ERR_STREAM_IN_USE);
7420
      /* The stream has been closed. */
7421
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7422
0
        return NGTCP2_ERR_INTERNAL;
7423
0
      }
7424
7425
0
      return 0;
7426
0
    }
7427
7428
0
    strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
7429
0
    if (strm == NULL) {
7430
0
      return NGTCP2_ERR_NOMEM;
7431
0
    }
7432
7433
0
    rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
7434
0
    if (rv != 0) {
7435
0
      ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
7436
0
      return rv;
7437
0
    }
7438
7439
0
    new_strm = 1;
7440
7441
0
    if (!bidi) {
7442
0
      ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_WR);
7443
0
      strm->flags |= NGTCP2_STRM_FLAG_FIN_ACKED;
7444
0
    }
7445
7446
0
    rv = conn_call_stream_open(conn, strm);
7447
0
    if (rv != 0) {
7448
0
      return rv;
7449
0
    }
7450
0
  }
7451
7452
0
  fr_end_offset = fr->offset + datalen;
7453
7454
0
  if (strm->rx.max_offset < fr_end_offset) {
7455
0
    return NGTCP2_ERR_FLOW_CONTROL;
7456
0
  }
7457
7458
0
  if (strm->rx.last_offset < fr_end_offset) {
7459
0
    uint64_t len = fr_end_offset - strm->rx.last_offset;
7460
7461
0
    if (conn_max_data_violated(conn, len)) {
7462
0
      return NGTCP2_ERR_FLOW_CONTROL;
7463
0
    }
7464
7465
0
    conn->rx.offset += len;
7466
7467
0
    if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
7468
0
      ngtcp2_conn_extend_max_offset(conn, len);
7469
0
    }
7470
0
  }
7471
7472
0
  rx_offset = ngtcp2_strm_rx_offset(strm);
7473
7474
0
  if (fr->fin) {
7475
0
    if (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) {
7476
0
      if (strm->rx.last_offset != fr_end_offset) {
7477
0
        return NGTCP2_ERR_FINAL_SIZE;
7478
0
      }
7479
7480
0
      if (strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_RECVED) {
7481
0
        if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7482
0
          return NGTCP2_ERR_INTERNAL;
7483
0
        }
7484
7485
0
        return 0;
7486
0
      }
7487
7488
0
      if (rx_offset == fr_end_offset) {
7489
0
        if (!new_strm && ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7490
0
          return NGTCP2_ERR_INTERNAL;
7491
0
        }
7492
7493
0
        return 0;
7494
0
      }
7495
0
    } else if (strm->rx.last_offset > fr_end_offset) {
7496
0
      return NGTCP2_ERR_FINAL_SIZE;
7497
0
    } else {
7498
0
      strm->rx.last_offset = fr_end_offset;
7499
7500
0
      ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_RD);
7501
0
    }
7502
0
  } else {
7503
0
    if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
7504
0
        strm->rx.last_offset < fr_end_offset) {
7505
0
      return NGTCP2_ERR_FINAL_SIZE;
7506
0
    }
7507
7508
0
    strm->rx.last_offset =
7509
0
      ngtcp2_max_uint64(strm->rx.last_offset, fr_end_offset);
7510
7511
0
    if (fr_end_offset <= rx_offset) {
7512
0
      if (!new_strm && ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7513
0
        return NGTCP2_ERR_INTERNAL;
7514
0
      }
7515
7516
0
      return 0;
7517
0
    }
7518
7519
0
    if (strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_RECVED) {
7520
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7521
0
        return NGTCP2_ERR_INTERNAL;
7522
0
      }
7523
7524
0
      return 0;
7525
0
    }
7526
0
  }
7527
7528
0
  if (fr->offset <= rx_offset) {
7529
0
    size_t ncut = (size_t)(rx_offset - fr->offset);
7530
0
    uint64_t offset = rx_offset;
7531
0
    const uint8_t *data;
7532
0
    int fin;
7533
7534
0
    if (fr->datacnt) {
7535
0
      data = fr->data[0].base + ncut;
7536
0
      datalen -= ncut;
7537
7538
0
      rx_offset += datalen;
7539
0
      ngtcp2_strm_update_rx_offset(strm, rx_offset);
7540
0
    } else {
7541
0
      data = NULL;
7542
0
      datalen = 0;
7543
0
    }
7544
7545
0
    if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
7546
0
      return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
7547
0
    }
7548
7549
0
    fin = (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
7550
0
          rx_offset == strm->rx.last_offset;
7551
7552
0
    assert(fin || datalen);
7553
7554
0
    if (fin) {
7555
0
      sdflags |= NGTCP2_STREAM_DATA_FLAG_FIN;
7556
0
    }
7557
0
    if (!conn_is_tls_handshake_completed(conn)) {
7558
0
      sdflags |= NGTCP2_STREAM_DATA_FLAG_0RTT;
7559
0
    }
7560
0
    rv = conn_call_recv_stream_data(conn, strm, sdflags, offset, data,
7561
0
                                    (size_t)datalen);
7562
0
    if (rv != 0) {
7563
0
      return rv;
7564
0
    }
7565
7566
0
    rv = conn_emit_pending_stream_data(conn, strm, rx_offset);
7567
0
    if (rv != 0) {
7568
0
      return rv;
7569
0
    }
7570
0
  } else if (fr->datacnt && !(strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING)) {
7571
0
    nwrite = ngtcp2_strm_recv_reordering(strm, fr->data[0].base,
7572
0
                                         fr->data[0].len, fr->offset);
7573
0
    if (nwrite < 0) {
7574
0
      return (int)nwrite;
7575
0
    }
7576
7577
0
    if (nwrite == 0 && ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7578
0
      return NGTCP2_ERR_INTERNAL;
7579
0
    }
7580
0
  }
7581
0
  return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
7582
0
}
7583
7584
/*
7585
 * conn_reset_stream adds RESET_STREAM frame to the transmission
7586
 * queue.
7587
 *
7588
 * This function returns 0 if it succeeds, or one of the following
7589
 * negative error codes:
7590
 *
7591
 * NGTCP2_ERR_NOMEM
7592
 *     Out of memory.
7593
 */
7594
static int conn_reset_stream(ngtcp2_conn *conn, ngtcp2_strm *strm,
7595
0
                             uint64_t app_error_code) {
7596
0
  strm->flags |= NGTCP2_STRM_FLAG_SEND_RESET_STREAM;
7597
0
  strm->tx.reset_stream_app_error_code = app_error_code;
7598
7599
0
  if (ngtcp2_strm_is_tx_queued(strm)) {
7600
0
    return 0;
7601
0
  }
7602
7603
0
  strm->cycle = conn_tx_strmq_first_cycle(conn);
7604
7605
0
  return ngtcp2_conn_tx_strmq_push(conn, strm);
7606
0
}
7607
7608
/*
7609
 * conn_stop_sending adds STOP_SENDING frame to the transmission
7610
 * queue.
7611
 *
7612
 * This function returns 0 if it succeeds, or one of the following
7613
 * negative error codes:
7614
 *
7615
 * NGTCP2_ERR_NOMEM
7616
 *     Out of memory.
7617
 */
7618
static int conn_stop_sending(ngtcp2_conn *conn, ngtcp2_strm *strm,
7619
0
                             uint64_t app_error_code) {
7620
0
  strm->flags |= NGTCP2_STRM_FLAG_SEND_STOP_SENDING;
7621
0
  strm->tx.stop_sending_app_error_code = app_error_code;
7622
7623
0
  if (ngtcp2_strm_is_tx_queued(strm)) {
7624
0
    return 0;
7625
0
  }
7626
7627
0
  strm->cycle = conn_tx_strmq_first_cycle(conn);
7628
7629
0
  return ngtcp2_conn_tx_strmq_push(conn, strm);
7630
0
}
7631
7632
/*
7633
 * handle_max_remote_streams_extension extends
7634
 * |*punsent_max_remote_streams| by |n| if a condition allows it.
7635
 */
7636
static void
7637
handle_max_remote_streams_extension(uint64_t *punsent_max_remote_streams,
7638
0
                                    size_t n) {
7639
0
  if (
7640
0
#if SIZE_MAX == UINT64_MAX
7641
0
    NGTCP2_MAX_STREAMS < n ||
7642
0
#endif /* SIZE_MAX == UINT64_MAX */
7643
0
    *punsent_max_remote_streams > (uint64_t)(NGTCP2_MAX_STREAMS - n)) {
7644
0
    *punsent_max_remote_streams = NGTCP2_MAX_STREAMS;
7645
0
  } else {
7646
0
    *punsent_max_remote_streams += n;
7647
0
  }
7648
0
}
7649
7650
/*
7651
 * conn_recv_reset_stream is called when RESET_STREAM |fr| is
7652
 * received.
7653
 *
7654
 * This function returns 0 if it succeeds, or one of the following
7655
 * negative error codes:
7656
 *
7657
 * NGTCP2_ERR_STREAM_STATE
7658
 *     RESET_STREAM frame is received to the local stream which is not
7659
 *     initiated.
7660
 * NGTCP2_ERR_STREAM_LIMIT
7661
 *     RESET_STREAM frame has remote stream ID which is strictly
7662
 *     greater than the allowed limit.
7663
 * NGTCP2_ERR_PROTO
7664
 *     RESET_STREAM frame is received to the local unidirectional
7665
 *     stream
7666
 * NGTCP2_ERR_NOMEM
7667
 *     Out of memory.
7668
 * NGTCP2_ERR_CALLBACK_FAILURE
7669
 *     User-defined callback function failed.
7670
 * NGTCP2_ERR_FLOW_CONTROL
7671
 *     Flow control limit is violated; or the final size is beyond the
7672
 *     NGTCP2_MAX_VARINT.
7673
 * NGTCP2_ERR_FINAL_SIZE
7674
 *     The final offset is strictly larger than it is permitted.
7675
 * NGTCP2_ERR_INTERNAL
7676
 *     Suspicious remote endpoint activity exceeded threshold.
7677
 */
7678
static int conn_recv_reset_stream(ngtcp2_conn *conn,
7679
                                  const ngtcp2_reset_stream *fr,
7680
0
                                  ngtcp2_tstamp ts) {
7681
0
  ngtcp2_strm *strm;
7682
0
  int local_stream = conn_local_stream(conn, fr->stream_id);
7683
0
  int bidi = bidi_stream(fr->stream_id);
7684
0
  uint64_t datalen;
7685
0
  ngtcp2_idtr *idtr;
7686
0
  int rv;
7687
7688
  /* TODO share this piece of code */
7689
0
  if (bidi) {
7690
0
    if (local_stream) {
7691
0
      if (conn->local.bidi.next_stream_id <= fr->stream_id) {
7692
0
        return NGTCP2_ERR_STREAM_STATE;
7693
0
      }
7694
0
    } else if (conn->remote.bidi.max_streams <
7695
0
               ngtcp2_ord_stream_id(fr->stream_id)) {
7696
0
      return NGTCP2_ERR_STREAM_LIMIT;
7697
0
    }
7698
7699
0
    idtr = &conn->remote.bidi.idtr;
7700
0
  } else {
7701
0
    if (local_stream) {
7702
0
      return NGTCP2_ERR_PROTO;
7703
0
    }
7704
0
    if (conn->remote.uni.max_streams < ngtcp2_ord_stream_id(fr->stream_id)) {
7705
0
      return NGTCP2_ERR_STREAM_LIMIT;
7706
0
    }
7707
7708
0
    idtr = &conn->remote.uni.idtr;
7709
0
  }
7710
7711
0
  if (NGTCP2_MAX_VARINT < fr->final_size) {
7712
0
    return NGTCP2_ERR_FLOW_CONTROL;
7713
0
  }
7714
7715
0
  strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
7716
0
  if (strm == NULL) {
7717
0
    if (local_stream) {
7718
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7719
0
        return NGTCP2_ERR_INTERNAL;
7720
0
      }
7721
7722
0
      return 0;
7723
0
    }
7724
7725
0
    rv = ngtcp2_idtr_open(idtr, fr->stream_id);
7726
0
    if (rv != 0) {
7727
0
      if (ngtcp2_err_is_fatal(rv)) {
7728
0
        return rv;
7729
0
      }
7730
0
      assert(rv == NGTCP2_ERR_STREAM_IN_USE);
7731
7732
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7733
0
        return NGTCP2_ERR_INTERNAL;
7734
0
      }
7735
7736
0
      return 0;
7737
0
    }
7738
7739
0
    if (conn_initial_stream_rx_offset(conn, fr->stream_id) < fr->final_size ||
7740
0
        conn_max_data_violated(conn, fr->final_size)) {
7741
0
      return NGTCP2_ERR_FLOW_CONTROL;
7742
0
    }
7743
7744
    /* Stream is reset before we create ngtcp2_strm object. */
7745
0
    strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
7746
0
    if (strm == NULL) {
7747
0
      return NGTCP2_ERR_NOMEM;
7748
0
    }
7749
0
    rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
7750
0
    if (rv != 0) {
7751
0
      ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
7752
0
      return rv;
7753
0
    }
7754
7755
0
    rv = conn_call_stream_open(conn, strm);
7756
0
    if (rv != 0) {
7757
0
      return rv;
7758
0
    }
7759
0
  }
7760
7761
0
  if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD)) {
7762
0
    if (strm->rx.last_offset != fr->final_size) {
7763
0
      return NGTCP2_ERR_FINAL_SIZE;
7764
0
    }
7765
0
  } else if (strm->rx.last_offset > fr->final_size) {
7766
0
    return NGTCP2_ERR_FINAL_SIZE;
7767
0
  }
7768
7769
0
  if (strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_RECVED) {
7770
0
    if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7771
0
      return NGTCP2_ERR_INTERNAL;
7772
0
    }
7773
7774
0
    return 0;
7775
0
  }
7776
7777
0
  if (strm->rx.max_offset < fr->final_size) {
7778
0
    return NGTCP2_ERR_FLOW_CONTROL;
7779
0
  }
7780
7781
0
  datalen = fr->final_size - strm->rx.last_offset;
7782
7783
0
  if (conn_max_data_violated(conn, datalen)) {
7784
0
    return NGTCP2_ERR_FLOW_CONTROL;
7785
0
  }
7786
7787
0
  rv = conn_call_stream_reset(conn, fr->stream_id, fr->final_size,
7788
0
                              fr->app_error_code, strm->stream_user_data);
7789
0
  if (rv != 0) {
7790
0
    return rv;
7791
0
  }
7792
7793
  /* Extend connection flow control window for the amount of data
7794
     which are not passed to application. */
7795
0
  if (!(strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING)) {
7796
0
    ngtcp2_conn_extend_max_offset(conn, strm->rx.last_offset -
7797
0
                                          ngtcp2_strm_rx_offset(strm));
7798
0
  }
7799
7800
0
  conn->rx.offset += datalen;
7801
0
  ngtcp2_conn_extend_max_offset(conn, datalen);
7802
7803
0
  strm->rx.last_offset = fr->final_size;
7804
0
  strm->flags |=
7805
0
    NGTCP2_STRM_FLAG_SHUT_RD | NGTCP2_STRM_FLAG_RESET_STREAM_RECVED;
7806
7807
0
  ngtcp2_strm_set_app_error_code(strm, fr->app_error_code);
7808
7809
0
  return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
7810
0
}
7811
7812
/*
7813
 * conn_recv_stop_sending is called when STOP_SENDING |fr| is received.
7814
 *
7815
 * This function returns 0 if it succeeds, or one of the following
7816
 * negative error codes:
7817
 *
7818
 * NGTCP2_ERR_STREAM_STATE
7819
 *     STOP_SENDING frame is received for a local stream which is not
7820
 *     initiated; or STOP_SENDING frame is received for a local
7821
 *     unidirectional stream.
7822
 * NGTCP2_ERR_STREAM_LIMIT
7823
 *     STOP_SENDING frame has remote stream ID which is strictly
7824
 *     greater than the allowed limit.
7825
 * NGTCP2_ERR_NOMEM
7826
 *     Out of memory.
7827
 * NGTCP2_ERR_CALLBACK_FAILURE
7828
 *     User-defined callback function failed.
7829
 * NGTCP2_ERR_INTERNAL
7830
 *     Suspicious remote endpoint activity exceeded threshold.
7831
 */
7832
static int conn_recv_stop_sending(ngtcp2_conn *conn,
7833
                                  const ngtcp2_stop_sending *fr,
7834
0
                                  ngtcp2_tstamp ts) {
7835
0
  int rv;
7836
0
  ngtcp2_strm *strm;
7837
0
  ngtcp2_idtr *idtr;
7838
0
  int local_stream = conn_local_stream(conn, fr->stream_id);
7839
0
  int bidi = bidi_stream(fr->stream_id);
7840
7841
0
  if (bidi) {
7842
0
    if (local_stream) {
7843
0
      if (conn->local.bidi.next_stream_id <= fr->stream_id) {
7844
0
        return NGTCP2_ERR_STREAM_STATE;
7845
0
      }
7846
0
    } else if (conn->remote.bidi.max_streams <
7847
0
               ngtcp2_ord_stream_id(fr->stream_id)) {
7848
0
      return NGTCP2_ERR_STREAM_LIMIT;
7849
0
    }
7850
7851
0
    idtr = &conn->remote.bidi.idtr;
7852
0
  } else {
7853
0
    if (!local_stream || conn->local.uni.next_stream_id <= fr->stream_id) {
7854
0
      return NGTCP2_ERR_STREAM_STATE;
7855
0
    }
7856
7857
0
    idtr = &conn->remote.uni.idtr;
7858
0
  }
7859
7860
0
  strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
7861
0
  if (strm == NULL) {
7862
0
    if (local_stream) {
7863
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7864
0
        return NGTCP2_ERR_INTERNAL;
7865
0
      }
7866
7867
0
      return 0;
7868
0
    }
7869
0
    rv = ngtcp2_idtr_open(idtr, fr->stream_id);
7870
0
    if (rv != 0) {
7871
0
      if (ngtcp2_err_is_fatal(rv)) {
7872
0
        return rv;
7873
0
      }
7874
0
      assert(rv == NGTCP2_ERR_STREAM_IN_USE);
7875
7876
0
      if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7877
0
        return NGTCP2_ERR_INTERNAL;
7878
0
      }
7879
7880
0
      return 0;
7881
0
    }
7882
7883
    /* STOP_SENDING frame is received before we create ngtcp2_strm
7884
       object. */
7885
0
    strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
7886
0
    if (strm == NULL) {
7887
0
      return NGTCP2_ERR_NOMEM;
7888
0
    }
7889
0
    rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
7890
0
    if (rv != 0) {
7891
0
      ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
7892
0
      return rv;
7893
0
    }
7894
7895
0
    rv = conn_call_stream_open(conn, strm);
7896
0
    if (rv != 0) {
7897
0
      return rv;
7898
0
    }
7899
0
  }
7900
7901
0
  if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING_RECVED) {
7902
0
    if (ngtcp2_ratelim_drain(&conn->glitch_rlim, 1, ts) != 0) {
7903
0
      return NGTCP2_ERR_INTERNAL;
7904
0
    }
7905
7906
0
    return 0;
7907
0
  }
7908
7909
0
  ngtcp2_strm_set_app_error_code(strm, fr->app_error_code);
7910
7911
  /* No RESET_STREAM is required if we have sent FIN and all data have
7912
     been acknowledged. */
7913
0
  if (!ngtcp2_strm_is_all_tx_data_fin_acked(strm) &&
7914
0
      !(strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM)) {
7915
0
    strm->flags |= NGTCP2_STRM_FLAG_RESET_STREAM;
7916
7917
0
    rv = conn_reset_stream(conn, strm, fr->app_error_code);
7918
0
    if (rv != 0) {
7919
0
      return rv;
7920
0
    }
7921
0
  }
7922
7923
0
  strm->flags |=
7924
0
    NGTCP2_STRM_FLAG_SHUT_WR | NGTCP2_STRM_FLAG_STOP_SENDING_RECVED;
7925
7926
0
  ngtcp2_strm_streamfrq_clear(strm);
7927
7928
0
  return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
7929
0
}
7930
7931
/*
7932
 * check_stateless_reset returns nonzero if Stateless Reset |sr|
7933
 * coming via |path| is valid against |dcid|.
7934
 */
7935
static int check_stateless_reset(const ngtcp2_dcid *dcid,
7936
                                 const ngtcp2_path *path,
7937
0
                                 const ngtcp2_pkt_stateless_reset2 *sr) {
7938
0
  return ngtcp2_dcid_verify_stateless_reset_token(dcid, path, &sr->token) == 0;
7939
0
}
7940
7941
/*
7942
 * conn_on_stateless_reset decodes Stateless Reset from the buffer
7943
 * pointed by |payload| whose length is |payloadlen|.  |payload|
7944
 * should start after first byte of packet.
7945
 *
7946
 * If Stateless Reset is decoded, and the Stateless Reset Token is
7947
 * validated, the connection is closed.
7948
 *
7949
 * This function returns 0 if it succeeds, or one of the following
7950
 * negative error codes:
7951
 *
7952
 * NGTCP2_ERR_INVALID_ARGUMENT
7953
 *     Could not decode Stateless Reset; or Stateless Reset Token does
7954
 *     not match; or No stateless reset token is available.
7955
 * NGTCP2_ERR_CALLBACK_FAILURE
7956
 *     User callback failed.
7957
 */
7958
static int conn_on_stateless_reset(ngtcp2_conn *conn, const ngtcp2_path *path,
7959
0
                                   const uint8_t *payload, size_t payloadlen) {
7960
0
  int rv;
7961
0
  ngtcp2_pv *pv = conn->pv;
7962
0
  ngtcp2_pkt_stateless_reset2 sr;
7963
7964
0
  rv = ngtcp2_pkt_decode_stateless_reset(&sr, payload, payloadlen);
7965
0
  if (rv != 0) {
7966
0
    return rv;
7967
0
  }
7968
7969
0
  if (!check_stateless_reset(&conn->dcid.current, path, &sr) &&
7970
0
      (!pv || (!check_stateless_reset(&pv->dcid, path, &sr) &&
7971
0
               (!(pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) ||
7972
0
                !check_stateless_reset(&pv->fallback_dcid, path, &sr))))) {
7973
0
    rv = ngtcp2_dcidtr_verify_stateless_reset(&conn->dcid.dtr, path, &sr.token);
7974
0
    if (rv != 0) {
7975
0
      return rv;
7976
0
    }
7977
0
  }
7978
7979
0
  conn->state = NGTCP2_CS_DRAINING;
7980
7981
0
  ngtcp2_log_rx_sr(&conn->log, &sr);
7982
7983
0
  ngtcp2_qlog_stateless_reset_pkt_received(&conn->qlog, &sr);
7984
7985
0
  return conn_call_recv_stateless_reset(conn, &sr);
7986
0
}
7987
7988
/*
7989
 * conn_recv_max_streams processes the incoming MAX_STREAMS frame
7990
 * |fr|.
7991
 *
7992
 * This function returns 0 if it succeeds, or one of the following
7993
 * negative error codes:
7994
 *
7995
 * NGTCP2_ERR_CALLBACK_FAILURE
7996
 *     User callback failed.
7997
 * NGTCP2_ERR_FRAME_ENCODING
7998
 *     The maximum streams field exceeds the maximum value.
7999
 */
8000
static int conn_recv_max_streams(ngtcp2_conn *conn,
8001
0
                                 const ngtcp2_max_streams *fr) {
8002
0
  uint64_t n;
8003
8004
0
  if (fr->max_streams > NGTCP2_MAX_STREAMS) {
8005
0
    return NGTCP2_ERR_FRAME_ENCODING;
8006
0
  }
8007
8008
0
  n = ngtcp2_min_uint64(fr->max_streams, NGTCP2_MAX_STREAMS);
8009
8010
0
  if (fr->type == NGTCP2_FRAME_MAX_STREAMS_BIDI) {
8011
0
    if (conn->local.bidi.max_streams < n) {
8012
0
      conn->local.bidi.max_streams = n;
8013
0
      return conn_call_extend_max_local_streams_bidi(conn, n);
8014
0
    }
8015
0
    return 0;
8016
0
  }
8017
8018
0
  if (conn->local.uni.max_streams < n) {
8019
0
    conn->local.uni.max_streams = n;
8020
0
    return conn_call_extend_max_local_streams_uni(conn, n);
8021
0
  }
8022
0
  return 0;
8023
0
}
8024
8025
/*
8026
 * conn_recv_new_connection_id processes the incoming
8027
 * NEW_CONNECTION_ID frame |fr|.
8028
 *
8029
 * This function returns 0 if it succeeds, or one of the following
8030
 * negative error codes:
8031
 *
8032
 * NGTCP2_ERR_PROTO
8033
 *     |fr| has the duplicated sequence number with different CID or
8034
 *     token; or DCID is zero-length.
8035
 */
8036
static int conn_recv_new_connection_id(ngtcp2_conn *conn,
8037
0
                                       const ngtcp2_new_connection_id *fr) {
8038
0
  size_t len;
8039
0
  ngtcp2_pv *pv = conn->pv;
8040
0
  int rv;
8041
0
  int found = 0;
8042
0
  size_t extra_dcid = 0;
8043
8044
0
  if (conn->dcid.current.cid.datalen == 0) {
8045
0
    return NGTCP2_ERR_PROTO;
8046
0
  }
8047
8048
0
  if (fr->retire_prior_to > fr->seq) {
8049
0
    return NGTCP2_ERR_FRAME_ENCODING;
8050
0
  }
8051
8052
0
  rv = ngtcp2_dcid_verify_uniqueness(&conn->dcid.current, fr->seq, &fr->cid,
8053
0
                                     &fr->token);
8054
0
  if (rv != 0) {
8055
0
    return rv;
8056
0
  }
8057
0
  if (ngtcp2_cid_eq(&conn->dcid.current.cid, &fr->cid)) {
8058
0
    found = 1;
8059
0
  }
8060
8061
0
  if (pv) {
8062
0
    rv =
8063
0
      ngtcp2_dcid_verify_uniqueness(&pv->dcid, fr->seq, &fr->cid, &fr->token);
8064
0
    if (rv != 0) {
8065
0
      return rv;
8066
0
    }
8067
0
    if (ngtcp2_cid_eq(&pv->dcid.cid, &fr->cid)) {
8068
0
      found = 1;
8069
0
    }
8070
0
  }
8071
8072
0
  rv = ngtcp2_dcidtr_verify_token_uniqueness(&conn->dcid.dtr, &found, fr->seq,
8073
0
                                             &fr->cid, &fr->token);
8074
0
  if (rv != 0) {
8075
0
    return rv;
8076
0
  }
8077
8078
0
  if (conn->dcid.retire_prior_to < fr->retire_prior_to) {
8079
0
    conn->dcid.retire_prior_to = fr->retire_prior_to;
8080
8081
0
    rv = ngtcp2_dcidtr_retire_inactive_dcid_prior_to(
8082
0
      &conn->dcid.dtr, fr->retire_prior_to, dcidtr_on_retire, conn);
8083
0
    if (rv != 0) {
8084
0
      return rv;
8085
0
    }
8086
0
  } else if (fr->seq < conn->dcid.retire_prior_to) {
8087
    /* If packets are reordered, we might have retire_prior_to which
8088
       is larger than fr->seq.
8089
8090
       A malicious peer might send crafted NEW_CONNECTION_ID to force
8091
       local endpoint to create lots of RETIRE_CONNECTION_ID frames.
8092
       For example, a peer might send seq = 50000 and retire_prior_to
8093
       = 50000.  Then send NEW_CONNECTION_ID frames with seq <
8094
       50000. */
8095
0
    if (ngtcp2_dcidtr_check_retired_seq_tracked(&conn->dcid.dtr, fr->seq)) {
8096
0
      return 0;
8097
0
    }
8098
8099
0
    rv = ngtcp2_dcidtr_track_retired_seq(&conn->dcid.dtr, fr->seq);
8100
0
    if (rv != 0) {
8101
0
      return rv;
8102
0
    }
8103
8104
0
    return conn_enqueue_retire_connection_id(conn, fr->seq);
8105
0
  }
8106
8107
0
  if (found) {
8108
0
    return 0;
8109
0
  }
8110
8111
0
  if (ngtcp2_gaptr_is_pushed(&conn->dcid.seqgap, fr->seq, 1)) {
8112
0
    return 0;
8113
0
  }
8114
8115
0
  rv = ngtcp2_gaptr_push(&conn->dcid.seqgap, fr->seq, 1);
8116
0
  if (rv != 0) {
8117
0
    return rv;
8118
0
  }
8119
8120
0
  if (ngtcp2_ksl_len(&conn->dcid.seqgap.gap) > 32) {
8121
0
    ngtcp2_gaptr_drop_first_gap(&conn->dcid.seqgap);
8122
0
  }
8123
8124
0
  len = ngtcp2_dcidtr_inactive_len(&conn->dcid.dtr);
8125
8126
0
  if (conn->dcid.current.seq >= conn->dcid.retire_prior_to) {
8127
0
    ++extra_dcid;
8128
0
  }
8129
0
  if (pv) {
8130
0
    if (pv->dcid.seq != conn->dcid.current.seq &&
8131
0
        pv->dcid.seq >= conn->dcid.retire_prior_to) {
8132
0
      ++extra_dcid;
8133
0
    }
8134
0
    if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8135
0
        pv->fallback_dcid.seq != conn->dcid.current.seq &&
8136
0
        pv->fallback_dcid.seq >= conn->dcid.retire_prior_to) {
8137
0
      ++extra_dcid;
8138
0
    }
8139
0
  }
8140
8141
0
  if (conn->local.transport_params.active_connection_id_limit <=
8142
0
      len + extra_dcid) {
8143
0
    return NGTCP2_ERR_CONNECTION_ID_LIMIT;
8144
0
  }
8145
8146
0
  if (len >= NGTCP2_DCIDTR_MAX_UNUSED_DCID_SIZE) {
8147
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "too many connection ID");
8148
0
    return 0;
8149
0
  }
8150
8151
0
  ngtcp2_dcidtr_push_unused(&conn->dcid.dtr, fr->seq, &fr->cid, &fr->token);
8152
8153
0
  return 0;
8154
0
}
8155
8156
/*
8157
 * conn_post_process_recv_new_connection_id handles retirement request
8158
 * of active DCIDs.
8159
 *
8160
 * This function returns 0 if it succeeds, or one of the following
8161
 * negative error codes:
8162
 *
8163
 * NGTCP2_ERR_NOMEM
8164
 *     Out of memory.
8165
 * NGTCP2_ERR_CALLBACK_FAILURE
8166
 *     User-defined callback function failed.
8167
 */
8168
static int conn_post_process_recv_new_connection_id(ngtcp2_conn *conn,
8169
0
                                                    ngtcp2_tstamp ts) {
8170
0
  ngtcp2_pv *pv = conn->pv;
8171
0
  ngtcp2_dcid dcid;
8172
0
  int rv;
8173
8174
0
  if (conn->dcid.current.seq < conn->dcid.retire_prior_to) {
8175
0
    if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
8176
0
      return 0;
8177
0
    }
8178
8179
0
    rv = conn_retire_active_dcid(conn, &conn->dcid.current, ts);
8180
0
    if (rv != 0) {
8181
0
      return rv;
8182
0
    }
8183
8184
0
    ngtcp2_dcidtr_pop_unused_cid_token(&conn->dcid.dtr, &dcid);
8185
8186
0
    if (pv) {
8187
0
      if (conn->dcid.current.seq == pv->dcid.seq) {
8188
0
        ngtcp2_dcid_copy_cid_token(&pv->dcid, &dcid);
8189
0
      }
8190
0
      if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8191
0
          conn->dcid.current.seq == pv->fallback_dcid.seq) {
8192
0
        ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, &dcid);
8193
0
      }
8194
0
    }
8195
8196
0
    ngtcp2_dcid_copy_cid_token(&conn->dcid.current, &dcid);
8197
8198
0
    rv = conn_call_activate_dcid(conn, &conn->dcid.current);
8199
0
    if (rv != 0) {
8200
0
      return rv;
8201
0
    }
8202
0
  }
8203
8204
0
  if (pv) {
8205
0
    if (pv->dcid.seq < conn->dcid.retire_prior_to) {
8206
0
      if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
8207
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
8208
0
                        "path migration is aborted because connection ID is"
8209
0
                        "retired and no unused connection ID is available");
8210
8211
0
        return conn_abort_pv(conn, ts);
8212
0
      }
8213
8214
0
      rv = conn_retire_active_dcid(conn, &pv->dcid, ts);
8215
0
      if (rv != 0) {
8216
0
        return rv;
8217
0
      }
8218
8219
0
      ngtcp2_dcidtr_pop_unused_cid_token(&conn->dcid.dtr, &dcid);
8220
8221
0
      if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8222
0
          pv->dcid.seq == pv->fallback_dcid.seq) {
8223
0
        ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, &dcid);
8224
0
      }
8225
8226
0
      ngtcp2_dcid_copy_cid_token(&pv->dcid, &dcid);
8227
8228
0
      rv = conn_call_activate_dcid(conn, &pv->dcid);
8229
0
      if (rv != 0) {
8230
0
        return rv;
8231
0
      }
8232
0
    }
8233
0
    if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8234
0
        pv->fallback_dcid.seq < conn->dcid.retire_prior_to) {
8235
0
      if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
8236
        /* Now we have no fallback dcid. */
8237
0
        return conn_abort_pv(conn, ts);
8238
0
      }
8239
8240
0
      rv = conn_retire_active_dcid(conn, &pv->fallback_dcid, ts);
8241
0
      if (rv != 0) {
8242
0
        return rv;
8243
0
      }
8244
8245
0
      ngtcp2_dcidtr_pop_unused_cid_token(&conn->dcid.dtr, &dcid);
8246
0
      ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, &dcid);
8247
8248
0
      rv = conn_call_activate_dcid(conn, &pv->fallback_dcid);
8249
0
      if (rv != 0) {
8250
0
        return rv;
8251
0
      }
8252
0
    }
8253
0
  }
8254
8255
0
  return 0;
8256
0
}
8257
8258
/*
8259
 * conn_recv_retire_connection_id processes the incoming
8260
 * RETIRE_CONNECTION_ID frame |fr|.  |hd| is a packet header which
8261
 * |fr| is included.
8262
 *
8263
 * This function returns 0 if it succeeds, or one of the following
8264
 * negative error codes:
8265
 *
8266
 * NGTCP2_ERR_NOMEM
8267
 *     Out of memory.
8268
 * NGTCP2_ERR_PROTO
8269
 *     SCID is zero-length.
8270
 * NGTCP2_ERR_FRAME_ENCODING
8271
 *     Attempt to retire CID which is used as DCID to send this frame.
8272
 */
8273
static int conn_recv_retire_connection_id(ngtcp2_conn *conn,
8274
                                          const ngtcp2_pkt_hd *hd,
8275
                                          const ngtcp2_retire_connection_id *fr,
8276
0
                                          ngtcp2_tstamp ts) {
8277
0
  ngtcp2_ksl_it it;
8278
0
  ngtcp2_scid *scid;
8279
8280
0
  if (conn->oscid.datalen == 0 || conn->scid.last_seq < fr->seq) {
8281
0
    return NGTCP2_ERR_PROTO;
8282
0
  }
8283
8284
0
  for (it = ngtcp2_ksl_begin(&conn->scid.set); !ngtcp2_ksl_it_end(&it);
8285
0
       ngtcp2_ksl_it_next(&it)) {
8286
0
    scid = ngtcp2_ksl_it_get(&it);
8287
0
    if (scid->seq == fr->seq) {
8288
0
      if (ngtcp2_cid_eq(&scid->cid, &hd->dcid)) {
8289
0
        return NGTCP2_ERR_PROTO;
8290
0
      }
8291
8292
0
      if (!(scid->flags & NGTCP2_SCID_FLAG_RETIRED)) {
8293
0
        scid->flags |= NGTCP2_SCID_FLAG_RETIRED;
8294
0
        ++conn->scid.num_retired;
8295
0
      }
8296
8297
0
      if (scid->pe.index != NGTCP2_PQ_BAD_INDEX) {
8298
0
        ngtcp2_pq_remove(&conn->scid.used, &scid->pe);
8299
0
        scid->pe.index = NGTCP2_PQ_BAD_INDEX;
8300
0
      }
8301
8302
0
      scid->retired_ts = ts;
8303
8304
0
      return ngtcp2_pq_push(&conn->scid.used, &scid->pe);
8305
0
    }
8306
0
  }
8307
8308
0
  return 0;
8309
0
}
8310
8311
/*
8312
 * conn_recv_new_token processes the incoming NEW_TOKEN frame |fr|.
8313
 *
8314
 * This function returns 0 if it succeeds, or one of the following
8315
 * negative error codes:
8316
 *
8317
 * NGTCP2_ERR_FRAME_ENCODING
8318
 *     Token is empty
8319
 * NGTCP2_ERR_PROTO:
8320
 *     Server received NEW_TOKEN.
8321
 */
8322
0
static int conn_recv_new_token(ngtcp2_conn *conn, const ngtcp2_new_token *fr) {
8323
0
  if (conn->server) {
8324
0
    return NGTCP2_ERR_PROTO;
8325
0
  }
8326
8327
0
  if (fr->tokenlen == 0) {
8328
0
    return NGTCP2_ERR_FRAME_ENCODING;
8329
0
  }
8330
8331
0
  return conn_call_recv_new_token(conn, fr->token, fr->tokenlen);
8332
0
}
8333
8334
/*
8335
 * conn_recv_streams_blocked_bidi processes the incoming
8336
 * STREAMS_BLOCKED (0x16).
8337
 *
8338
 * This function returns 0 if it succeeds, or one of the following
8339
 * negative error codes:
8340
 *
8341
 * NGTCP2_ERR_FRAME_ENCODING
8342
 *     Maximum Streams is larger than advertised value.
8343
 */
8344
static int conn_recv_streams_blocked_bidi(ngtcp2_conn *conn,
8345
0
                                          ngtcp2_streams_blocked *fr) {
8346
0
  if (fr->max_streams > conn->remote.bidi.max_streams) {
8347
0
    return NGTCP2_ERR_FRAME_ENCODING;
8348
0
  }
8349
8350
0
  return 0;
8351
0
}
8352
8353
/*
8354
 * conn_recv_streams_blocked_uni processes the incoming
8355
 * STREAMS_BLOCKED (0x17).
8356
 *
8357
 * This function returns 0 if it succeeds, or one of the following
8358
 * negative error codes:
8359
 *
8360
 * NGTCP2_ERR_FRAME_ENCODING
8361
 *     Maximum Streams is larger than advertised value.
8362
 */
8363
static int conn_recv_streams_blocked_uni(ngtcp2_conn *conn,
8364
0
                                         ngtcp2_streams_blocked *fr) {
8365
0
  if (fr->max_streams > conn->remote.uni.max_streams) {
8366
0
    return NGTCP2_ERR_FRAME_ENCODING;
8367
0
  }
8368
8369
0
  return 0;
8370
0
}
8371
8372
/*
8373
 * conn_recv_stream_data_blocked processes the incoming
8374
 * STREAM_DATA_BLOCKED frame |fr|.
8375
 *
8376
 * This function returns 0 if it succeeds, or one of the following
8377
 * negative error codes:
8378
 *
8379
 * NGTCP2_ERR_STREAM_STATE
8380
 *     STREAM_DATA_BLOCKED is received for a local stream which is not
8381
 *     initiated; or it is received for a local unidirectional stream.
8382
 * NGTCP2_ERR_STREAM_LIMIT
8383
 *     STREAM_DATA_BLOCKED has remote stream ID which is strictly
8384
 *     greater than the allowed limit.
8385
 * NGTCP2_ERR_FLOW_CONTROL
8386
 *     STREAM_DATA_BLOCKED frame violates flow control limit.
8387
 * NGTCP2_ERR_FINAL_SIZE
8388
 *     The offset is strictly larger than it is permitted.
8389
 * NGTCP2_ERR_NOMEM
8390
 *     Out of memory.
8391
 * NGTCP2_ERR_CALLBACK_FAILURE
8392
 *     User-defined callback function failed.
8393
 */
8394
static int conn_recv_stream_data_blocked(ngtcp2_conn *conn,
8395
0
                                         ngtcp2_stream_data_blocked *fr) {
8396
0
  int rv;
8397
0
  ngtcp2_strm *strm;
8398
0
  ngtcp2_idtr *idtr;
8399
0
  int local_stream = conn_local_stream(conn, fr->stream_id);
8400
0
  int bidi = bidi_stream(fr->stream_id);
8401
0
  uint64_t datalen;
8402
8403
0
  if (bidi) {
8404
0
    if (local_stream) {
8405
0
      if (conn->local.bidi.next_stream_id <= fr->stream_id) {
8406
0
        return NGTCP2_ERR_STREAM_STATE;
8407
0
      }
8408
0
    } else if (conn->remote.bidi.max_streams <
8409
0
               ngtcp2_ord_stream_id(fr->stream_id)) {
8410
0
      return NGTCP2_ERR_STREAM_LIMIT;
8411
0
    }
8412
8413
0
    idtr = &conn->remote.bidi.idtr;
8414
0
  } else {
8415
0
    if (local_stream) {
8416
0
      return NGTCP2_ERR_STREAM_STATE;
8417
0
    }
8418
0
    if (conn->remote.uni.max_streams < ngtcp2_ord_stream_id(fr->stream_id)) {
8419
0
      return NGTCP2_ERR_STREAM_LIMIT;
8420
0
    }
8421
8422
0
    idtr = &conn->remote.uni.idtr;
8423
0
  }
8424
8425
0
  strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
8426
0
  if (strm == NULL) {
8427
0
    if (local_stream) {
8428
0
      return 0;
8429
0
    }
8430
8431
0
    rv = ngtcp2_idtr_open(idtr, fr->stream_id);
8432
0
    if (rv != 0) {
8433
0
      if (ngtcp2_err_is_fatal(rv)) {
8434
0
        return rv;
8435
0
      }
8436
0
      assert(rv == NGTCP2_ERR_STREAM_IN_USE);
8437
0
      return 0;
8438
0
    }
8439
8440
    /* Frame is received before we create ngtcp2_strm object. */
8441
0
    strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
8442
0
    if (strm == NULL) {
8443
0
      return NGTCP2_ERR_NOMEM;
8444
0
    }
8445
0
    rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
8446
0
    if (rv != 0) {
8447
0
      ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
8448
0
      return rv;
8449
0
    }
8450
8451
0
    if (!bidi) {
8452
0
      ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_WR);
8453
0
      strm->flags |= NGTCP2_STRM_FLAG_FIN_ACKED;
8454
0
    }
8455
8456
0
    rv = conn_call_stream_open(conn, strm);
8457
0
    if (rv != 0) {
8458
0
      return rv;
8459
0
    }
8460
0
  }
8461
8462
0
  if (strm->rx.max_offset < fr->offset) {
8463
0
    return NGTCP2_ERR_FLOW_CONTROL;
8464
0
  }
8465
8466
0
  if (fr->offset <= strm->rx.last_offset) {
8467
0
    return 0;
8468
0
  }
8469
8470
0
  if (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) {
8471
0
    return NGTCP2_ERR_FINAL_SIZE;
8472
0
  }
8473
8474
0
  datalen = fr->offset - strm->rx.last_offset;
8475
0
  if (datalen) {
8476
0
    if (conn_max_data_violated(conn, datalen)) {
8477
0
      return NGTCP2_ERR_FLOW_CONTROL;
8478
0
    }
8479
8480
0
    conn->rx.offset += datalen;
8481
8482
0
    if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
8483
0
      ngtcp2_conn_extend_max_offset(conn, datalen);
8484
0
    }
8485
0
  }
8486
8487
0
  strm->rx.last_offset = fr->offset;
8488
8489
0
  return 0;
8490
0
}
8491
8492
/*
8493
 * conn_recv_data_blocked processes the incoming DATA_BLOCKED frame
8494
 * |fr|.
8495
 *
8496
 * This function returns 0 if it succeeds, or one of the following
8497
 * negative error codes:
8498
 *
8499
 * NGTCP2_ERR_FLOW_CONTROL
8500
 *     It violates connection-level flow control limit.
8501
 */
8502
0
static int conn_recv_data_blocked(ngtcp2_conn *conn, ngtcp2_data_blocked *fr) {
8503
0
  if (conn->rx.max_offset < fr->offset) {
8504
0
    return NGTCP2_ERR_FLOW_CONTROL;
8505
0
  }
8506
8507
0
  return 0;
8508
0
}
8509
8510
/*
8511
 * conn_select_preferred_addr asks a client application to select a
8512
 * server address from preferred addresses received from server.  If a
8513
 * client chooses the address, path validation will start.
8514
 *
8515
 * This function returns 0 if it succeeds, or one of the following
8516
 * negative error codes:
8517
 *
8518
 * NGTCP2_ERR_NOMEM
8519
 *     Out of memory.
8520
 * NGTCP2_ERR_CALLBACK_FAILURE
8521
 *     User-defined callback function failed.
8522
 */
8523
0
static int conn_select_preferred_addr(ngtcp2_conn *conn) {
8524
0
  ngtcp2_path_storage ps;
8525
0
  int rv;
8526
0
  ngtcp2_pv *pv;
8527
0
  ngtcp2_dcid dcid;
8528
8529
0
  if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
8530
0
    return 0;
8531
0
  }
8532
8533
0
  ngtcp2_path_storage_zero(&ps);
8534
0
  ngtcp2_addr_copy(&ps.path.local, &conn->dcid.current.ps.path.local);
8535
8536
0
  rv = conn_call_select_preferred_addr(conn, &ps.path);
8537
0
  if (rv != 0) {
8538
0
    return rv;
8539
0
  }
8540
8541
0
  if (ngtcp2_addr_empty(&ps.path.remote) ||
8542
0
      ngtcp2_addr_eq(&conn->dcid.current.ps.path.remote, &ps.path.remote)) {
8543
0
    return 0;
8544
0
  }
8545
8546
0
  assert(conn->pv == NULL);
8547
8548
0
  ngtcp2_dcidtr_pop_unused(&conn->dcid.dtr, &dcid);
8549
0
  ngtcp2_dcid_set_path(&dcid, &ps.path);
8550
8551
0
  rv = ngtcp2_pv_new(&pv, &dcid, conn_compute_pv_timeout(conn),
8552
0
                     NGTCP2_PV_FLAG_PREFERRED_ADDR, &conn->log, conn->mem);
8553
0
  if (rv != 0) {
8554
0
    return rv;
8555
0
  }
8556
8557
0
  conn->pv = pv;
8558
8559
0
  rv = conn_call_activate_dcid(conn, &pv->dcid);
8560
0
  if (rv != 0) {
8561
0
    return rv;
8562
0
  }
8563
8564
0
  return conn_call_begin_path_validation(conn, conn->pv);
8565
0
}
8566
8567
/*
8568
 * conn_recv_handshake_done processes the incoming HANDSHAKE_DONE
8569
 * frame |fr|.
8570
 *
8571
 * This function returns 0 if it succeeds, or one of the following
8572
 * negative error codes:
8573
 *
8574
 * NGTCP2_ERR_PROTO
8575
 *     Server received HANDSHAKE_DONE frame.
8576
 * NGTCP2_ERR_NOMEM
8577
 *     Out of memory.
8578
 * NGTCP2_ERR_CALLBACK_FAILURE
8579
 *     User-defined callback function failed.
8580
 */
8581
0
static int conn_recv_handshake_done(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
8582
0
  int rv;
8583
8584
0
  if (conn->server) {
8585
0
    return NGTCP2_ERR_PROTO;
8586
0
  }
8587
8588
0
  if (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) {
8589
0
    return 0;
8590
0
  }
8591
8592
0
  conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED |
8593
0
                 NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
8594
8595
0
  conn->handshake_confirmed_ts = ts;
8596
8597
0
  ngtcp2_conn_discard_handshake_state(conn, ts);
8598
8599
0
  assert(conn->remote.transport_params);
8600
8601
0
  if (conn->remote.transport_params->preferred_addr_present) {
8602
0
    rv = conn_select_preferred_addr(conn);
8603
0
    if (rv != 0) {
8604
0
      return rv;
8605
0
    }
8606
0
  }
8607
8608
0
  rv = conn_call_handshake_confirmed(conn);
8609
0
  if (rv != 0) {
8610
0
    return rv;
8611
0
  }
8612
8613
  /* Re-arm loss detection timer after handshake has been
8614
     confirmed. */
8615
0
  ngtcp2_conn_set_loss_detection_timer(conn, ts);
8616
8617
0
  return 0;
8618
0
}
8619
8620
/*
8621
 * conn_recv_datagram processes the incoming DATAGRAM frame |fr|.
8622
 *
8623
 * This function returns 0 if it succeeds, or one of the following
8624
 * negative error codes:
8625
 *
8626
 * NGTCP2_ERR_CALLBACK_FAILURE
8627
 *     User-defined callback function failed.
8628
 */
8629
0
static int conn_recv_datagram(ngtcp2_conn *conn, ngtcp2_datagram *fr) {
8630
0
  assert(conn->local.transport_params.max_datagram_frame_size);
8631
8632
0
  return conn_call_recv_datagram(conn, fr);
8633
0
}
8634
8635
/*
8636
 * conn_key_phase_changed returns nonzero if |hd| indicates that the
8637
 * key phase has unexpected value.
8638
 */
8639
0
static int conn_key_phase_changed(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd) {
8640
0
  ngtcp2_pktns *pktns = &conn->pktns;
8641
8642
0
  return !(pktns->crypto.rx.ckm->flags & NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE) ^
8643
0
         !(hd->flags & NGTCP2_PKT_FLAG_KEY_PHASE);
8644
0
}
8645
8646
static int conn_initiate_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts);
8647
8648
/*
8649
 * conn_prepare_key_update installs new updated keys.
8650
 */
8651
0
static int conn_prepare_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
8652
0
  int rv;
8653
0
  ngtcp2_tstamp confirmed_ts = conn->crypto.key_update.confirmed_ts;
8654
0
  ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
8655
0
  ngtcp2_pktns *pktns = &conn->pktns;
8656
0
  ngtcp2_crypto_km *rx_ckm = pktns->crypto.rx.ckm;
8657
0
  ngtcp2_crypto_km *tx_ckm = pktns->crypto.tx.ckm;
8658
0
  ngtcp2_crypto_km *new_rx_ckm, *new_tx_ckm;
8659
0
  ngtcp2_crypto_aead_ctx rx_aead_ctx = {0}, tx_aead_ctx = {0};
8660
0
  size_t secretlen, ivlen;
8661
8662
0
  if ((conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) &&
8663
0
      tx_ckm->use_count >= pktns->crypto.ctx.max_encryption &&
8664
0
      conn_initiate_key_update(conn, ts) != 0) {
8665
0
    return NGTCP2_ERR_AEAD_LIMIT_REACHED;
8666
0
  }
8667
8668
0
  if ((conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED) ||
8669
0
      ngtcp2_tstamp_not_elapsed(confirmed_ts, pto, ts)) {
8670
0
    return 0;
8671
0
  }
8672
8673
0
  if (conn->crypto.key_update.new_rx_ckm ||
8674
0
      conn->crypto.key_update.new_tx_ckm) {
8675
0
    assert(conn->crypto.key_update.new_rx_ckm);
8676
0
    assert(conn->crypto.key_update.new_tx_ckm);
8677
0
    return 0;
8678
0
  }
8679
8680
0
  secretlen = rx_ckm->secret.len;
8681
0
  ivlen = rx_ckm->iv.len;
8682
8683
0
  rv = ngtcp2_crypto_km_nocopy_new(&conn->crypto.key_update.new_rx_ckm,
8684
0
                                   secretlen, ivlen, conn->mem);
8685
0
  if (rv != 0) {
8686
0
    return rv;
8687
0
  }
8688
8689
0
  rv = ngtcp2_crypto_km_nocopy_new(&conn->crypto.key_update.new_tx_ckm,
8690
0
                                   secretlen, ivlen, conn->mem);
8691
0
  if (rv != 0) {
8692
0
    return rv;
8693
0
  }
8694
8695
0
  new_rx_ckm = conn->crypto.key_update.new_rx_ckm;
8696
0
  new_tx_ckm = conn->crypto.key_update.new_tx_ckm;
8697
8698
0
  rv = conn_call_update_key(
8699
0
    conn, new_rx_ckm->secret.base, new_tx_ckm->secret.base, &rx_aead_ctx,
8700
0
    new_rx_ckm->iv.base, &tx_aead_ctx, new_tx_ckm->iv.base, rx_ckm->secret.base,
8701
0
    tx_ckm->secret.base, secretlen);
8702
0
  if (rv != 0) {
8703
0
    return rv;
8704
0
  }
8705
8706
0
  new_rx_ckm->aead_ctx = rx_aead_ctx;
8707
0
  new_tx_ckm->aead_ctx = tx_aead_ctx;
8708
8709
0
  if (!(rx_ckm->flags & NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE)) {
8710
0
    new_rx_ckm->flags |= NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE;
8711
0
    new_tx_ckm->flags |= NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE;
8712
0
  }
8713
8714
0
  if (conn->crypto.key_update.old_rx_ckm) {
8715
0
    conn_call_delete_crypto_aead_ctx(
8716
0
      conn, &conn->crypto.key_update.old_rx_ckm->aead_ctx);
8717
0
    ngtcp2_crypto_km_del(conn->crypto.key_update.old_rx_ckm, conn->mem);
8718
0
    conn->crypto.key_update.old_rx_ckm = NULL;
8719
0
  }
8720
8721
0
  return 0;
8722
0
}
8723
8724
/*
8725
 * conn_rotate_keys rotates keys.  The current key moves to old key,
8726
 * and new key moves to the current key.  If the local endpoint
8727
 * initiated this key update, pass nonzero as |initiator|.
8728
 */
8729
static void conn_rotate_keys(ngtcp2_conn *conn, int64_t pkt_num,
8730
0
                             int initiator) {
8731
0
  ngtcp2_pktns *pktns = &conn->pktns;
8732
8733
0
  assert(conn->crypto.key_update.new_rx_ckm);
8734
0
  assert(conn->crypto.key_update.new_tx_ckm);
8735
0
  assert(!conn->crypto.key_update.old_rx_ckm);
8736
0
  assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
8737
8738
0
  conn->crypto.key_update.old_rx_ckm = pktns->crypto.rx.ckm;
8739
8740
0
  pktns->crypto.rx.ckm = conn->crypto.key_update.new_rx_ckm;
8741
0
  conn->crypto.key_update.new_rx_ckm = NULL;
8742
0
  pktns->crypto.rx.ckm->pkt_num = pkt_num;
8743
8744
0
  assert(pktns->crypto.tx.ckm);
8745
8746
0
  conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
8747
0
  ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
8748
8749
0
  pktns->crypto.tx.ckm = conn->crypto.key_update.new_tx_ckm;
8750
0
  conn->crypto.key_update.new_tx_ckm = NULL;
8751
0
  pktns->crypto.tx.ckm->pkt_num = pktns->tx.last_pkt_num + 1;
8752
8753
0
  conn->flags |= NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED;
8754
0
  if (initiator) {
8755
0
    conn->flags |= NGTCP2_CONN_FLAG_KEY_UPDATE_INITIATOR;
8756
0
  }
8757
0
}
8758
8759
/*
8760
 * conn_path_validation_in_progress returns nonzero if path validation
8761
 * against |path| is underway.
8762
 */
8763
static int conn_path_validation_in_progress(ngtcp2_conn *conn,
8764
0
                                            const ngtcp2_path *path) {
8765
0
  ngtcp2_pv *pv = conn->pv;
8766
8767
0
  return pv && ngtcp2_path_eq(&pv->dcid.ps.path, path);
8768
0
}
8769
8770
/*
8771
 * conn_recv_non_probing_pkt_on_new_path is called when non-probing
8772
 * packet is received via new path.  It starts path validation against
8773
 * the new path.
8774
 *
8775
 * This function returns 0 if it succeeds, or one of the following
8776
 * negative error codes:
8777
 *
8778
 * NGTCP2_ERR_CONN_ID_BLOCKED
8779
 *     No DCID is available
8780
 * NGTCP2_ERR_NOMEM
8781
 *     Out of memory
8782
 */
8783
static int conn_recv_non_probing_pkt_on_new_path(ngtcp2_conn *conn,
8784
                                                 const ngtcp2_path *path,
8785
                                                 size_t dgramlen,
8786
                                                 int new_cid_used,
8787
0
                                                 ngtcp2_tstamp ts) {
8788
0
  ngtcp2_dcid dcid;
8789
0
  ngtcp2_pv *pv = NULL;
8790
0
  int rv;
8791
0
  ngtcp2_duration pto;
8792
0
  int local_addr_eq;
8793
0
  int pref_addr_migration;
8794
0
  uint32_t remote_addr_cmp;
8795
0
  const ngtcp2_path_history_entry *validated_path;
8796
8797
0
  assert(conn->server);
8798
8799
0
  if (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8800
0
      ngtcp2_path_eq(&conn->pv->fallback_dcid.ps.path, path)) {
8801
    /* If new path equals fallback path, that means connection
8802
       migrated back to the original path.  Fallback path is
8803
       considered to be validated. */
8804
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
8805
0
                    "path is migrated back to the original path");
8806
0
    ngtcp2_dcid_copy(&conn->dcid.current, &conn->pv->fallback_dcid);
8807
0
    conn_reset_congestion_state(conn, ts);
8808
0
    conn->dcid.current.bytes_recv += dgramlen;
8809
0
    conn_reset_ecn_validation_state(conn);
8810
8811
0
    rv = conn_abort_pv(conn, ts);
8812
0
    if (rv != 0) {
8813
0
      return rv;
8814
0
    }
8815
8816
    /* Run PMTUD just in case if it is prematurely aborted */
8817
0
    assert(!conn->pmtud);
8818
8819
0
    if (!conn->local.settings.no_pmtud) {
8820
0
      return conn_start_pmtud(conn);
8821
0
    }
8822
8823
0
    return 0;
8824
0
  }
8825
8826
0
  remote_addr_cmp =
8827
0
    ngtcp2_addr_cmp(&conn->dcid.current.ps.path.remote, &path->remote);
8828
0
  local_addr_eq =
8829
0
    ngtcp2_addr_eq(&conn->dcid.current.ps.path.local, &path->local);
8830
0
  pref_addr_migration =
8831
0
    !local_addr_eq && conn_server_preferred_addr_migration(conn, &path->local);
8832
8833
  /*
8834
   * When to change DCID?  RFC 9002 section 9.5 says:
8835
   *
8836
   * An endpoint MUST NOT reuse a connection ID when sending from more
8837
   * than one local address -- for example, when initiating connection
8838
   * migration as described in Section 9.2 or when probing a new
8839
   * network path as described in Section 9.1.
8840
   *
8841
   * Similarly, an endpoint MUST NOT reuse a connection ID when
8842
   * sending to more than one destination address.  Due to network
8843
   * changes outside the control of its peer, an endpoint might
8844
   * receive packets from a new source address with the same
8845
   * Destination Connection ID field value, in which case it MAY
8846
   * continue to use the current connection ID with the new remote
8847
   * address while still sending from the same local address.
8848
   */
8849
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
8850
0
                  "non-probing packet was received from new remote address");
8851
8852
0
  if (ngtcp2_dcidtr_pop_bound_dcid(&conn->dcid.dtr, &dcid, path) == 0) {
8853
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
8854
0
                    "Found DCID which has already been bound to the new path");
8855
8856
0
    if (dcid.cid.datalen) {
8857
0
      rv = conn_call_activate_dcid(conn, &dcid);
8858
0
      if (rv != 0) {
8859
0
        return rv;
8860
0
      }
8861
0
    }
8862
0
  } else {
8863
0
    if (conn->dcid.current.cid.datalen &&
8864
0
        ((new_cid_used && remote_addr_cmp) || !local_addr_eq)) {
8865
      /* New DCID is required. */
8866
0
      if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
8867
0
        return NGTCP2_ERR_CONN_ID_BLOCKED;
8868
0
      }
8869
8870
0
      ngtcp2_dcidtr_pop_unused(&conn->dcid.dtr, &dcid);
8871
8872
0
      rv = conn_call_activate_dcid(conn, &dcid);
8873
0
      if (rv != 0) {
8874
0
        return rv;
8875
0
      }
8876
0
    } else {
8877
      /* Use the current DCID if a remote endpoint does not change
8878
         DCID. */
8879
0
      ngtcp2_dcid_copy(&dcid, &conn->dcid.current);
8880
0
      dcid.bytes_sent = 0;
8881
0
      dcid.bytes_recv = 0;
8882
0
      dcid.flags &= (uint8_t)~NGTCP2_DCID_FLAG_PATH_VALIDATED;
8883
0
    }
8884
8885
0
    ngtcp2_dcid_set_path(&dcid, path);
8886
0
  }
8887
8888
0
  dcid.bytes_recv += dgramlen;
8889
8890
0
  validated_path = ngtcp2_conn_find_path_history(conn, path, ts);
8891
0
  if (!validated_path) {
8892
0
    pto = conn_compute_pto(conn, &conn->pktns);
8893
8894
0
    rv = ngtcp2_pv_new(&pv, &dcid, conn_compute_pv_timeout_pto(conn, pto),
8895
0
                       NGTCP2_PV_FLAG_NONE, &conn->log, conn->mem);
8896
0
    if (rv != 0) {
8897
0
      return rv;
8898
0
    }
8899
8900
0
    if (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT)) {
8901
0
      ngtcp2_pv_set_fallback(pv, &conn->pv->fallback_dcid,
8902
0
                             conn->pv->fallback_pto);
8903
      /* Unset the flag bit so that conn_stop_pv does not retire
8904
         DCID. */
8905
0
      conn->pv->flags &= (uint8_t)~NGTCP2_PV_FLAG_FALLBACK_PRESENT;
8906
0
    } else if (!pref_addr_migration) {
8907
0
      ngtcp2_pv_set_fallback(pv, &conn->dcid.current, pto);
8908
0
    }
8909
0
  }
8910
8911
0
  if (!pref_addr_migration || validated_path) {
8912
0
    if (conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) {
8913
0
      ngtcp2_conn_add_path_history(conn, &conn->dcid.current, ts);
8914
0
    }
8915
8916
0
    ngtcp2_dcid_copy(&conn->dcid.current, &dcid);
8917
8918
0
    if (!local_addr_eq || (remote_addr_cmp & (NGTCP2_ADDR_CMP_FLAG_ADDR |
8919
0
                                              NGTCP2_ADDR_CMP_FLAG_FAMILY))) {
8920
0
      conn_reset_congestion_state(conn, ts);
8921
0
    }
8922
8923
0
    conn_reset_ecn_validation_state(conn);
8924
8925
0
    ngtcp2_conn_stop_pmtud(conn);
8926
8927
0
    if (validated_path) {
8928
0
      ngtcp2_dcid_apply_validated_path(&conn->dcid.current, validated_path);
8929
8930
0
      if (!conn->local.settings.no_pmtud) {
8931
0
        rv = conn_start_pmtud(conn);
8932
0
        if (rv != 0) {
8933
0
          return rv;
8934
0
        }
8935
0
      }
8936
0
    }
8937
0
  }
8938
8939
0
  if (conn->pv) {
8940
0
    ngtcp2_log_info(
8941
0
      &conn->log, NGTCP2_LOG_EVENT_PTV,
8942
0
      "path migration is aborted because new migration has started");
8943
0
    rv = conn_abort_pv(conn, ts);
8944
0
    if (rv != 0) {
8945
0
      return rv;
8946
0
    }
8947
0
  }
8948
8949
0
  conn->pv = pv;
8950
8951
0
  return conn_call_begin_path_validation(conn, conn->pv);
8952
0
}
8953
8954
/*
8955
 * conn_recv_pkt_from_new_path is called when a 1RTT packet is
8956
 * received from new path (not current path).  This packet would be a
8957
 * packet which only contains probing frame, or reordered packet, or a
8958
 * path is being validated.
8959
 *
8960
 * This function returns 0 if it succeeds, or one of the following
8961
 * negative error codes:
8962
 *
8963
 * NGTCP2_ERR_CONN_ID_BLOCKED
8964
 *     No unused DCID is available
8965
 * NGTCP2_ERR_NOMEM
8966
 *     Out of memory
8967
 */
8968
static int conn_recv_pkt_from_new_path(ngtcp2_conn *conn,
8969
                                       const ngtcp2_path *path, size_t dgramlen,
8970
                                       int path_challenge_recved,
8971
0
                                       ngtcp2_tstamp ts) {
8972
0
  ngtcp2_pv *pv = conn->pv;
8973
0
  ngtcp2_dcid *bound_dcid;
8974
0
  int rv;
8975
8976
0
  if (pv) {
8977
0
    if (ngtcp2_path_eq(&pv->dcid.ps.path, path)) {
8978
0
      pv->dcid.bytes_recv += dgramlen;
8979
0
      return 0;
8980
0
    }
8981
8982
0
    if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
8983
0
        ngtcp2_path_eq(&pv->fallback_dcid.ps.path, path)) {
8984
0
      pv->fallback_dcid.bytes_recv += dgramlen;
8985
0
      return 0;
8986
0
    }
8987
0
  }
8988
8989
0
  if (!path_challenge_recved) {
8990
0
    return 0;
8991
0
  }
8992
8993
0
  rv = conn_bind_dcid(conn, &bound_dcid, path, ts);
8994
0
  if (rv != 0) {
8995
0
    return rv;
8996
0
  }
8997
8998
0
  bound_dcid->bytes_recv += dgramlen;
8999
9000
0
  return 0;
9001
0
}
9002
9003
/*
9004
 * conn_recv_delayed_handshake_pkt processes the received Handshake
9005
 * packet which is received after handshake completed.  This function
9006
 * does the minimal job, and its purpose is send acknowledgement of
9007
 * this packet to the peer.  We assume that hd->type ==
9008
 * NGTCP2_PKT_HANDSHAKE.
9009
 *
9010
 * This function returns 0 if it succeeds, or one of the following
9011
 * negative error codes:
9012
 *
9013
 * NGTCP2_ERR_FRAME_ENCODING
9014
 *     Frame is badly formatted; or frame type is unknown.
9015
 * NGTCP2_ERR_NOMEM
9016
 *     Out of memory
9017
 * NGTCP2_ERR_DISCARD_PKT
9018
 *     Packet was discarded.
9019
 * NGTCP2_ERR_ACK_FRAME
9020
 *     ACK frame is malformed.
9021
 * NGTCP2_ERR_PROTO
9022
 *     Frame that is not allowed in Handshake packet is received.
9023
 */
9024
static int
9025
conn_recv_delayed_handshake_pkt(ngtcp2_conn *conn, const ngtcp2_pkt_info *pi,
9026
                                const ngtcp2_pkt_hd *hd, size_t pktlen,
9027
                                const uint8_t *payload, size_t payloadlen,
9028
0
                                ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
9029
0
  ngtcp2_ssize nread;
9030
0
  ngtcp2_frame_decoder frd;
9031
0
  ngtcp2_frame fr;
9032
0
  int rv;
9033
0
  int require_ack = 0;
9034
0
  ngtcp2_pktns *pktns;
9035
0
  size_t num_ack_processed = 0;
9036
9037
0
  assert(hd->type == NGTCP2_PKT_HANDSHAKE);
9038
9039
0
  pktns = conn->hs_pktns;
9040
9041
0
  if (payloadlen == 0) {
9042
    /* QUIC packet must contain at least one frame */
9043
0
    return NGTCP2_ERR_PROTO;
9044
0
  }
9045
9046
0
  ngtcp2_qlog_pkt_received_start(&conn->qlog);
9047
9048
0
  for (; payloadlen;) {
9049
0
    nread = ngtcp2_frame_decoder_decode(&frd, &fr, payload, payloadlen);
9050
0
    if (nread < 0) {
9051
0
      return (int)nread;
9052
0
    }
9053
9054
0
    payload += nread;
9055
0
    payloadlen -= (size_t)nread;
9056
9057
0
    switch (fr.hd.type) {
9058
0
    case NGTCP2_FRAME_ACK:
9059
0
    case NGTCP2_FRAME_ACK_ECN:
9060
0
      fr.ack.ack_delay = 0;
9061
0
      fr.ack.ack_delay_unscaled = 0;
9062
9063
0
      rv =
9064
0
        ngtcp2_pkt_validate_ack(&fr.ack, conn->local.settings.initial_pkt_num);
9065
0
      if (rv != 0) {
9066
0
        return rv;
9067
0
      }
9068
9069
0
      break;
9070
0
    }
9071
9072
0
    ngtcp2_log_rx_fr(&conn->log, hd, &fr);
9073
9074
0
    switch (fr.hd.type) {
9075
0
    case NGTCP2_FRAME_ACK:
9076
0
    case NGTCP2_FRAME_ACK_ECN:
9077
0
      if (num_ack_processed >= NGTCP2_MAX_ACK_PER_PKT) {
9078
0
        break;
9079
0
      }
9080
0
      if (!conn->server) {
9081
0
        conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
9082
0
      }
9083
0
      rv = conn_recv_ack(conn, pktns, &fr.ack, pkt_ts, ts);
9084
0
      if (rv != 0) {
9085
0
        return rv;
9086
0
      }
9087
0
      ++num_ack_processed;
9088
0
      break;
9089
0
    case NGTCP2_FRAME_PADDING:
9090
0
      break;
9091
0
    case NGTCP2_FRAME_CONNECTION_CLOSE:
9092
0
      rv = conn_recv_connection_close(conn, &fr.connection_close);
9093
0
      if (rv != 0) {
9094
0
        return rv;
9095
0
      }
9096
0
      break;
9097
0
    case NGTCP2_FRAME_PING:
9098
0
      ++conn->cstat.ping_recv;
9099
      /* fall through */
9100
0
    case NGTCP2_FRAME_CRYPTO:
9101
0
      require_ack = 1;
9102
0
      break;
9103
0
    default:
9104
0
      return NGTCP2_ERR_PROTO;
9105
0
    }
9106
9107
0
    ngtcp2_qlog_write_frame(&conn->qlog, &fr);
9108
0
  }
9109
9110
0
  ngtcp2_qlog_pkt_received_end(&conn->qlog, hd, pktlen);
9111
9112
0
  rv = pktns_commit_recv_pkt_num(pktns, hd->pkt_num, pi, require_ack, pkt_ts);
9113
0
  if (rv != 0) {
9114
0
    return rv;
9115
0
  }
9116
9117
  /* Initial and Handshake are always acknowledged without delay.  No
9118
     need to call ngtcp2_acktr_immediate_ack(). */
9119
9120
0
  conn_restart_timer_on_read(conn, ts);
9121
9122
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
9123
9124
0
  return 0;
9125
0
}
9126
9127
/*
9128
 * conn_recv_pkt processes a packet contained in the buffer pointed by
9129
 * |pkt| of length |pktlen|.  |pkt| may contain multiple QUIC packets.
9130
 * This function only processes the first packet.  |pkt_ts| is the
9131
 * timestamp when packet is received.  |ts| should be the current
9132
 * time.  Usually they are the same, but for buffered packets,
9133
 * |pkt_ts| would be earlier than |ts|.
9134
 *
9135
 * This function returns the number of bytes processed if it succeeds,
9136
 * or one of the following negative error codes:
9137
 *
9138
 * NGTCP2_ERR_DISCARD_PKT
9139
 *     Packet was discarded because plain text header was malformed;
9140
 *     or its payload could not be decrypted.
9141
 * NGTCP2_ERR_PROTO
9142
 *     Packet is badly formatted; or 0RTT packet contains other than
9143
 *     PADDING or STREAM frames; or other QUIC protocol violation is
9144
 *     found.
9145
 * NGTCP2_ERR_CALLBACK_FAILURE
9146
 *     User-defined callback function failed.
9147
 * NGTCP2_ERR_NOMEM
9148
 *     Out of memory.
9149
 * NGTCP2_ERR_FRAME_ENCODING
9150
 *     Frame is badly formatted; or frame type is unknown.
9151
 * NGTCP2_ERR_ACK_FRAME
9152
 *     ACK frame is malformed.
9153
 * NGTCP2_ERR_STREAM_STATE
9154
 *     Frame is received to the local stream which is not initiated.
9155
 * NGTCP2_ERR_STREAM_LIMIT
9156
 *     Frame has remote stream ID which is strictly greater than the
9157
 *     allowed limit.
9158
 * NGTCP2_ERR_FLOW_CONTROL
9159
 *     Flow control limit is violated.
9160
 * NGTCP2_ERR_FINAL_SIZE
9161
 *     Frame has strictly larger end offset than it is permitted.
9162
 * NGTCP2_ERR_INTERNAL
9163
 *     Suspicious remote endpoint activity exceeded threshold.
9164
 */
9165
static ngtcp2_ssize conn_recv_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
9166
                                  const ngtcp2_pkt_info *pi, const uint8_t *pkt,
9167
                                  size_t pktlen, size_t dgramlen,
9168
0
                                  ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
9169
0
  ngtcp2_pkt_hd hd;
9170
0
  int rv = 0;
9171
0
  size_t hdpktlen;
9172
0
  const uint8_t *payload;
9173
0
  size_t payloadlen;
9174
0
  ngtcp2_ssize nread, nwrite;
9175
0
  ngtcp2_frame_decoder frd;
9176
0
  ngtcp2_frame fr;
9177
0
  int require_ack = 0;
9178
0
  ngtcp2_crypto_aead *aead;
9179
0
  ngtcp2_crypto_cipher *hp;
9180
0
  ngtcp2_crypto_km *ckm;
9181
0
  ngtcp2_crypto_cipher_ctx *hp_ctx;
9182
0
  ngtcp2_hp_mask hp_mask;
9183
0
  ngtcp2_decrypt decrypt;
9184
0
  ngtcp2_pktns *pktns;
9185
0
  int non_probing_pkt = 0;
9186
0
  int key_phase_bit_changed = 0;
9187
0
  int force_decrypt_failure = 0;
9188
0
  int recv_ncid = 0;
9189
0
  int new_cid_used = 0;
9190
0
  int path_challenge_recved = 0;
9191
0
  size_t num_ack_processed = 0;
9192
9193
0
  if (pkt[0] & NGTCP2_HEADER_FORM_BIT) {
9194
0
    nread = ngtcp2_pkt_decode_hd_long(&hd, pkt, pktlen);
9195
0
    if (nread < 0) {
9196
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9197
0
                      "could not decode long header");
9198
0
      return NGTCP2_ERR_DISCARD_PKT;
9199
0
    }
9200
9201
0
    if (pktlen < (size_t)nread + hd.len) {
9202
0
      return NGTCP2_ERR_DISCARD_PKT;
9203
0
    }
9204
9205
0
    assert(conn->negotiated_version);
9206
9207
0
    if (hd.version != conn->client_chosen_version &&
9208
0
        hd.version != conn->negotiated_version) {
9209
0
      return NGTCP2_ERR_DISCARD_PKT;
9210
0
    }
9211
9212
0
    if (conn_verify_fixed_bit(conn, &hd) != 0) {
9213
0
      return NGTCP2_ERR_DISCARD_PKT;
9214
0
    }
9215
9216
0
    pktlen = (size_t)nread + hd.len;
9217
9218
    /* Quoted from spec: if subsequent packets of those types include
9219
       a different Source Connection ID, they MUST be discarded. */
9220
0
    if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
9221
0
      ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
9222
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9223
0
                      "packet was ignored because of mismatched SCID");
9224
0
      return NGTCP2_ERR_DISCARD_PKT;
9225
0
    }
9226
9227
0
    switch (hd.type) {
9228
0
    case NGTCP2_PKT_INITIAL:
9229
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9230
0
                      "delayed Initial packet was discarded");
9231
0
      return (ngtcp2_ssize)pktlen;
9232
0
    case NGTCP2_PKT_HANDSHAKE:
9233
0
      if (hd.version != conn->negotiated_version) {
9234
0
        return NGTCP2_ERR_DISCARD_PKT;
9235
0
      }
9236
9237
0
      if (!conn->hs_pktns) {
9238
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9239
0
                        "delayed Handshake packet was discarded");
9240
0
        return (ngtcp2_ssize)pktlen;
9241
0
      }
9242
9243
0
      pktns = conn->hs_pktns;
9244
0
      aead = &pktns->crypto.ctx.aead;
9245
0
      hp = &pktns->crypto.ctx.hp;
9246
0
      ckm = pktns->crypto.rx.ckm;
9247
0
      hp_ctx = &pktns->crypto.rx.hp_ctx;
9248
0
      hp_mask = conn->callbacks.hp_mask;
9249
0
      decrypt = conn->callbacks.decrypt;
9250
0
      break;
9251
0
    case NGTCP2_PKT_0RTT:
9252
0
      if (!conn->server || hd.version != conn->client_chosen_version) {
9253
0
        return NGTCP2_ERR_DISCARD_PKT;
9254
0
      }
9255
9256
0
      if (!conn->early.ckm) {
9257
0
        return (ngtcp2_ssize)pktlen;
9258
0
      }
9259
9260
0
      pktns = &conn->pktns;
9261
0
      aead = &conn->early.ctx.aead;
9262
0
      hp = &conn->early.ctx.hp;
9263
0
      ckm = conn->early.ckm;
9264
0
      hp_ctx = &conn->early.hp_ctx;
9265
0
      hp_mask = conn->callbacks.hp_mask;
9266
0
      decrypt = conn->callbacks.decrypt;
9267
0
      break;
9268
0
    default:
9269
0
      ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
9270
0
      ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_PKT,
9271
0
                       "packet type 0x%02x was ignored", hd.type);
9272
0
      return (ngtcp2_ssize)pktlen;
9273
0
    }
9274
0
  } else {
9275
0
    nread = ngtcp2_pkt_decode_hd_short(&hd, pkt, pktlen, conn->oscid.datalen);
9276
0
    if (nread < 0) {
9277
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9278
0
                      "could not decode short header");
9279
0
      return NGTCP2_ERR_DISCARD_PKT;
9280
0
    }
9281
9282
0
    if (conn_verify_fixed_bit(conn, &hd) != 0) {
9283
0
      return NGTCP2_ERR_DISCARD_PKT;
9284
0
    }
9285
9286
0
    pktns = &conn->pktns;
9287
0
    aead = &pktns->crypto.ctx.aead;
9288
0
    hp = &pktns->crypto.ctx.hp;
9289
0
    ckm = pktns->crypto.rx.ckm;
9290
0
    hp_ctx = &pktns->crypto.rx.hp_ctx;
9291
0
    hp_mask = conn->callbacks.hp_mask;
9292
0
    decrypt = conn->callbacks.decrypt;
9293
0
  }
9294
9295
0
  rv = conn_ensure_decrypt_hp_buffer(conn, (size_t)nread + 4);
9296
0
  if (rv != 0) {
9297
0
    return rv;
9298
0
  }
9299
9300
0
  nwrite = decrypt_hp(&hd, conn->crypto.decrypt_hp_buf.base, hp, pkt, pktlen,
9301
0
                      (size_t)nread, hp_ctx, hp_mask);
9302
0
  if (nwrite < 0) {
9303
0
    if (ngtcp2_err_is_fatal((int)nwrite)) {
9304
0
      return nwrite;
9305
0
    }
9306
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9307
0
                    "could not decrypt packet number");
9308
0
    return NGTCP2_ERR_DISCARD_PKT;
9309
0
  }
9310
9311
0
  hdpktlen = (size_t)nwrite;
9312
0
  payload = pkt + hdpktlen;
9313
0
  payloadlen = pktlen - hdpktlen;
9314
9315
0
  hd.pkt_num = ngtcp2_pkt_adjust_pkt_num(pktns->acktr.max_pkt_num, hd.pkt_num,
9316
0
                                         hd.pkt_numlen);
9317
0
  if (hd.pkt_num > NGTCP2_MAX_PKT_NUM) {
9318
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_PKT,
9319
0
                     "pkn=%" PRId64 " is greater than maximum pkn", hd.pkt_num);
9320
0
    return NGTCP2_ERR_DISCARD_PKT;
9321
0
  }
9322
9323
0
  ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
9324
9325
0
  if (hd.type == NGTCP2_PKT_1RTT) {
9326
0
    if (conn->server && conn->rx.preferred_addr.pkt_num != -1 &&
9327
0
        conn->rx.preferred_addr.pkt_num < hd.pkt_num &&
9328
0
        ngtcp2_sockaddr_eq((const ngtcp2_sockaddr *)&conn->hs_local_addr,
9329
0
                           path->local.addr)) {
9330
0
      ngtcp2_log_infof(
9331
0
        &conn->log, NGTCP2_LOG_EVENT_PKT,
9332
0
        "pkt=%" PRId64
9333
0
        " is discarded because it was received on handshake local "
9334
0
        "address after preferred address migration",
9335
0
        hd.pkt_num);
9336
0
      return NGTCP2_ERR_DISCARD_PKT;
9337
0
    }
9338
9339
0
    key_phase_bit_changed = conn_key_phase_changed(conn, &hd);
9340
0
  }
9341
9342
0
  rv = conn_ensure_decrypt_buffer(conn, payloadlen);
9343
0
  if (rv != 0) {
9344
0
    return rv;
9345
0
  }
9346
9347
0
  if (key_phase_bit_changed) {
9348
0
    assert(hd.type == NGTCP2_PKT_1RTT);
9349
9350
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT, "unexpected KEY_PHASE");
9351
9352
0
    if (ckm->pkt_num > hd.pkt_num) {
9353
0
      if (conn->crypto.key_update.old_rx_ckm) {
9354
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9355
0
                        "decrypting with old key");
9356
0
        ckm = conn->crypto.key_update.old_rx_ckm;
9357
0
      } else {
9358
0
        force_decrypt_failure = 1;
9359
0
      }
9360
0
    } else if (pktns->acktr.max_pkt_num < hd.pkt_num) {
9361
0
      assert(ckm->pkt_num < hd.pkt_num);
9362
0
      if (!conn->crypto.key_update.new_rx_ckm) {
9363
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9364
0
                        "new key is not available");
9365
0
        force_decrypt_failure = 1;
9366
0
      } else {
9367
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9368
0
                        "decrypting with new key");
9369
0
        ckm = conn->crypto.key_update.new_rx_ckm;
9370
0
      }
9371
0
    } else {
9372
0
      force_decrypt_failure = 1;
9373
0
    }
9374
0
  }
9375
9376
0
  nwrite = decrypt_pkt(conn->crypto.decrypt_buf.base, aead, payload, payloadlen,
9377
0
                       conn->crypto.decrypt_hp_buf.base, hdpktlen, hd.pkt_num,
9378
0
                       ckm, decrypt);
9379
9380
0
  if (force_decrypt_failure) {
9381
0
    nwrite = NGTCP2_ERR_DECRYPT;
9382
0
  }
9383
9384
0
  if (nwrite < 0) {
9385
0
    if (ngtcp2_err_is_fatal((int)nwrite)) {
9386
0
      return nwrite;
9387
0
    }
9388
9389
0
    assert(NGTCP2_ERR_DECRYPT == nwrite);
9390
9391
0
    if (hd.type == NGTCP2_PKT_1RTT &&
9392
0
        ++conn->crypto.decryption_failure_count >=
9393
0
          pktns->crypto.ctx.max_decryption_failure) {
9394
0
      return NGTCP2_ERR_AEAD_LIMIT_REACHED;
9395
0
    }
9396
9397
0
    if (hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) {
9398
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9399
0
                      "could not decrypt packet payload");
9400
0
      return NGTCP2_ERR_DISCARD_PKT;
9401
0
    }
9402
9403
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9404
0
                    "could not decrypt packet payload");
9405
0
    return NGTCP2_ERR_DISCARD_PKT;
9406
0
  }
9407
9408
0
  rv = ngtcp2_pkt_verify_reserved_bits(conn->crypto.decrypt_hp_buf.base[0]);
9409
0
  if (rv != 0) {
9410
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9411
0
                    "packet has incorrect reserved bits");
9412
9413
0
    return NGTCP2_ERR_PROTO;
9414
0
  }
9415
9416
0
  if (pktns_pkt_num_is_duplicate(pktns, hd.pkt_num)) {
9417
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9418
0
                    "packet was discarded because of duplicated packet number");
9419
0
    return NGTCP2_ERR_DISCARD_PKT;
9420
0
  }
9421
9422
0
  payload = conn->crypto.decrypt_buf.base;
9423
0
  payloadlen = (size_t)nwrite;
9424
9425
0
  if (payloadlen == 0) {
9426
    /* QUIC packet must contain at least one frame */
9427
0
    return NGTCP2_ERR_PROTO;
9428
0
  }
9429
9430
0
  if (hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) {
9431
0
    switch (hd.type) {
9432
0
    case NGTCP2_PKT_HANDSHAKE:
9433
0
      rv = conn_verify_dcid(conn, NULL, &hd);
9434
0
      if (rv != 0) {
9435
0
        if (ngtcp2_err_is_fatal(rv)) {
9436
0
          return rv;
9437
0
        }
9438
0
        ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9439
0
                        "packet was ignored because of mismatched DCID");
9440
0
        return NGTCP2_ERR_DISCARD_PKT;
9441
0
      }
9442
9443
0
      rv = conn_recv_delayed_handshake_pkt(conn, pi, &hd, pktlen, payload,
9444
0
                                           payloadlen, pkt_ts, ts);
9445
0
      if (rv < 0) {
9446
0
        return (ngtcp2_ssize)rv;
9447
0
      }
9448
9449
0
      return (ngtcp2_ssize)pktlen;
9450
0
    case NGTCP2_PKT_0RTT:
9451
0
      if (!ngtcp2_cid_eq(&conn->rcid, &hd.dcid)) {
9452
0
        rv = conn_verify_dcid(conn, NULL, &hd);
9453
0
        if (rv != 0) {
9454
0
          if (ngtcp2_err_is_fatal(rv)) {
9455
0
            return rv;
9456
0
          }
9457
0
          ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9458
0
                          "packet was ignored because of mismatched DCID");
9459
0
          return NGTCP2_ERR_DISCARD_PKT;
9460
0
        }
9461
0
      }
9462
0
      break;
9463
0
    default:
9464
      /* Unreachable */
9465
0
      ngtcp2_unreachable();
9466
0
    }
9467
0
  } else {
9468
0
    rv = conn_verify_dcid(conn, &new_cid_used, &hd);
9469
0
    if (rv != 0) {
9470
0
      if (ngtcp2_err_is_fatal(rv)) {
9471
0
        return rv;
9472
0
      }
9473
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9474
0
                      "packet was ignored because of mismatched DCID");
9475
0
      return NGTCP2_ERR_DISCARD_PKT;
9476
0
    }
9477
0
  }
9478
9479
0
  ngtcp2_qlog_pkt_received_start(&conn->qlog);
9480
9481
0
  for (; payloadlen;) {
9482
0
    nread = ngtcp2_frame_decoder_decode(&frd, &fr, payload, payloadlen);
9483
0
    if (nread < 0) {
9484
0
      return nread;
9485
0
    }
9486
9487
0
    payload += nread;
9488
0
    payloadlen -= (size_t)nread;
9489
9490
0
    switch (fr.hd.type) {
9491
0
    case NGTCP2_FRAME_ACK:
9492
0
    case NGTCP2_FRAME_ACK_ECN:
9493
0
      if ((hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) &&
9494
0
          hd.type == NGTCP2_PKT_0RTT) {
9495
0
        return NGTCP2_ERR_PROTO;
9496
0
      }
9497
0
      assert(conn->remote.transport_params);
9498
0
      assign_recved_ack_delay_unscaled(
9499
0
        &fr.ack, conn->remote.transport_params->ack_delay_exponent);
9500
9501
0
      rv =
9502
0
        ngtcp2_pkt_validate_ack(&fr.ack, conn->local.settings.initial_pkt_num);
9503
0
      if (rv != 0) {
9504
0
        return rv;
9505
0
      }
9506
9507
0
      break;
9508
0
    }
9509
9510
0
    ngtcp2_log_rx_fr(&conn->log, &hd, &fr);
9511
9512
0
    if (hd.type == NGTCP2_PKT_0RTT) {
9513
0
      switch (fr.hd.type) {
9514
0
      case NGTCP2_FRAME_PADDING:
9515
0
      case NGTCP2_FRAME_PING:
9516
0
      case NGTCP2_FRAME_RESET_STREAM:
9517
0
      case NGTCP2_FRAME_STOP_SENDING:
9518
0
      case NGTCP2_FRAME_STREAM:
9519
0
      case NGTCP2_FRAME_MAX_DATA:
9520
0
      case NGTCP2_FRAME_MAX_STREAM_DATA:
9521
0
      case NGTCP2_FRAME_MAX_STREAMS_BIDI:
9522
0
      case NGTCP2_FRAME_MAX_STREAMS_UNI:
9523
0
      case NGTCP2_FRAME_DATA_BLOCKED:
9524
0
      case NGTCP2_FRAME_STREAM_DATA_BLOCKED:
9525
0
      case NGTCP2_FRAME_STREAMS_BLOCKED_BIDI:
9526
0
      case NGTCP2_FRAME_STREAMS_BLOCKED_UNI:
9527
0
      case NGTCP2_FRAME_NEW_CONNECTION_ID:
9528
0
      case NGTCP2_FRAME_PATH_CHALLENGE:
9529
0
      case NGTCP2_FRAME_CONNECTION_CLOSE:
9530
0
      case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
9531
0
      case NGTCP2_FRAME_DATAGRAM:
9532
0
      case NGTCP2_FRAME_DATAGRAM_LEN:
9533
0
        break;
9534
0
      default:
9535
0
        return NGTCP2_ERR_PROTO;
9536
0
      }
9537
0
    }
9538
9539
0
    switch (fr.hd.type) {
9540
0
    case NGTCP2_FRAME_ACK:
9541
0
    case NGTCP2_FRAME_ACK_ECN:
9542
0
    case NGTCP2_FRAME_PADDING:
9543
0
    case NGTCP2_FRAME_CONNECTION_CLOSE:
9544
0
    case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
9545
0
      break;
9546
0
    default:
9547
0
      require_ack = 1;
9548
0
    }
9549
9550
0
    switch (fr.hd.type) {
9551
0
    case NGTCP2_FRAME_ACK:
9552
0
    case NGTCP2_FRAME_ACK_ECN:
9553
0
      if (num_ack_processed >= NGTCP2_MAX_ACK_PER_PKT) {
9554
0
        break;
9555
0
      }
9556
0
      if (!conn->server) {
9557
0
        conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
9558
0
      }
9559
0
      rv = conn_recv_ack(conn, pktns, &fr.ack, pkt_ts, ts);
9560
0
      if (rv != 0) {
9561
0
        return rv;
9562
0
      }
9563
0
      non_probing_pkt = 1;
9564
0
      ++num_ack_processed;
9565
0
      break;
9566
0
    case NGTCP2_FRAME_STREAM:
9567
0
      rv = conn_recv_stream(conn, &fr.stream, ts);
9568
0
      if (rv != 0) {
9569
0
        return rv;
9570
0
      }
9571
0
      non_probing_pkt = 1;
9572
0
      break;
9573
0
    case NGTCP2_FRAME_CRYPTO:
9574
0
      rv = conn_recv_crypto(conn, NGTCP2_ENCRYPTION_LEVEL_1RTT,
9575
0
                            &pktns->crypto.strm, &fr.stream, ts);
9576
0
      if (rv != 0) {
9577
0
        return rv;
9578
0
      }
9579
0
      non_probing_pkt = 1;
9580
0
      break;
9581
0
    case NGTCP2_FRAME_RESET_STREAM:
9582
0
      rv = conn_recv_reset_stream(conn, &fr.reset_stream, ts);
9583
0
      if (rv != 0) {
9584
0
        return rv;
9585
0
      }
9586
0
      non_probing_pkt = 1;
9587
0
      break;
9588
0
    case NGTCP2_FRAME_STOP_SENDING:
9589
0
      rv = conn_recv_stop_sending(conn, &fr.stop_sending, ts);
9590
0
      if (rv != 0) {
9591
0
        return rv;
9592
0
      }
9593
0
      non_probing_pkt = 1;
9594
0
      break;
9595
0
    case NGTCP2_FRAME_MAX_STREAM_DATA:
9596
0
      rv = conn_recv_max_stream_data(conn, &fr.max_stream_data, ts);
9597
0
      if (rv != 0) {
9598
0
        return rv;
9599
0
      }
9600
0
      non_probing_pkt = 1;
9601
0
      break;
9602
0
    case NGTCP2_FRAME_MAX_DATA:
9603
0
      conn_recv_max_data(conn, &fr.max_data);
9604
0
      non_probing_pkt = 1;
9605
0
      break;
9606
0
    case NGTCP2_FRAME_MAX_STREAMS_BIDI:
9607
0
    case NGTCP2_FRAME_MAX_STREAMS_UNI:
9608
0
      rv = conn_recv_max_streams(conn, &fr.max_streams);
9609
0
      if (rv != 0) {
9610
0
        return rv;
9611
0
      }
9612
0
      non_probing_pkt = 1;
9613
0
      break;
9614
0
    case NGTCP2_FRAME_CONNECTION_CLOSE:
9615
0
    case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
9616
0
      rv = conn_recv_connection_close(conn, &fr.connection_close);
9617
0
      if (rv != 0) {
9618
0
        return rv;
9619
0
      }
9620
0
      break;
9621
0
    case NGTCP2_FRAME_PING:
9622
0
      ++conn->cstat.ping_recv;
9623
0
      non_probing_pkt = 1;
9624
0
      break;
9625
0
    case NGTCP2_FRAME_PATH_CHALLENGE:
9626
0
      conn_recv_path_challenge(conn, path, &fr.path_challenge);
9627
0
      path_challenge_recved = 1;
9628
0
      break;
9629
0
    case NGTCP2_FRAME_PATH_RESPONSE:
9630
0
      rv = conn_recv_path_response(conn, &hd, &fr.path_response, ts);
9631
0
      if (rv != 0) {
9632
0
        return rv;
9633
0
      }
9634
0
      break;
9635
0
    case NGTCP2_FRAME_NEW_CONNECTION_ID:
9636
0
      rv = conn_recv_new_connection_id(conn, &fr.new_connection_id);
9637
0
      if (rv != 0) {
9638
0
        return rv;
9639
0
      }
9640
0
      recv_ncid = 1;
9641
0
      break;
9642
0
    case NGTCP2_FRAME_RETIRE_CONNECTION_ID:
9643
0
      rv =
9644
0
        conn_recv_retire_connection_id(conn, &hd, &fr.retire_connection_id, ts);
9645
0
      if (rv != 0) {
9646
0
        return rv;
9647
0
      }
9648
0
      non_probing_pkt = 1;
9649
0
      break;
9650
0
    case NGTCP2_FRAME_NEW_TOKEN:
9651
0
      rv = conn_recv_new_token(conn, &fr.new_token);
9652
0
      if (rv != 0) {
9653
0
        return rv;
9654
0
      }
9655
0
      non_probing_pkt = 1;
9656
0
      break;
9657
0
    case NGTCP2_FRAME_HANDSHAKE_DONE:
9658
0
      rv = conn_recv_handshake_done(conn, ts);
9659
0
      if (rv != 0) {
9660
0
        return rv;
9661
0
      }
9662
0
      non_probing_pkt = 1;
9663
0
      break;
9664
0
    case NGTCP2_FRAME_STREAMS_BLOCKED_BIDI:
9665
0
      rv = conn_recv_streams_blocked_bidi(conn, &fr.streams_blocked);
9666
0
      if (rv != 0) {
9667
0
        return rv;
9668
0
      }
9669
0
      non_probing_pkt = 1;
9670
0
      break;
9671
0
    case NGTCP2_FRAME_STREAMS_BLOCKED_UNI:
9672
0
      rv = conn_recv_streams_blocked_uni(conn, &fr.streams_blocked);
9673
0
      if (rv != 0) {
9674
0
        return rv;
9675
0
      }
9676
0
      non_probing_pkt = 1;
9677
0
      break;
9678
0
    case NGTCP2_FRAME_STREAM_DATA_BLOCKED:
9679
0
      rv = conn_recv_stream_data_blocked(conn, &fr.stream_data_blocked);
9680
0
      if (rv != 0) {
9681
0
        return rv;
9682
0
      }
9683
0
      non_probing_pkt = 1;
9684
0
      break;
9685
0
    case NGTCP2_FRAME_DATA_BLOCKED:
9686
0
      rv = conn_recv_data_blocked(conn, &fr.data_blocked);
9687
0
      if (rv != 0) {
9688
0
        return rv;
9689
0
      }
9690
0
      non_probing_pkt = 1;
9691
0
      break;
9692
0
    case NGTCP2_FRAME_DATAGRAM:
9693
0
    case NGTCP2_FRAME_DATAGRAM_LEN:
9694
0
      if ((uint64_t)nread >
9695
0
          conn->local.transport_params.max_datagram_frame_size) {
9696
0
        return NGTCP2_ERR_PROTO;
9697
0
      }
9698
0
      rv = conn_recv_datagram(conn, &fr.datagram);
9699
0
      if (rv != 0) {
9700
0
        return rv;
9701
0
      }
9702
0
      non_probing_pkt = 1;
9703
0
      break;
9704
0
    }
9705
9706
0
    ngtcp2_qlog_write_frame(&conn->qlog, &fr);
9707
0
  }
9708
9709
0
  ngtcp2_qlog_pkt_received_end(&conn->qlog, &hd, pktlen);
9710
9711
0
  if (recv_ncid) {
9712
0
    rv = conn_post_process_recv_new_connection_id(conn, ts);
9713
0
    if (rv != 0) {
9714
0
      return rv;
9715
0
    }
9716
0
  }
9717
9718
0
  if (conn->server && hd.type == NGTCP2_PKT_1RTT &&
9719
0
      !ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
9720
0
    if (non_probing_pkt && pktns->acktr.max_pkt_num < hd.pkt_num &&
9721
0
        !conn_path_validation_in_progress(conn, path)) {
9722
0
      rv = conn_recv_non_probing_pkt_on_new_path(conn, path, dgramlen,
9723
0
                                                 new_cid_used, ts);
9724
0
      if (rv != 0) {
9725
0
        if (ngtcp2_err_is_fatal(rv)) {
9726
0
          return rv;
9727
0
        }
9728
9729
        /* DCID is not available.  Just continue. */
9730
0
        assert(NGTCP2_ERR_CONN_ID_BLOCKED == rv);
9731
0
      }
9732
0
    } else {
9733
0
      rv = conn_recv_pkt_from_new_path(conn, path, dgramlen,
9734
0
                                       path_challenge_recved, ts);
9735
0
      if (rv != 0) {
9736
0
        if (ngtcp2_err_is_fatal(rv)) {
9737
0
          return rv;
9738
0
        }
9739
9740
        /* DCID is not available.  Just continue. */
9741
0
        assert(NGTCP2_ERR_CONN_ID_BLOCKED == rv);
9742
0
      }
9743
0
    }
9744
0
  }
9745
9746
0
  if (hd.type == NGTCP2_PKT_1RTT) {
9747
0
    if (ckm == conn->crypto.key_update.new_rx_ckm) {
9748
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "rotate keys");
9749
0
      conn_rotate_keys(conn, hd.pkt_num, /* initiator = */ 0);
9750
0
    } else if (ckm->pkt_num > hd.pkt_num) {
9751
0
      ckm->pkt_num = hd.pkt_num;
9752
0
    }
9753
9754
0
    if (conn->server && conn->early.ckm &&
9755
0
        conn->early.discard_started_ts == UINT64_MAX) {
9756
0
      conn->early.discard_started_ts = ts;
9757
0
    }
9758
9759
0
    if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
9760
0
      conn_update_keep_alive_last_ts(conn, ts);
9761
0
    }
9762
0
  }
9763
9764
0
  rv = pktns_commit_recv_pkt_num(pktns, hd.pkt_num, pi, require_ack, pkt_ts);
9765
0
  if (rv != 0) {
9766
0
    return rv;
9767
0
  }
9768
9769
0
  if (require_ack &&
9770
0
      (++pktns->acktr.rx_npkt >= conn->local.settings.ack_thresh ||
9771
0
       (pi->ecn & NGTCP2_ECN_MASK) == NGTCP2_ECN_CE)) {
9772
0
    ngtcp2_acktr_immediate_ack(&pktns->acktr);
9773
0
  }
9774
9775
0
  conn_restart_timer_on_read(conn, ts);
9776
9777
0
  ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
9778
9779
0
  return conn->state == NGTCP2_CS_DRAINING ? NGTCP2_ERR_DRAINING
9780
0
                                           : (ngtcp2_ssize)pktlen;
9781
0
}
9782
9783
/*
9784
 * conn_process_buffered_protected_pkt processes buffered 0RTT or 1RTT
9785
 * packets.
9786
 *
9787
 * This function returns 0 if it succeeds, or the same negative error
9788
 * codes from conn_recv_pkt.
9789
 */
9790
static int conn_process_buffered_protected_pkt(ngtcp2_conn *conn,
9791
                                               ngtcp2_pktns *pktns,
9792
0
                                               ngtcp2_tstamp ts) {
9793
0
  ngtcp2_ssize nread;
9794
0
  ngtcp2_pkt_chain **ppc, *next;
9795
0
  int rv;
9796
9797
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
9798
0
                  "processing buffered protected packet");
9799
9800
0
  for (ppc = &pktns->rx.buffed_pkts; *ppc;) {
9801
0
    next = (*ppc)->next;
9802
0
    nread = conn_recv_pkt(conn, &(*ppc)->path.path, &(*ppc)->pi, (*ppc)->pkt,
9803
0
                          (*ppc)->pktlen, (*ppc)->dgramlen, (*ppc)->ts, ts);
9804
0
    if (nread < 0 && !ngtcp2_err_is_fatal((int)nread) &&
9805
0
        nread != NGTCP2_ERR_DRAINING) {
9806
      /* TODO We don't know this is the first QUIC packet in a
9807
         datagram. */
9808
0
      rv = conn_on_stateless_reset(conn, &(*ppc)->path.path, (*ppc)->pkt,
9809
0
                                   (*ppc)->pktlen);
9810
0
      if (rv == 0) {
9811
0
        ngtcp2_pkt_chain_del(*ppc, conn->mem);
9812
0
        *ppc = next;
9813
0
        return NGTCP2_ERR_DRAINING;
9814
0
      }
9815
0
    }
9816
9817
0
    ngtcp2_pkt_chain_del(*ppc, conn->mem);
9818
0
    *ppc = next;
9819
0
    if (nread < 0) {
9820
0
      if (nread == NGTCP2_ERR_DISCARD_PKT) {
9821
0
        ++conn->cstat.pkt_discarded;
9822
0
        continue;
9823
0
      }
9824
0
      return (int)nread;
9825
0
    }
9826
0
  }
9827
9828
0
  return 0;
9829
0
}
9830
9831
/*
9832
 * conn_process_buffered_handshake_pkt processes buffered Handshake
9833
 * packets.
9834
 *
9835
 * This function returns 0 if it succeeds, or the same negative error
9836
 * codes from conn_recv_handshake_pkt.
9837
 */
9838
static int conn_process_buffered_handshake_pkt(ngtcp2_conn *conn,
9839
0
                                               ngtcp2_tstamp ts) {
9840
0
  ngtcp2_pktns *pktns = conn->hs_pktns;
9841
0
  ngtcp2_ssize nread;
9842
0
  ngtcp2_pkt_chain **ppc, *next;
9843
9844
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
9845
0
                  "processing buffered handshake packet");
9846
9847
0
  for (ppc = &pktns->rx.buffed_pkts; *ppc;) {
9848
0
    next = (*ppc)->next;
9849
0
    nread = conn_recv_handshake_pkt(conn, &(*ppc)->path.path, &(*ppc)->pi,
9850
0
                                    (*ppc)->pkt, (*ppc)->pktlen,
9851
0
                                    (*ppc)->dgramlen, (*ppc)->ts, ts);
9852
0
    ngtcp2_pkt_chain_del(*ppc, conn->mem);
9853
0
    *ppc = next;
9854
0
    if (nread < 0) {
9855
0
      if (nread == NGTCP2_ERR_DISCARD_PKT) {
9856
0
        ++conn->cstat.pkt_discarded;
9857
0
        continue;
9858
0
      }
9859
0
      return (int)nread;
9860
0
    }
9861
0
  }
9862
9863
0
  return 0;
9864
0
}
9865
9866
0
static void conn_sync_stream_id_limit(ngtcp2_conn *conn) {
9867
0
  ngtcp2_transport_params *params = conn->remote.transport_params;
9868
9869
0
  assert(params);
9870
9871
0
  conn->local.bidi.max_streams = params->initial_max_streams_bidi;
9872
0
  conn->local.uni.max_streams = params->initial_max_streams_uni;
9873
0
}
9874
9875
0
static int strm_set_max_offset(void *data, void *ptr) {
9876
0
  ngtcp2_conn *conn = ptr;
9877
0
  ngtcp2_transport_params *params = conn->remote.transport_params;
9878
0
  ngtcp2_strm *strm = data;
9879
0
  uint64_t max_offset;
9880
0
  int rv;
9881
9882
0
  assert(params);
9883
9884
0
  if (!conn_local_stream(conn, strm->stream_id)) {
9885
0
    return 0;
9886
0
  }
9887
9888
0
  if (bidi_stream(strm->stream_id)) {
9889
0
    max_offset = params->initial_max_stream_data_bidi_remote;
9890
0
  } else {
9891
0
    max_offset = params->initial_max_stream_data_uni;
9892
0
  }
9893
9894
0
  if (strm->tx.max_offset < max_offset) {
9895
0
    strm->tx.max_offset = max_offset;
9896
9897
    /* Don't call callback if stream is half-closed local */
9898
0
    if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
9899
0
      return 0;
9900
0
    }
9901
9902
0
    rv = conn_call_extend_max_stream_data(conn, strm, strm->stream_id,
9903
0
                                          strm->tx.max_offset);
9904
0
    if (rv != 0) {
9905
0
      return rv;
9906
0
    }
9907
0
  }
9908
9909
0
  return 0;
9910
0
}
9911
9912
0
static int conn_sync_stream_data_limit(ngtcp2_conn *conn) {
9913
0
  return ngtcp2_map_each(&conn->strms, strm_set_max_offset, conn);
9914
0
}
9915
9916
/*
9917
 * conn_handshake_completed is called once cryptographic handshake has
9918
 * completed.
9919
 *
9920
 * This function returns 0 if it succeeds, or one of the following
9921
 * negative error codes:
9922
 *
9923
 * NGTCP2_ERR_CALLBACK_FAILURE
9924
 *     User callback failed.
9925
 */
9926
0
static int conn_handshake_completed(ngtcp2_conn *conn) {
9927
0
  int rv;
9928
9929
0
  conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED;
9930
9931
0
  rv = conn_call_handshake_completed(conn);
9932
0
  if (rv != 0) {
9933
0
    return rv;
9934
0
  }
9935
9936
0
  if (conn->local.bidi.max_streams > 0) {
9937
0
    rv = conn_call_extend_max_local_streams_bidi(conn,
9938
0
                                                 conn->local.bidi.max_streams);
9939
0
    if (rv != 0) {
9940
0
      return rv;
9941
0
    }
9942
0
  }
9943
0
  if (conn->local.uni.max_streams > 0) {
9944
0
    rv =
9945
0
      conn_call_extend_max_local_streams_uni(conn, conn->local.uni.max_streams);
9946
0
    if (rv != 0) {
9947
0
      return rv;
9948
0
    }
9949
0
  }
9950
9951
0
  return 0;
9952
0
}
9953
9954
/*
9955
 * conn_recv_cpkt processes compound packet after handshake.  The
9956
 * buffer pointed by |pkt| might contain multiple packets.  The 1RTT
9957
 * packet must be the last one because it does not have payload length
9958
 * field.
9959
 *
9960
 * This function returns 0 if it succeeds, or the same negative error
9961
 * codes from conn_recv_pkt except for NGTCP2_ERR_DISCARD_PKT.
9962
 */
9963
static int conn_recv_cpkt(ngtcp2_conn *conn, const ngtcp2_path *path,
9964
                          const ngtcp2_pkt_info *pi, const uint8_t *pkt,
9965
0
                          size_t pktlen, ngtcp2_tstamp ts) {
9966
0
  ngtcp2_ssize nread;
9967
0
  int rv;
9968
0
  const uint8_t *origpkt = pkt;
9969
0
  size_t dgramlen = pktlen;
9970
9971
0
  if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
9972
0
    conn->dcid.current.bytes_recv += dgramlen;
9973
0
  }
9974
9975
0
  if (conn->server && conn->local.transport_params.disable_active_migration &&
9976
0
      !ngtcp2_addr_eq(&conn->dcid.current.ps.path.local, &path->local) &&
9977
0
      !conn_server_preferred_addr_migration(conn, &path->local)) {
9978
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
9979
0
                    "packet is discarded because active migration is disabled");
9980
9981
0
    return 0;
9982
0
  }
9983
9984
0
  while (pktlen) {
9985
0
    nread = conn_recv_pkt(conn, path, pi, pkt, pktlen, dgramlen, ts, ts);
9986
0
    if (nread < 0) {
9987
0
      if (ngtcp2_err_is_fatal((int)nread)) {
9988
0
        return (int)nread;
9989
0
      }
9990
9991
0
      if (nread == NGTCP2_ERR_DRAINING) {
9992
0
        return NGTCP2_ERR_DRAINING;
9993
0
      }
9994
9995
0
      if (origpkt == pkt) {
9996
0
        rv = conn_on_stateless_reset(conn, path, origpkt, dgramlen);
9997
0
        if (rv == 0) {
9998
0
          return NGTCP2_ERR_DRAINING;
9999
0
        }
10000
0
      }
10001
0
      if (nread == NGTCP2_ERR_DISCARD_PKT) {
10002
0
        ++conn->cstat.pkt_discarded;
10003
0
        return 0;
10004
0
      }
10005
0
      return (int)nread;
10006
0
    }
10007
10008
0
    assert(pktlen >= (size_t)nread);
10009
0
    pkt += nread;
10010
0
    pktlen -= (size_t)nread;
10011
10012
0
    ++conn->cstat.pkt_recv;
10013
0
    conn->cstat.bytes_recv += (uint64_t)nread;
10014
10015
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_PKT,
10016
0
                     "read packet %td left %zu", nread, pktlen);
10017
0
  }
10018
10019
0
  return 0;
10020
0
}
10021
10022
/*
10023
 * conn_enqueue_handshake_done enqueues HANDSHAKE_DONE frame for
10024
 * transmission.
10025
 */
10026
0
static int conn_enqueue_handshake_done(ngtcp2_conn *conn) {
10027
0
  ngtcp2_pktns *pktns = &conn->pktns;
10028
0
  ngtcp2_frame_chain *nfrc;
10029
0
  int rv;
10030
10031
0
  assert(conn->server);
10032
10033
0
  rv = ngtcp2_frame_chain_objalloc_new(&nfrc, &conn->frc_objalloc);
10034
0
  if (rv != 0) {
10035
0
    return rv;
10036
0
  }
10037
10038
0
  nfrc->fr.handshake_done.type = NGTCP2_FRAME_HANDSHAKE_DONE;
10039
0
  nfrc->next = pktns->tx.frq;
10040
0
  pktns->tx.frq = nfrc;
10041
10042
0
  return 0;
10043
0
}
10044
10045
/**
10046
 * @function
10047
 *
10048
 * `conn_read_handshake` performs QUIC cryptographic handshake by
10049
 * reading given data.  |pkt| points to the buffer to read and
10050
 * |pktlen| is the length of the buffer.  |path| is the network path.
10051
 *
10052
 * This function returns the number of bytes processed.  Unless the
10053
 * last packet is 1RTT packet and an application decryption key has
10054
 * been installed, it returns |pktlen| if it succeeds.  If it finds
10055
 * 1RTT packet and an application decryption key has been installed,
10056
 * it returns the number of bytes just before 1RTT packet begins.
10057
 *
10058
 * This function returns the number of bytes processed if it succeeds,
10059
 * or one of the following negative error codes: (TBD).
10060
 */
10061
static ngtcp2_ssize conn_read_handshake(ngtcp2_conn *conn,
10062
                                        const ngtcp2_path *path,
10063
                                        const ngtcp2_pkt_info *pi,
10064
                                        const uint8_t *pkt, size_t pktlen,
10065
0
                                        ngtcp2_tstamp ts) {
10066
0
  int rv;
10067
0
  ngtcp2_ssize nread;
10068
10069
0
  switch (conn->state) {
10070
0
  case NGTCP2_CS_CLIENT_INITIAL:
10071
    /* TODO Better to log something when we ignore input */
10072
0
    return (ngtcp2_ssize)pktlen;
10073
0
  case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
10074
0
    nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
10075
0
    if (nread < 0) {
10076
0
      return nread;
10077
0
    }
10078
10079
0
    if (conn->state == NGTCP2_CS_CLIENT_INITIAL) {
10080
      /* Retry packet was received */
10081
0
      return (ngtcp2_ssize)pktlen;
10082
0
    }
10083
10084
0
    assert(conn->hs_pktns);
10085
10086
0
    if (conn->hs_pktns->crypto.rx.ckm && conn->in_pktns) {
10087
0
      rv = conn_process_buffered_handshake_pkt(conn, ts);
10088
0
      if (rv != 0) {
10089
0
        return rv;
10090
0
      }
10091
0
    }
10092
10093
0
    if (conn_is_tls_handshake_completed(conn) &&
10094
0
        !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
10095
0
      rv = conn_handshake_completed(conn);
10096
0
      if (rv != 0) {
10097
0
        return rv;
10098
0
      }
10099
10100
0
      rv = conn_process_buffered_protected_pkt(conn, &conn->pktns, ts);
10101
0
      if (rv != 0) {
10102
0
        return rv;
10103
0
      }
10104
0
    }
10105
10106
0
    return nread;
10107
0
  case NGTCP2_CS_SERVER_INITIAL:
10108
0
    nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
10109
0
    if (nread < 0) {
10110
0
      return nread;
10111
0
    }
10112
10113
    /*
10114
     * Client Hello might not fit into single Initial packet (e.g.,
10115
     * resuming session with client authentication).  If we get Client
10116
     * Initial which does not increase offset or it is 0RTT packet
10117
     * buffered, perform address validation in order to buffer
10118
     * validated data only.
10119
     */
10120
0
    if (ngtcp2_strm_rx_offset(&conn->in_pktns->crypto.strm) == 0) {
10121
0
      if (conn->in_pktns->crypto.strm.rx.rob &&
10122
0
          ngtcp2_rob_data_buffered(conn->in_pktns->crypto.strm.rx.rob)) {
10123
        /* Address has been validated with token */
10124
0
        if (conn->local.settings.tokenlen) {
10125
0
          return nread;
10126
0
        }
10127
0
        return NGTCP2_ERR_RETRY;
10128
0
      }
10129
      /* If CRYPTO frame is not processed, just drop connection. */
10130
0
      return NGTCP2_ERR_DROP_CONN;
10131
0
    }
10132
10133
    /* Process re-ordered 0-RTT packets which arrived before Initial
10134
       packet. */
10135
0
    if (conn->early.ckm) {
10136
0
      assert(conn->in_pktns);
10137
10138
0
      rv = conn_process_buffered_protected_pkt(conn, conn->in_pktns, ts);
10139
0
      if (rv != 0) {
10140
0
        return rv;
10141
0
      }
10142
0
    }
10143
10144
0
    return nread;
10145
0
  case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
10146
0
    nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
10147
0
    if (nread < 0) {
10148
0
      return nread;
10149
0
    }
10150
10151
0
    if (conn->hs_pktns->crypto.rx.ckm) {
10152
0
      rv = conn_process_buffered_handshake_pkt(conn, ts);
10153
0
      if (rv != 0) {
10154
0
        return rv;
10155
0
      }
10156
0
    }
10157
10158
0
    if (conn->hs_pktns->acktr.max_pkt_num != -1) {
10159
0
      ngtcp2_conn_discard_initial_state(conn, ts);
10160
0
    }
10161
10162
0
    if (!conn_is_tls_handshake_completed(conn)) {
10163
      /* If server hits amplification limit, it cancels loss detection
10164
         timer.  If server receives a packet from client, the limit is
10165
         increased and server can send more.  If server has
10166
         ack-eliciting Initial or Handshake packets, it should resend
10167
         it if timer fired but timer is not armed in this case.  So
10168
         instead of resending Initial/Handshake packets, if server has
10169
         1RTT data to send, it might send them and then might hit
10170
         amplification limit again until it hits stream data limit.
10171
         Initial/Handshake data is not resent.  In order to avoid this
10172
         situation, try to arm loss detection and check the expiry
10173
         here so that on next write call, we can resend
10174
         Initial/Handshake first. */
10175
0
      if (conn->cstat.loss_detection_timer == UINT64_MAX) {
10176
0
        ngtcp2_conn_set_loss_detection_timer(conn, ts);
10177
0
        if (ngtcp2_conn_loss_detection_expiry(conn) <= ts) {
10178
0
          rv = ngtcp2_conn_on_loss_detection_timer(conn, ts);
10179
0
          if (rv != 0) {
10180
0
            return rv;
10181
0
          }
10182
0
        }
10183
0
      }
10184
10185
0
      if ((size_t)nread < pktlen) {
10186
        /* We have 1RTT packet and application rx key, but the
10187
           handshake has not completed yet. */
10188
0
        ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
10189
0
                         "buffering 1RTT packet len=%zu",
10190
0
                         pktlen - (size_t)nread);
10191
10192
0
        rv = conn_buffer_pkt(conn, &conn->pktns, path, pi, pkt + nread,
10193
0
                             pktlen - (size_t)nread, pktlen, ts);
10194
0
        if (rv != 0) {
10195
0
          assert(ngtcp2_err_is_fatal(rv));
10196
0
          return rv;
10197
0
        }
10198
10199
0
        return (ngtcp2_ssize)pktlen;
10200
0
      }
10201
10202
0
      return nread;
10203
0
    }
10204
10205
0
    if (!(conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED)) {
10206
0
      return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
10207
0
    }
10208
10209
0
    rv = conn_handshake_completed(conn);
10210
0
    if (rv != 0) {
10211
0
      return rv;
10212
0
    }
10213
0
    conn->state = NGTCP2_CS_POST_HANDSHAKE;
10214
10215
0
    rv = conn_call_activate_dcid(conn, &conn->dcid.current);
10216
0
    if (rv != 0) {
10217
0
      return rv;
10218
0
    }
10219
10220
0
    rv = conn_process_buffered_protected_pkt(conn, &conn->pktns, ts);
10221
0
    if (rv != 0) {
10222
0
      return rv;
10223
0
    }
10224
10225
0
    ngtcp2_conn_discard_handshake_state(conn, ts);
10226
10227
0
    rv = conn_enqueue_handshake_done(conn);
10228
0
    if (rv != 0) {
10229
0
      return rv;
10230
0
    }
10231
10232
0
    if (!conn->local.settings.no_pmtud) {
10233
0
      rv = conn_start_pmtud(conn);
10234
0
      if (rv != 0) {
10235
0
        return rv;
10236
0
      }
10237
0
    }
10238
10239
0
    conn->handshake_confirmed_ts = ts;
10240
10241
    /* Re-arm loss detection timer here after handshake has been
10242
       confirmed. */
10243
0
    ngtcp2_conn_set_loss_detection_timer(conn, ts);
10244
10245
0
    return nread;
10246
0
  case NGTCP2_CS_CLOSING:
10247
0
    return NGTCP2_ERR_CLOSING;
10248
0
  case NGTCP2_CS_DRAINING:
10249
0
    return NGTCP2_ERR_DRAINING;
10250
0
  default:
10251
0
    return (ngtcp2_ssize)pktlen;
10252
0
  }
10253
0
}
10254
10255
int ngtcp2_conn_read_pkt_versioned(ngtcp2_conn *conn, const ngtcp2_path *path,
10256
                                   int pkt_info_version,
10257
                                   const ngtcp2_pkt_info *pi,
10258
                                   const uint8_t *pkt, size_t pktlen,
10259
0
                                   ngtcp2_tstamp ts) {
10260
0
  int rv = 0;
10261
0
  ngtcp2_ssize nread = 0;
10262
0
  const ngtcp2_pkt_info zero_pi = {0};
10263
0
  (void)pkt_info_version;
10264
10265
0
  assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
10266
10267
0
  conn_update_timestamp(conn, ts);
10268
10269
0
  ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON, "recv packet len=%zu",
10270
0
                   pktlen);
10271
10272
0
  if (pktlen == 0) {
10273
0
    return 0;
10274
0
  }
10275
10276
  /* client does not expect a packet from unknown path. */
10277
0
  if (!conn->server && !ngtcp2_path_eq(&conn->dcid.current.ps.path, path) &&
10278
0
      (!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path)) &&
10279
0
      !ngtcp2_dcidtr_check_path_retired(&conn->dcid.dtr, path)) {
10280
0
    ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
10281
0
                    "ignore packet from unknown path");
10282
0
    ++conn->cstat.pkt_discarded;
10283
10284
0
    return 0;
10285
0
  }
10286
10287
0
  if (!pi) {
10288
0
    pi = &zero_pi;
10289
0
  }
10290
10291
0
  switch (conn->state) {
10292
0
  case NGTCP2_CS_CLIENT_INITIAL:
10293
0
  case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
10294
0
    nread = conn_read_handshake(conn, path, pi, pkt, pktlen, ts);
10295
0
    if (nread < 0) {
10296
0
      return (int)nread;
10297
0
    }
10298
10299
0
    if ((size_t)nread == pktlen) {
10300
0
      return 0;
10301
0
    }
10302
10303
0
    assert(conn->pktns.crypto.rx.ckm);
10304
10305
0
    pkt += nread;
10306
0
    pktlen -= (size_t)nread;
10307
10308
0
    break;
10309
0
  case NGTCP2_CS_SERVER_INITIAL:
10310
0
  case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
10311
0
    if (!ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
10312
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
10313
0
                      "ignore packet from unknown path during handshake");
10314
10315
0
      if (conn->state == NGTCP2_CS_SERVER_INITIAL &&
10316
0
          ngtcp2_strm_rx_offset(&conn->in_pktns->crypto.strm) == 0 &&
10317
0
          (!conn->in_pktns->crypto.strm.rx.rob ||
10318
0
           !ngtcp2_rob_data_buffered(conn->in_pktns->crypto.strm.rx.rob))) {
10319
0
        return NGTCP2_ERR_DROP_CONN;
10320
0
      }
10321
10322
0
      return 0;
10323
0
    }
10324
10325
0
    nread = conn_read_handshake(conn, path, pi, pkt, pktlen, ts);
10326
0
    if (nread < 0) {
10327
0
      return (int)nread;
10328
0
    }
10329
10330
0
    if ((size_t)nread == pktlen) {
10331
0
      return 0;
10332
0
    }
10333
10334
0
    assert(conn->pktns.crypto.rx.ckm);
10335
10336
0
    pkt += nread;
10337
0
    pktlen -= (size_t)nread;
10338
10339
0
    break;
10340
0
  case NGTCP2_CS_CLOSING:
10341
0
    return NGTCP2_ERR_CLOSING;
10342
0
  case NGTCP2_CS_DRAINING:
10343
0
    return NGTCP2_ERR_DRAINING;
10344
0
  case NGTCP2_CS_POST_HANDSHAKE:
10345
0
    rv = conn_prepare_key_update(conn, ts);
10346
0
    if (rv != 0) {
10347
0
      return rv;
10348
0
    }
10349
0
    break;
10350
0
  default:
10351
0
    ngtcp2_unreachable();
10352
0
  }
10353
10354
0
  return conn_recv_cpkt(conn, path, pi, pkt, pktlen, ts);
10355
0
}
10356
10357
0
int ngtcp2_conn_continue_handshake(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
10358
0
  int rv;
10359
0
  ngtcp2_encryption_level encryption_level;
10360
0
  uint64_t offset;
10361
10362
0
  conn_update_timestamp(conn, ts);
10363
10364
0
  switch (conn->state) {
10365
0
  case NGTCP2_CS_CLIENT_INITIAL:
10366
0
  case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
10367
0
  case NGTCP2_CS_SERVER_INITIAL:
10368
0
  case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
10369
    /* Most of the handshake interruption happens in Initial
10370
       encryption level, but this might not be the case depending on
10371
       the TLS stack and its functionality and where interruption
10372
       occurs.  After all, we do not need to support all kinds of
10373
       interruptions. */
10374
0
    if (conn->in_pktns) {
10375
0
      encryption_level = NGTCP2_ENCRYPTION_LEVEL_INITIAL;
10376
0
      offset = ngtcp2_strm_rx_offset(&conn->in_pktns->crypto.strm);
10377
0
    } else if (conn->hs_pktns) {
10378
0
      encryption_level = NGTCP2_ENCRYPTION_LEVEL_HANDSHAKE;
10379
0
      offset = ngtcp2_strm_rx_offset(&conn->hs_pktns->crypto.strm);
10380
0
    } else {
10381
0
      return 0;
10382
0
    }
10383
10384
0
    rv = conn_call_recv_crypto_data(conn, encryption_level, offset, NULL, 0);
10385
0
    if (rv != 0) {
10386
0
      return rv;
10387
0
    }
10388
10389
0
    return (int)conn_read_handshake(conn, /* path = */ NULL, /* pi = */ NULL,
10390
0
                                    /* pkt = */ NULL, 0, ts);
10391
0
  case NGTCP2_CS_CLOSING:
10392
0
    return NGTCP2_ERR_CLOSING;
10393
0
  case NGTCP2_CS_DRAINING:
10394
0
    return NGTCP2_ERR_DRAINING;
10395
0
  default:
10396
0
    return 0;
10397
0
  }
10398
0
}
10399
10400
/*
10401
 * conn_check_pkt_num_exhausted returns nonzero if packet number is
10402
 * exhausted in at least one of packet number space.
10403
 */
10404
0
static int conn_check_pkt_num_exhausted(ngtcp2_conn *conn) {
10405
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
10406
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
10407
10408
0
  return (in_pktns && in_pktns->tx.last_pkt_num == NGTCP2_MAX_PKT_NUM) ||
10409
0
         (hs_pktns && hs_pktns->tx.last_pkt_num == NGTCP2_MAX_PKT_NUM) ||
10410
0
         conn->pktns.tx.last_pkt_num == NGTCP2_MAX_PKT_NUM;
10411
0
}
10412
10413
/*
10414
 * conn_retransmit_retry_early retransmits 0RTT packet after Retry is
10415
 * received from server.
10416
 */
10417
static ngtcp2_ssize
10418
conn_retransmit_retry_early(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
10419
                            uint8_t *dest, size_t destlen, size_t dgram_offset,
10420
0
                            uint8_t flags, ngtcp2_tstamp ts) {
10421
0
  return conn_write_pkt(conn, pi, dest, destlen, dgram_offset, NULL,
10422
0
                        NGTCP2_PKT_0RTT, flags, ts);
10423
0
}
10424
10425
/*
10426
 * conn_handshake_probe_left returns nonzero if there are probe
10427
 * packets to be sent for Initial or Handshake packet number space
10428
 * left.
10429
 */
10430
0
static int conn_handshake_probe_left(ngtcp2_conn *conn) {
10431
0
  return (conn->in_pktns && conn->in_pktns->rtb.probe_pkt_left) ||
10432
0
         conn->hs_pktns->rtb.probe_pkt_left;
10433
0
}
10434
10435
/*
10436
 * conn_validate_early_transport_params_limits validates that the
10437
 * limits in transport parameters remembered by client for early data
10438
 * are not reduced.  This function is only used by client and should
10439
 * only be called when early data is accepted by server.
10440
 */
10441
0
static int conn_validate_early_transport_params_limits(ngtcp2_conn *conn) {
10442
0
  const ngtcp2_transport_params *params = conn->remote.transport_params;
10443
10444
0
  assert(!conn->server);
10445
0
  assert(params);
10446
10447
0
  if (conn->early.transport_params.active_connection_id_limit >
10448
0
        params->active_connection_id_limit ||
10449
0
      conn->early.transport_params.initial_max_data >
10450
0
        params->initial_max_data ||
10451
0
      conn->early.transport_params.initial_max_stream_data_bidi_local >
10452
0
        params->initial_max_stream_data_bidi_local ||
10453
0
      conn->early.transport_params.initial_max_stream_data_bidi_remote >
10454
0
        params->initial_max_stream_data_bidi_remote ||
10455
0
      conn->early.transport_params.initial_max_stream_data_uni >
10456
0
        params->initial_max_stream_data_uni ||
10457
0
      conn->early.transport_params.initial_max_streams_bidi >
10458
0
        params->initial_max_streams_bidi ||
10459
0
      conn->early.transport_params.initial_max_streams_uni >
10460
0
        params->initial_max_streams_uni ||
10461
0
      conn->early.transport_params.max_datagram_frame_size >
10462
0
        params->max_datagram_frame_size) {
10463
0
    return NGTCP2_ERR_PROTO;
10464
0
  }
10465
10466
0
  return 0;
10467
0
}
10468
10469
/*
10470
 * conn_write_handshake writes QUIC handshake packets to the buffer
10471
 * pointed by |dest| of length |destlen|.  |write_datalen| specifies
10472
 * the expected length of 0RTT packet payload.  Specify 0 to
10473
 * |write_datalen| if there is no such data.
10474
 *
10475
 * This function returns the number of bytes written to the buffer, or
10476
 * one of the following negative error codes:
10477
 *
10478
 * NGTCP2_ERR_PKT_NUM_EXHAUSTED
10479
 *     Packet number is exhausted.
10480
 * NGTCP2_ERR_NOMEM
10481
 *     Out of memory
10482
 * NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM
10483
 *     Required transport parameter is missing.
10484
 * NGTCP2_CS_CLOSING
10485
 *     Connection is in closing state.
10486
 * NGTCP2_CS_DRAINING
10487
 *     Connection is in draining state.
10488
 *
10489
 * In addition to the above negative error codes, the same error codes
10490
 * from conn_recv_pkt may also be returned.
10491
 */
10492
static ngtcp2_ssize conn_write_handshake(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
10493
                                         uint8_t *dest, size_t destlen,
10494
                                         uint8_t wflags, uint64_t write_datalen,
10495
0
                                         ngtcp2_tstamp ts) {
10496
0
  int rv;
10497
0
  ngtcp2_ssize res = 0, nwrite = 0, early_spktlen = 0;
10498
0
  size_t origlen = destlen;
10499
0
  uint64_t pending_early_datalen;
10500
0
  ngtcp2_preferred_addr *paddr;
10501
0
  ngtcp2_stateless_reset_token token;
10502
10503
0
  switch (conn->state) {
10504
0
  case NGTCP2_CS_CLIENT_INITIAL:
10505
0
    pending_early_datalen = conn_retry_early_payloadlen(conn);
10506
0
    if (pending_early_datalen) {
10507
0
      write_datalen = pending_early_datalen;
10508
0
    }
10509
10510
0
    if (!(conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY)) {
10511
0
      nwrite =
10512
0
        conn_write_client_initial(conn, pi, dest, destlen, write_datalen, ts);
10513
0
      if (nwrite <= 0) {
10514
0
        return nwrite;
10515
0
      }
10516
0
    } else {
10517
0
      nwrite =
10518
0
        conn_write_handshake_pkt(conn, pi, dest, destlen, 0, NGTCP2_PKT_INITIAL,
10519
0
                                 NGTCP2_WRITE_PKT_FLAG_NONE, write_datalen, ts);
10520
0
      if (nwrite < 0) {
10521
0
        return nwrite;
10522
0
      }
10523
0
    }
10524
10525
0
    if (pending_early_datalen) {
10526
0
      early_spktlen = conn_retransmit_retry_early(
10527
0
        conn, pi, dest + nwrite, destlen - (size_t)nwrite, (size_t)nwrite,
10528
0
        wflags | (nwrite ? NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING
10529
0
                         : NGTCP2_WRITE_PKT_FLAG_NONE),
10530
0
        ts);
10531
10532
0
      if (early_spktlen < 0) {
10533
0
        assert(ngtcp2_err_is_fatal((int)early_spktlen));
10534
0
        return early_spktlen;
10535
0
      }
10536
0
    }
10537
10538
0
    conn->state = NGTCP2_CS_CLIENT_WAIT_HANDSHAKE;
10539
10540
0
    res = nwrite + early_spktlen;
10541
10542
0
    return res;
10543
0
  case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
10544
0
    pending_early_datalen = 0;
10545
10546
0
    if (!conn_handshake_probe_left(conn) && conn_cwnd_is_zero(conn)) {
10547
0
      destlen = 0;
10548
0
    } else {
10549
0
      if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
10550
0
        pending_early_datalen = conn_retry_early_payloadlen(conn);
10551
0
        if (pending_early_datalen) {
10552
0
          write_datalen = pending_early_datalen;
10553
0
        }
10554
0
      }
10555
10556
0
      nwrite =
10557
0
        conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
10558
0
      if (nwrite < 0) {
10559
0
        return nwrite;
10560
0
      }
10561
10562
0
      res += nwrite;
10563
0
      dest += nwrite;
10564
0
      destlen -= (size_t)nwrite;
10565
0
    }
10566
10567
0
    if (!conn_is_tls_handshake_completed(conn)) {
10568
0
      if (pending_early_datalen &&
10569
0
          !(conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED)) {
10570
0
        nwrite = conn_retransmit_retry_early(
10571
0
          conn, pi, dest, destlen, (size_t)res,
10572
0
          wflags | ((nwrite &&
10573
0
                     ngtcp2_pkt_get_type_long(
10574
0
                       conn->negotiated_version ? conn->negotiated_version
10575
0
                                                : conn->client_chosen_version,
10576
0
                       *(dest - nwrite)) == NGTCP2_PKT_INITIAL)
10577
0
                      ? NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING
10578
0
                      : NGTCP2_WRITE_PKT_FLAG_NONE),
10579
0
          ts);
10580
0
        if (nwrite < 0) {
10581
0
          return nwrite;
10582
0
        }
10583
10584
0
        res += nwrite;
10585
0
      }
10586
10587
0
      if (res == 0) {
10588
0
        nwrite = conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
10589
0
        if (nwrite < 0) {
10590
0
          return nwrite;
10591
0
        }
10592
0
        res = nwrite;
10593
0
      }
10594
10595
0
      return res;
10596
0
    }
10597
10598
0
    if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
10599
0
      return res;
10600
0
    }
10601
10602
0
    if (!(conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED)) {
10603
0
      return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
10604
0
    }
10605
10606
0
    if ((conn->flags & NGTCP2_CONN_FLAG_EARLY_KEY_INSTALLED) &&
10607
0
        !(conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED)) {
10608
0
      rv = conn_validate_early_transport_params_limits(conn);
10609
0
      if (rv != 0) {
10610
0
        return rv;
10611
0
      }
10612
0
    }
10613
10614
    /* Server might increase stream data limits.  Extend it if we have
10615
       streams created for early data. */
10616
0
    rv = conn_sync_stream_data_limit(conn);
10617
0
    if (rv != 0) {
10618
0
      return rv;
10619
0
    }
10620
10621
0
    conn->state = NGTCP2_CS_POST_HANDSHAKE;
10622
10623
0
    assert(conn->remote.transport_params);
10624
10625
0
    if (conn->remote.transport_params->preferred_addr_present) {
10626
0
      assert(!ngtcp2_dcidtr_unused_full(&conn->dcid.dtr));
10627
10628
0
      paddr = &conn->remote.transport_params->preferred_addr;
10629
0
      memcpy(token.data, paddr->stateless_reset_token, sizeof(token.data));
10630
0
      ngtcp2_dcidtr_push_unused(&conn->dcid.dtr, 1, &paddr->cid, &token);
10631
10632
0
      rv = ngtcp2_gaptr_push(&conn->dcid.seqgap, 1, 1);
10633
0
      if (rv != 0) {
10634
0
        return (ngtcp2_ssize)rv;
10635
0
      }
10636
0
    }
10637
10638
0
    if (conn->remote.transport_params->stateless_reset_token_present &&
10639
0
        conn->dcid.current.seq == 0) {
10640
0
      assert(!(conn->dcid.current.flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT));
10641
0
      memcpy(token.data, conn->remote.transport_params->stateless_reset_token,
10642
0
             sizeof(token.data));
10643
0
      ngtcp2_dcid_set_token(&conn->dcid.current, &token);
10644
0
    }
10645
10646
0
    rv = conn_call_activate_dcid(conn, &conn->dcid.current);
10647
0
    if (rv != 0) {
10648
0
      return rv;
10649
0
    }
10650
10651
0
    conn_process_early_rtb(conn);
10652
10653
0
    if (!conn->local.settings.no_pmtud) {
10654
0
      rv = conn_start_pmtud(conn);
10655
0
      if (rv != 0) {
10656
0
        return rv;
10657
0
      }
10658
0
    }
10659
10660
0
    return res;
10661
0
  case NGTCP2_CS_SERVER_INITIAL:
10662
0
    nwrite =
10663
0
      conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
10664
0
    if (nwrite < 0) {
10665
0
      return nwrite;
10666
0
    }
10667
10668
0
    if (nwrite) {
10669
0
      conn->state = NGTCP2_CS_SERVER_WAIT_HANDSHAKE;
10670
0
    }
10671
10672
0
    return nwrite;
10673
0
  case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
10674
0
    if (conn_handshake_probe_left(conn) || !conn_cwnd_is_zero(conn)) {
10675
0
      nwrite =
10676
0
        conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
10677
0
      if (nwrite < 0) {
10678
0
        return nwrite;
10679
0
      }
10680
10681
0
      res += nwrite;
10682
0
    }
10683
10684
0
    if (res == 0) {
10685
0
      nwrite = conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
10686
0
      if (nwrite < 0) {
10687
0
        return nwrite;
10688
0
      }
10689
10690
0
      res += nwrite;
10691
0
    }
10692
10693
0
    return res;
10694
0
  case NGTCP2_CS_CLOSING:
10695
0
    return NGTCP2_ERR_CLOSING;
10696
0
  case NGTCP2_CS_DRAINING:
10697
0
    return NGTCP2_ERR_DRAINING;
10698
0
  default:
10699
0
    return 0;
10700
0
  }
10701
0
}
10702
10703
/**
10704
 * @function
10705
 *
10706
 * `conn_client_write_handshake` writes client side handshake data and
10707
 * 0RTT packet.
10708
 *
10709
 * In order to send STREAM data in 0RTT packet, specify
10710
 * |vmsg|->stream.  |vmsg|->stream.strm, |vmsg|->stream.fin,
10711
 * |vmsg|->stream.data, and |vmsg|->stream.datacnt are stream to which
10712
 * 0-RTT data is sent, whether it is a last data chunk in this stream,
10713
 * a vector of 0-RTT data, and its number of elements respectively.
10714
 * The amount of 0RTT data sent is assigned to
10715
 * *|vmsg|->stream.pdatalen.  If no data is sent, -1 is assigned.
10716
 * Note that 0 length STREAM frame is allowed in QUIC, so 0 might be
10717
 * assigned to *|vmsg|->stream.pdatalen.
10718
 *
10719
 * This function returns 0 if it cannot write any frame because buffer
10720
 * is too small, or packet is congestion limited.  Application should
10721
 * keep reading and wait for congestion window to grow.
10722
 *
10723
 * This function returns the number of bytes written to the buffer
10724
 * pointed by |dest| if it succeeds, or one of the following negative
10725
 * error codes: (TBD).
10726
 */
10727
static ngtcp2_ssize
10728
conn_client_write_handshake(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
10729
                            uint8_t *dest, size_t destlen, uint8_t wflags,
10730
0
                            ngtcp2_vmsg *vmsg, ngtcp2_tstamp ts) {
10731
0
  int send_stream = 0;
10732
0
  int send_datagram = 0;
10733
0
  ngtcp2_ssize spktlen, early_spktlen;
10734
0
  uint64_t datalen;
10735
0
  uint64_t write_datalen = 0;
10736
0
  int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
10737
0
  uint32_t version;
10738
10739
0
  assert(!conn->server);
10740
10741
  /* conn->early.ckm might be created in the first call of
10742
     conn_handshake().  Check it later. */
10743
0
  if (vmsg) {
10744
0
    switch (vmsg->type) {
10745
0
    case NGTCP2_VMSG_TYPE_STREAM:
10746
0
      datalen = ngtcp2_vec_len(vmsg->stream.data, vmsg->stream.datacnt);
10747
0
      send_stream = conn_retry_early_payloadlen(conn) == 0;
10748
0
      if (send_stream) {
10749
0
        write_datalen = ngtcp2_min_uint64(datalen + NGTCP2_STREAM_OVERHEAD,
10750
0
                                          NGTCP2_MIN_COALESCED_PAYLOADLEN);
10751
10752
0
        if (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_MORE) {
10753
0
          wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
10754
0
        }
10755
0
      } else {
10756
0
        vmsg = NULL;
10757
0
      }
10758
0
      break;
10759
0
    case NGTCP2_VMSG_TYPE_DATAGRAM:
10760
0
      datalen = ngtcp2_vec_len(vmsg->datagram.data, vmsg->datagram.datacnt);
10761
0
      send_datagram = conn_retry_early_payloadlen(conn) == 0;
10762
0
      if (send_datagram) {
10763
0
        write_datalen = datalen + NGTCP2_DATAGRAM_OVERHEAD;
10764
10765
0
        if (vmsg->datagram.flags & NGTCP2_WRITE_DATAGRAM_FLAG_MORE) {
10766
0
          wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
10767
0
        }
10768
0
      } else {
10769
0
        vmsg = NULL;
10770
0
      }
10771
0
      break;
10772
0
    }
10773
0
  }
10774
10775
0
  if (!ppe_pending) {
10776
0
    spktlen =
10777
0
      conn_write_handshake(conn, pi, dest, destlen, wflags, write_datalen, ts);
10778
10779
0
    if (spktlen < 0) {
10780
0
      return spktlen;
10781
0
    }
10782
10783
0
    if ((conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) ||
10784
0
        !conn->early.ckm || (!send_stream && !send_datagram)) {
10785
0
      return spktlen;
10786
0
    }
10787
10788
    /* If spktlen > 0, we are making a compound packet.  If Initial
10789
       packet is written, we have to pad bytes to 0-RTT packet. */
10790
0
    version = conn->negotiated_version ? conn->negotiated_version
10791
0
                                       : conn->client_chosen_version;
10792
0
    if (spktlen > 0 &&
10793
0
        ngtcp2_pkt_get_type_long(version, dest[0]) == NGTCP2_PKT_INITIAL) {
10794
0
      wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
10795
0
    }
10796
0
  } else {
10797
0
    assert(!conn->pktns.crypto.rx.ckm);
10798
0
    assert(!conn->pktns.crypto.tx.ckm);
10799
0
    assert(conn->early.ckm);
10800
10801
0
    spktlen = conn->pkt.hs_spktlen;
10802
0
  }
10803
10804
0
  dest += spktlen;
10805
0
  destlen -= (size_t)spktlen;
10806
10807
0
  if (conn_cwnd_is_zero(conn)) {
10808
0
    return spktlen;
10809
0
  }
10810
10811
0
  early_spktlen = conn_write_pkt(conn, pi, dest, destlen, (size_t)spktlen, vmsg,
10812
0
                                 NGTCP2_PKT_0RTT, wflags, ts);
10813
0
  if (early_spktlen < 0) {
10814
0
    switch (early_spktlen) {
10815
0
    case NGTCP2_ERR_STREAM_DATA_BLOCKED:
10816
0
      if (!(wflags & NGTCP2_WRITE_PKT_FLAG_MORE)) {
10817
0
        if (spktlen) {
10818
0
          return spktlen;
10819
0
        }
10820
10821
0
        break;
10822
0
      }
10823
      /* fall through */
10824
0
    case NGTCP2_ERR_WRITE_MORE:
10825
0
      conn->pkt.hs_spktlen = spktlen;
10826
0
      break;
10827
0
    }
10828
0
    return early_spktlen;
10829
0
  }
10830
10831
0
  return spktlen + early_spktlen;
10832
0
}
10833
10834
0
void ngtcp2_conn_tls_handshake_completed(ngtcp2_conn *conn) {
10835
0
  conn->flags |= NGTCP2_CONN_FLAG_TLS_HANDSHAKE_COMPLETED;
10836
0
  if (conn->server) {
10837
0
    conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED;
10838
0
  }
10839
0
}
10840
10841
0
int ngtcp2_conn_get_handshake_completed(ngtcp2_conn *conn) {
10842
0
  return conn_is_tls_handshake_completed(conn) &&
10843
0
         (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED);
10844
0
}
10845
10846
0
int ngtcp2_accept(ngtcp2_pkt_hd *dest, const uint8_t *pkt, size_t pktlen) {
10847
0
  ngtcp2_ssize nread;
10848
0
  ngtcp2_pkt_hd hd, *p;
10849
10850
0
  if (dest) {
10851
0
    p = dest;
10852
0
  } else {
10853
0
    p = &hd;
10854
0
  }
10855
10856
0
  if (pktlen == 0 || (pkt[0] & NGTCP2_HEADER_FORM_BIT) == 0) {
10857
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
10858
0
  }
10859
10860
0
  nread = ngtcp2_pkt_decode_hd_long(p, pkt, pktlen);
10861
0
  if (nread < 0) {
10862
0
    return (int)nread;
10863
0
  }
10864
10865
0
  switch (p->type) {
10866
0
  case NGTCP2_PKT_INITIAL:
10867
0
    break;
10868
0
  case NGTCP2_PKT_0RTT:
10869
    /* 0-RTT packet may arrive before Initial packet due to
10870
       re-ordering.  ngtcp2 does not buffer 0RTT packet unless the
10871
       very first Initial packet is received or token is received.
10872
       Previously, we returned NGTCP2_ERR_RETRY here, so that client
10873
       can resend 0RTT data.  But it incurs 1RTT already and
10874
       diminishes the value of 0RTT.  Therefore, we just discard the
10875
       packet here for now. */
10876
0
  default:
10877
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
10878
0
  }
10879
10880
0
  if (pktlen < NGTCP2_MAX_UDP_PAYLOAD_SIZE ||
10881
0
      (p->tokenlen == 0 && p->dcid.datalen < NGTCP2_MIN_INITIAL_DCIDLEN)) {
10882
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
10883
0
  }
10884
10885
0
  return 0;
10886
0
}
10887
10888
int ngtcp2_conn_install_initial_key(
10889
  ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *rx_aead_ctx,
10890
  const uint8_t *rx_iv, const ngtcp2_crypto_cipher_ctx *rx_hp_ctx,
10891
  const ngtcp2_crypto_aead_ctx *tx_aead_ctx, const uint8_t *tx_iv,
10892
0
  const ngtcp2_crypto_cipher_ctx *tx_hp_ctx, size_t ivlen) {
10893
0
  ngtcp2_pktns *pktns = conn->in_pktns;
10894
0
  int rv;
10895
10896
0
  assert(ivlen >= 8);
10897
0
  assert(pktns);
10898
10899
0
  conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.rx.hp_ctx);
10900
0
  pktns->crypto.rx.hp_ctx.native_handle = NULL;
10901
10902
0
  if (pktns->crypto.rx.ckm) {
10903
0
    conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.rx.ckm->aead_ctx);
10904
0
    ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, conn->mem);
10905
0
    pktns->crypto.rx.ckm = NULL;
10906
0
  }
10907
10908
0
  conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.tx.hp_ctx);
10909
0
  pktns->crypto.tx.hp_ctx.native_handle = NULL;
10910
10911
0
  if (pktns->crypto.tx.ckm) {
10912
0
    conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
10913
0
    ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
10914
0
    pktns->crypto.tx.ckm = NULL;
10915
0
  }
10916
10917
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, NULL, 0, NULL, rx_iv, ivlen,
10918
0
                            conn->mem);
10919
0
  if (rv != 0) {
10920
0
    return rv;
10921
0
  }
10922
10923
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, NULL, 0, NULL, tx_iv, ivlen,
10924
0
                            conn->mem);
10925
0
  if (rv != 0) {
10926
0
    ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, conn->mem);
10927
0
    pktns->crypto.rx.ckm = NULL;
10928
10929
0
    return rv;
10930
0
  }
10931
10932
  /* Take owner ship after we are sure that no failure occurs, so that
10933
     caller can delete these contexts on failure. */
10934
0
  pktns->crypto.rx.ckm->aead_ctx = *rx_aead_ctx;
10935
0
  pktns->crypto.rx.hp_ctx = *rx_hp_ctx;
10936
0
  pktns->crypto.tx.ckm->aead_ctx = *tx_aead_ctx;
10937
0
  pktns->crypto.tx.hp_ctx = *tx_hp_ctx;
10938
10939
0
  return 0;
10940
0
}
10941
10942
int ngtcp2_conn_install_vneg_initial_key(
10943
  ngtcp2_conn *conn, uint32_t version,
10944
  const ngtcp2_crypto_aead_ctx *rx_aead_ctx, const uint8_t *rx_iv,
10945
  const ngtcp2_crypto_cipher_ctx *rx_hp_ctx,
10946
  const ngtcp2_crypto_aead_ctx *tx_aead_ctx, const uint8_t *tx_iv,
10947
0
  const ngtcp2_crypto_cipher_ctx *tx_hp_ctx, size_t ivlen) {
10948
0
  int rv;
10949
10950
0
  assert(ivlen >= 8);
10951
10952
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->vneg.rx.hp_ctx);
10953
0
  conn->vneg.rx.hp_ctx.native_handle = NULL;
10954
10955
0
  if (conn->vneg.rx.ckm) {
10956
0
    conn_call_delete_crypto_aead_ctx(conn, &conn->vneg.rx.ckm->aead_ctx);
10957
0
    ngtcp2_crypto_km_del(conn->vneg.rx.ckm, conn->mem);
10958
0
    conn->vneg.rx.ckm = NULL;
10959
0
  }
10960
10961
0
  conn_call_delete_crypto_cipher_ctx(conn, &conn->vneg.tx.hp_ctx);
10962
0
  conn->vneg.tx.hp_ctx.native_handle = NULL;
10963
10964
0
  if (conn->vneg.tx.ckm) {
10965
0
    conn_call_delete_crypto_aead_ctx(conn, &conn->vneg.tx.ckm->aead_ctx);
10966
0
    ngtcp2_crypto_km_del(conn->vneg.tx.ckm, conn->mem);
10967
0
    conn->vneg.tx.ckm = NULL;
10968
0
  }
10969
10970
0
  rv = ngtcp2_crypto_km_new(&conn->vneg.rx.ckm, NULL, 0, NULL, rx_iv, ivlen,
10971
0
                            conn->mem);
10972
0
  if (rv != 0) {
10973
0
    return rv;
10974
0
  }
10975
10976
0
  rv = ngtcp2_crypto_km_new(&conn->vneg.tx.ckm, NULL, 0, NULL, tx_iv, ivlen,
10977
0
                            conn->mem);
10978
0
  if (rv != 0) {
10979
0
    ngtcp2_crypto_km_del(conn->vneg.rx.ckm, conn->mem);
10980
0
    conn->vneg.rx.ckm = NULL;
10981
10982
0
    return rv;
10983
0
  }
10984
10985
  /* Take owner ship after we are sure that no failure occurs, so that
10986
     caller can delete these contexts on failure. */
10987
0
  conn->vneg.rx.ckm->aead_ctx = *rx_aead_ctx;
10988
0
  conn->vneg.rx.hp_ctx = *rx_hp_ctx;
10989
0
  conn->vneg.tx.ckm->aead_ctx = *tx_aead_ctx;
10990
0
  conn->vneg.tx.hp_ctx = *tx_hp_ctx;
10991
0
  conn->vneg.version = version;
10992
10993
0
  return 0;
10994
0
}
10995
10996
int ngtcp2_conn_install_rx_handshake_key(
10997
  ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *aead_ctx, const uint8_t *iv,
10998
0
  size_t ivlen, const ngtcp2_crypto_cipher_ctx *hp_ctx) {
10999
0
  ngtcp2_pktns *pktns = conn->hs_pktns;
11000
0
  int rv;
11001
11002
0
  assert(ivlen >= 8);
11003
0
  assert(pktns);
11004
0
  assert(!pktns->crypto.rx.hp_ctx.native_handle);
11005
0
  assert(!pktns->crypto.rx.ckm);
11006
11007
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, NULL, 0, aead_ctx, iv, ivlen,
11008
0
                            conn->mem);
11009
0
  if (rv != 0) {
11010
0
    return rv;
11011
0
  }
11012
11013
0
  pktns->crypto.rx.hp_ctx = *hp_ctx;
11014
11015
0
  rv = conn_call_recv_rx_key(conn, NGTCP2_ENCRYPTION_LEVEL_HANDSHAKE);
11016
0
  if (rv != 0) {
11017
0
    ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, conn->mem);
11018
0
    pktns->crypto.rx.ckm = NULL;
11019
0
    pktns->crypto.rx.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
11020
11021
0
    return rv;
11022
0
  }
11023
11024
0
  return 0;
11025
0
}
11026
11027
int ngtcp2_conn_install_tx_handshake_key(
11028
  ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *aead_ctx, const uint8_t *iv,
11029
0
  size_t ivlen, const ngtcp2_crypto_cipher_ctx *hp_ctx) {
11030
0
  ngtcp2_pktns *pktns = conn->hs_pktns;
11031
0
  int rv;
11032
11033
0
  assert(ivlen >= 8);
11034
0
  assert(pktns);
11035
0
  assert(!pktns->crypto.tx.hp_ctx.native_handle);
11036
0
  assert(!pktns->crypto.tx.ckm);
11037
11038
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, NULL, 0, aead_ctx, iv, ivlen,
11039
0
                            conn->mem);
11040
0
  if (rv != 0) {
11041
0
    return rv;
11042
0
  }
11043
11044
0
  pktns->crypto.tx.hp_ctx = *hp_ctx;
11045
11046
0
  if (conn->server) {
11047
0
    rv = ngtcp2_conn_commit_local_transport_params(conn);
11048
0
    if (rv != 0) {
11049
0
      goto fail;
11050
0
    }
11051
0
  }
11052
11053
0
  rv = conn_call_recv_tx_key(conn, NGTCP2_ENCRYPTION_LEVEL_HANDSHAKE);
11054
0
  if (rv != 0) {
11055
0
    goto fail;
11056
0
  }
11057
11058
0
  return 0;
11059
11060
0
fail:
11061
  /* If this function fails, aead_ctx and hp_ctx are still owned by
11062
     the caller.  Delete the install key to remove the any reference
11063
     to them. */
11064
0
  ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
11065
0
  pktns->crypto.tx.ckm = NULL;
11066
0
  pktns->crypto.tx.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
11067
11068
0
  return rv;
11069
0
}
11070
11071
int ngtcp2_conn_install_0rtt_key(ngtcp2_conn *conn,
11072
                                 const ngtcp2_crypto_aead_ctx *aead_ctx,
11073
                                 const uint8_t *iv, size_t ivlen,
11074
0
                                 const ngtcp2_crypto_cipher_ctx *hp_ctx) {
11075
0
  int rv;
11076
11077
0
  assert(ivlen >= 8);
11078
0
  assert(!conn->early.hp_ctx.native_handle);
11079
0
  assert(!conn->early.ckm);
11080
11081
0
  rv = ngtcp2_crypto_km_new(&conn->early.ckm, NULL, 0, aead_ctx, iv, ivlen,
11082
0
                            conn->mem);
11083
0
  if (rv != 0) {
11084
0
    return rv;
11085
0
  }
11086
11087
0
  conn->early.hp_ctx = *hp_ctx;
11088
11089
0
  conn->flags |= NGTCP2_CONN_FLAG_EARLY_KEY_INSTALLED;
11090
11091
0
  if (conn->server) {
11092
0
    rv = conn_call_recv_rx_key(conn, NGTCP2_ENCRYPTION_LEVEL_0RTT);
11093
0
  } else {
11094
0
    rv = conn_call_recv_tx_key(conn, NGTCP2_ENCRYPTION_LEVEL_0RTT);
11095
0
  }
11096
0
  if (rv != 0) {
11097
0
    ngtcp2_crypto_km_del(conn->early.ckm, conn->mem);
11098
0
    conn->early.ckm = NULL;
11099
0
    conn->early.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
11100
11101
0
    return rv;
11102
0
  }
11103
11104
0
  return 0;
11105
0
}
11106
11107
int ngtcp2_conn_install_rx_key(ngtcp2_conn *conn, const uint8_t *secret,
11108
                               size_t secretlen,
11109
                               const ngtcp2_crypto_aead_ctx *aead_ctx,
11110
                               const uint8_t *iv, size_t ivlen,
11111
0
                               const ngtcp2_crypto_cipher_ctx *hp_ctx) {
11112
0
  ngtcp2_pktns *pktns = &conn->pktns;
11113
0
  int rv;
11114
11115
0
  assert(ivlen >= 8);
11116
0
  assert(!pktns->crypto.rx.hp_ctx.native_handle);
11117
0
  assert(!pktns->crypto.rx.ckm);
11118
11119
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, secret, secretlen, aead_ctx,
11120
0
                            iv, ivlen, conn->mem);
11121
0
  if (rv != 0) {
11122
0
    return rv;
11123
0
  }
11124
11125
0
  pktns->crypto.rx.hp_ctx = *hp_ctx;
11126
11127
0
  if (!conn->server) {
11128
0
    if (conn->remote.pending_transport_params) {
11129
0
      ngtcp2_transport_params_del(conn->remote.transport_params, conn->mem);
11130
11131
0
      conn->remote.transport_params = conn->remote.pending_transport_params;
11132
0
      conn->remote.pending_transport_params = NULL;
11133
0
      conn_sync_stream_id_limit(conn);
11134
0
      conn->tx.max_offset = conn->remote.transport_params->initial_max_data;
11135
0
    }
11136
11137
0
    if (conn->early.ckm) {
11138
0
      conn_discard_early_key(conn);
11139
0
    }
11140
0
  }
11141
11142
0
  rv = conn_call_recv_rx_key(conn, NGTCP2_ENCRYPTION_LEVEL_1RTT);
11143
0
  if (rv != 0) {
11144
0
    ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, conn->mem);
11145
0
    pktns->crypto.rx.ckm = NULL;
11146
0
    pktns->crypto.rx.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
11147
11148
0
    return rv;
11149
0
  }
11150
11151
0
  return 0;
11152
0
}
11153
11154
int ngtcp2_conn_install_tx_key(ngtcp2_conn *conn, const uint8_t *secret,
11155
                               size_t secretlen,
11156
                               const ngtcp2_crypto_aead_ctx *aead_ctx,
11157
                               const uint8_t *iv, size_t ivlen,
11158
0
                               const ngtcp2_crypto_cipher_ctx *hp_ctx) {
11159
0
  ngtcp2_pktns *pktns = &conn->pktns;
11160
0
  int rv;
11161
11162
0
  assert(ivlen >= 8);
11163
0
  assert(!pktns->crypto.tx.hp_ctx.native_handle);
11164
0
  assert(!pktns->crypto.tx.ckm);
11165
11166
0
  rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, secret, secretlen, aead_ctx,
11167
0
                            iv, ivlen, conn->mem);
11168
0
  if (rv != 0) {
11169
0
    return rv;
11170
0
  }
11171
11172
0
  pktns->crypto.tx.hp_ctx = *hp_ctx;
11173
11174
0
  if (conn->server) {
11175
0
    if (conn->remote.pending_transport_params) {
11176
0
      ngtcp2_transport_params_del(conn->remote.transport_params, conn->mem);
11177
11178
0
      conn->remote.transport_params = conn->remote.pending_transport_params;
11179
0
      conn->remote.pending_transport_params = NULL;
11180
0
      conn_sync_stream_id_limit(conn);
11181
0
      conn->tx.max_offset = conn->remote.transport_params->initial_max_data;
11182
0
    }
11183
0
  } else if (conn->early.ckm) {
11184
0
    conn_discard_early_key(conn);
11185
0
  }
11186
11187
0
  rv = conn_call_recv_tx_key(conn, NGTCP2_ENCRYPTION_LEVEL_1RTT);
11188
0
  if (rv != 0) {
11189
0
    ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
11190
0
    pktns->crypto.tx.ckm = NULL;
11191
0
    pktns->crypto.tx.hp_ctx = (ngtcp2_crypto_cipher_ctx){0};
11192
11193
0
    return rv;
11194
0
  }
11195
11196
0
  return 0;
11197
0
}
11198
11199
0
static int conn_initiate_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11200
0
  ngtcp2_tstamp confirmed_ts = conn->crypto.key_update.confirmed_ts;
11201
0
  ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
11202
11203
0
  assert(conn->state == NGTCP2_CS_POST_HANDSHAKE);
11204
11205
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) ||
11206
0
      (conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED) ||
11207
0
      !conn->crypto.key_update.new_tx_ckm ||
11208
0
      !conn->crypto.key_update.new_rx_ckm ||
11209
0
      ngtcp2_tstamp_not_elapsed(confirmed_ts, 3 * pto, ts)) {
11210
0
    return NGTCP2_ERR_INVALID_STATE;
11211
0
  }
11212
11213
0
  conn_rotate_keys(conn, NGTCP2_MAX_PKT_NUM, /* initiator = */ 1);
11214
11215
0
  return 0;
11216
0
}
11217
11218
0
int ngtcp2_conn_initiate_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11219
0
  conn_update_timestamp(conn, ts);
11220
11221
0
  return conn_initiate_key_update(conn, ts);
11222
0
}
11223
11224
0
ngtcp2_tstamp ngtcp2_conn_loss_detection_expiry(ngtcp2_conn *conn) {
11225
0
  return conn->cstat.loss_detection_timer;
11226
0
}
11227
11228
0
ngtcp2_tstamp ngtcp2_conn_internal_expiry(ngtcp2_conn *conn) {
11229
0
  ngtcp2_tstamp res = UINT64_MAX, ts;
11230
0
  ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
11231
0
  ngtcp2_scid *scid;
11232
11233
0
  if (conn->pv) {
11234
0
    res = ngtcp2_pv_next_expiry(conn->pv);
11235
0
  }
11236
11237
0
  if (conn->pmtud) {
11238
0
    res = ngtcp2_min_uint64(res, conn->pmtud->expiry);
11239
0
  }
11240
11241
0
  if (!ngtcp2_pq_empty(&conn->scid.used)) {
11242
0
    scid = ngtcp2_struct_of(ngtcp2_pq_top(&conn->scid.used), ngtcp2_scid, pe);
11243
0
    if (scid->retired_ts != UINT64_MAX) {
11244
0
      res = ngtcp2_min_uint64(res, scid->retired_ts + pto);
11245
0
    }
11246
0
  }
11247
11248
0
  ts = ngtcp2_dcidtr_earliest_retired_ts(&conn->dcid.dtr);
11249
0
  if (ts != UINT64_MAX) {
11250
0
    res = ngtcp2_min_uint64(res, ts + pto);
11251
0
  }
11252
11253
0
  if (conn->dcid.current.cid.datalen) {
11254
0
    ts = ngtcp2_dcidtr_earliest_bound_ts(&conn->dcid.dtr);
11255
0
    if (ts != UINT64_MAX) {
11256
0
      res = ngtcp2_min_uint64(res, ts + 3 * pto);
11257
0
    }
11258
0
  }
11259
11260
0
  if (conn->server && conn->early.ckm &&
11261
0
      conn->early.discard_started_ts != UINT64_MAX) {
11262
0
    res = ngtcp2_min_uint64(res, conn->early.discard_started_ts + 3 * pto);
11263
0
  }
11264
11265
0
  return res;
11266
0
}
11267
11268
0
ngtcp2_tstamp ngtcp2_conn_ack_delay_expiry(ngtcp2_conn *conn) {
11269
0
  ngtcp2_acktr *acktr = &conn->pktns.acktr;
11270
11271
0
  if (!(acktr->flags & NGTCP2_ACKTR_FLAG_CANCEL_TIMER) &&
11272
0
      acktr->first_unacked_ts != UINT64_MAX) {
11273
0
    return acktr->first_unacked_ts + conn_compute_ack_delay(conn);
11274
0
  }
11275
0
  return UINT64_MAX;
11276
0
}
11277
11278
0
static ngtcp2_tstamp conn_handshake_expiry(ngtcp2_conn *conn) {
11279
0
  if (conn_is_tls_handshake_completed(conn) ||
11280
0
      conn->local.settings.handshake_timeout == UINT64_MAX ||
11281
0
      conn->local.settings.initial_ts >=
11282
0
        UINT64_MAX - conn->local.settings.handshake_timeout) {
11283
0
    return UINT64_MAX;
11284
0
  }
11285
11286
0
  return conn->local.settings.initial_ts +
11287
0
         conn->local.settings.handshake_timeout;
11288
0
}
11289
11290
0
ngtcp2_tstamp ngtcp2_conn_get_expiry(ngtcp2_conn *conn) {
11291
0
  ngtcp2_tstamp res = ngtcp2_min_uint64(ngtcp2_conn_loss_detection_expiry(conn),
11292
0
                                        ngtcp2_conn_ack_delay_expiry(conn));
11293
0
  res = ngtcp2_min_uint64(res, ngtcp2_conn_internal_expiry(conn));
11294
0
  res = ngtcp2_min_uint64(res, ngtcp2_conn_lost_pkt_expiry(conn));
11295
0
  res = ngtcp2_min_uint64(res, conn_keep_alive_expiry(conn));
11296
0
  res = ngtcp2_min_uint64(res, conn_handshake_expiry(conn));
11297
0
  res = ngtcp2_min_uint64(res, ngtcp2_conn_get_idle_expiry(conn));
11298
0
  return ngtcp2_min_uint64(res, conn->tx.pacing.next_ts);
11299
0
}
11300
11301
0
int ngtcp2_conn_handle_expiry(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11302
0
  int rv;
11303
0
  ngtcp2_duration pto;
11304
11305
0
  conn_update_timestamp(conn, ts);
11306
11307
0
  pto = conn_compute_pto(conn, &conn->pktns);
11308
11309
0
  assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
11310
11311
0
  if (ngtcp2_conn_get_idle_expiry(conn) <= ts) {
11312
0
    return NGTCP2_ERR_IDLE_CLOSE;
11313
0
  }
11314
11315
0
  ngtcp2_conn_cancel_expired_ack_delay_timer(conn, ts);
11316
11317
0
  conn_cancel_expired_keep_alive_timer(conn, ts);
11318
11319
0
  conn_cancel_expired_pkt_tx_timer(conn, ts);
11320
11321
0
  ngtcp2_conn_remove_lost_pkt(conn, ts);
11322
11323
0
  if (conn->pv) {
11324
0
    ngtcp2_pv_cancel_expired_timer(conn->pv, ts);
11325
0
  }
11326
11327
0
  if (conn->pmtud) {
11328
0
    ngtcp2_pmtud_handle_expiry(conn->pmtud, ts);
11329
0
    if (ngtcp2_pmtud_finished(conn->pmtud)) {
11330
0
      ngtcp2_conn_stop_pmtud(conn);
11331
0
    }
11332
0
  }
11333
11334
0
  if (ngtcp2_conn_loss_detection_expiry(conn) <= ts) {
11335
0
    rv = ngtcp2_conn_on_loss_detection_timer(conn, ts);
11336
0
    if (rv != 0) {
11337
0
      return rv;
11338
0
    }
11339
0
  }
11340
11341
0
  if (conn->dcid.current.cid.datalen) {
11342
0
    rv = ngtcp2_dcidtr_retire_stale_bound_dcid(&conn->dcid.dtr, 3 * pto, ts,
11343
0
                                               dcidtr_on_retire, conn);
11344
0
    if (rv != 0) {
11345
0
      return rv;
11346
0
    }
11347
0
  }
11348
11349
0
  rv = conn_remove_retired_connection_id(conn, pto, ts);
11350
0
  if (rv != 0) {
11351
0
    return rv;
11352
0
  }
11353
11354
0
  if (conn->server && conn->early.ckm &&
11355
0
      ngtcp2_tstamp_elapsed(conn->early.discard_started_ts, 3 * pto, ts)) {
11356
0
    conn_discard_early_key(conn);
11357
0
  }
11358
11359
0
  if (!conn_is_tls_handshake_completed(conn) &&
11360
0
      ngtcp2_tstamp_elapsed(conn->local.settings.initial_ts,
11361
0
                            conn->local.settings.handshake_timeout, ts)) {
11362
0
    return NGTCP2_ERR_HANDSHAKE_TIMEOUT;
11363
0
  }
11364
11365
0
  return 0;
11366
0
}
11367
11368
static void acktr_cancel_expired_ack_delay_timer(ngtcp2_acktr *acktr,
11369
                                                 ngtcp2_duration max_ack_delay,
11370
0
                                                 ngtcp2_tstamp ts) {
11371
0
  if (!(acktr->flags & NGTCP2_ACKTR_FLAG_CANCEL_TIMER) &&
11372
0
      ngtcp2_tstamp_elapsed(acktr->first_unacked_ts, max_ack_delay, ts)) {
11373
0
    acktr->flags |= NGTCP2_ACKTR_FLAG_CANCEL_TIMER;
11374
0
  }
11375
0
}
11376
11377
void ngtcp2_conn_cancel_expired_ack_delay_timer(ngtcp2_conn *conn,
11378
0
                                                ngtcp2_tstamp ts) {
11379
0
  ngtcp2_duration ack_delay = conn_compute_ack_delay(conn);
11380
11381
0
  if (conn->in_pktns) {
11382
0
    acktr_cancel_expired_ack_delay_timer(&conn->in_pktns->acktr, 0, ts);
11383
0
  }
11384
0
  if (conn->hs_pktns) {
11385
0
    acktr_cancel_expired_ack_delay_timer(&conn->hs_pktns->acktr, 0, ts);
11386
0
  }
11387
0
  acktr_cancel_expired_ack_delay_timer(&conn->pktns.acktr, ack_delay, ts);
11388
0
}
11389
11390
0
ngtcp2_tstamp ngtcp2_conn_lost_pkt_expiry(ngtcp2_conn *conn) {
11391
0
  ngtcp2_tstamp res = UINT64_MAX, ts;
11392
11393
0
  if (conn->in_pktns) {
11394
0
    ts = ngtcp2_rtb_lost_pkt_ts(&conn->in_pktns->rtb);
11395
0
    if (ts != UINT64_MAX) {
11396
0
      ts += conn_compute_pto(conn, conn->in_pktns) * 3;
11397
0
      res = ngtcp2_min_uint64(res, ts);
11398
0
    }
11399
0
  }
11400
11401
0
  if (conn->hs_pktns) {
11402
0
    ts = ngtcp2_rtb_lost_pkt_ts(&conn->hs_pktns->rtb);
11403
0
    if (ts != UINT64_MAX) {
11404
0
      ts += conn_compute_pto(conn, conn->hs_pktns) * 3;
11405
0
      res = ngtcp2_min_uint64(res, ts);
11406
0
    }
11407
0
  }
11408
11409
0
  ts = ngtcp2_rtb_lost_pkt_ts(&conn->pktns.rtb);
11410
0
  if (ts != UINT64_MAX) {
11411
0
    ts += conn_compute_pto(conn, &conn->pktns) * 3;
11412
0
    res = ngtcp2_min_uint64(res, ts);
11413
0
  }
11414
11415
0
  return res;
11416
0
}
11417
11418
0
void ngtcp2_conn_remove_lost_pkt(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11419
0
  ngtcp2_duration timeout;
11420
11421
0
  if (conn->in_pktns) {
11422
0
    timeout = conn_compute_pto(conn, conn->in_pktns) * 3;
11423
0
    ngtcp2_rtb_remove_expired_lost_pkt(&conn->in_pktns->rtb, timeout, ts);
11424
0
  }
11425
0
  if (conn->hs_pktns) {
11426
0
    timeout = conn_compute_pto(conn, conn->hs_pktns) * 3;
11427
0
    ngtcp2_rtb_remove_expired_lost_pkt(&conn->hs_pktns->rtb, timeout, ts);
11428
0
  }
11429
0
  timeout = conn_compute_pto(conn, &conn->pktns) * 3;
11430
0
  ngtcp2_rtb_remove_expired_lost_pkt(&conn->pktns.rtb, timeout, ts);
11431
0
}
11432
11433
/*
11434
 * select_preferred_version selects the most preferred version.
11435
 * |fallback_version| is chosen if no preference is made, or
11436
 * |preferred_versions| does not include any of |chosen_version| or
11437
 * |available_versions|.  |chosen_version| is treated as an extra
11438
 * other version.
11439
 */
11440
static uint32_t select_preferred_version(const uint32_t *preferred_versions,
11441
                                         size_t preferred_versionslen,
11442
                                         uint32_t chosen_version,
11443
                                         const uint8_t *available_versions,
11444
                                         size_t available_versionslen,
11445
0
                                         uint32_t fallback_version) {
11446
0
  size_t i, j;
11447
0
  const uint8_t *p;
11448
0
  uint32_t v;
11449
11450
0
  if (!preferred_versionslen ||
11451
0
      (!available_versionslen && chosen_version == fallback_version)) {
11452
0
    return fallback_version;
11453
0
  }
11454
11455
0
  for (i = 0; i < preferred_versionslen; ++i) {
11456
0
    if (preferred_versions[i] == chosen_version) {
11457
0
      return chosen_version;
11458
0
    }
11459
0
    for (j = 0, p = available_versions; j < available_versionslen;
11460
0
         j += sizeof(uint32_t)) {
11461
0
      p = ngtcp2_get_uint32be(&v, p);
11462
11463
0
      if (preferred_versions[i] == v) {
11464
0
        return v;
11465
0
      }
11466
0
    }
11467
0
  }
11468
11469
0
  return fallback_version;
11470
0
}
11471
11472
/*
11473
 * conn_client_validate_transport_params validates |params| as client.
11474
 * |params| must be sent with Encrypted Extensions.
11475
 *
11476
 * This function returns 0 if it succeeds, or one of the following
11477
 * negative error codes:
11478
 *
11479
 * NGTCP2_ERR_TRANSPORT_PARAM
11480
 *     params contains preferred address but server chose zero-length
11481
 *     connection ID.
11482
 * NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE
11483
 *     Validation against version negotiation parameters failed.
11484
 */
11485
static int
11486
conn_client_validate_transport_params(ngtcp2_conn *conn,
11487
0
                                      const ngtcp2_transport_params *params) {
11488
0
  if (!params->original_dcid_present) {
11489
0
    return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
11490
0
  }
11491
11492
0
  if (!ngtcp2_cid_eq(&conn->rcid, &params->original_dcid)) {
11493
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11494
0
  }
11495
11496
0
  if (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) {
11497
0
    if (!params->retry_scid_present) {
11498
0
      return NGTCP2_ERR_TRANSPORT_PARAM;
11499
0
    }
11500
0
    if (!ngtcp2_cid_eq(&conn->retry_scid, &params->retry_scid)) {
11501
0
      return NGTCP2_ERR_TRANSPORT_PARAM;
11502
0
    }
11503
0
  } else if (params->retry_scid_present) {
11504
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11505
0
  }
11506
11507
0
  if (params->preferred_addr_present && conn->dcid.current.cid.datalen == 0) {
11508
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11509
0
  }
11510
11511
0
  if (params->version_info_present) {
11512
0
    if (conn->negotiated_version != params->version_info.chosen_version) {
11513
0
      return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11514
0
    }
11515
11516
0
    assert(vneg_available_versions_includes(conn->vneg.available_versions,
11517
0
                                            conn->vneg.available_versionslen,
11518
0
                                            conn->negotiated_version));
11519
0
  } else if (conn->client_chosen_version != conn->negotiated_version) {
11520
0
    return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11521
0
  }
11522
11523
  /* When client reacted upon Version Negotiation */
11524
0
  if (conn->local.settings.original_version != conn->client_chosen_version) {
11525
0
    if (!params->version_info_present) {
11526
0
      assert(conn->client_chosen_version == conn->negotiated_version);
11527
11528
      /* QUIC v1 is treated specially.  If version_info is missing, no
11529
         further validation is necessary.  See
11530
         https://datatracker.ietf.org/doc/html/rfc9368#section-8
11531
       */
11532
0
      if (conn->client_chosen_version == NGTCP2_PROTO_VER_V1) {
11533
0
        return 0;
11534
0
      }
11535
11536
0
      return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11537
0
    }
11538
11539
    /* Server choose original version after Version Negotiation.  RFC
11540
       9368 does not say this particular case, but this smells like
11541
       misbehaved server because server should accept original_version
11542
       in the original connection. */
11543
0
    if (conn->local.settings.original_version ==
11544
0
        params->version_info.chosen_version) {
11545
0
      return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11546
0
    }
11547
11548
    /* Check version downgrade on incompatible version negotiation. */
11549
0
    if (params->version_info.available_versionslen == 0) {
11550
0
      return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11551
0
    }
11552
11553
0
    if (conn->client_chosen_version !=
11554
0
        select_preferred_version(conn->vneg.preferred_versions,
11555
0
                                 conn->vneg.preferred_versionslen,
11556
0
                                 params->version_info.chosen_version,
11557
0
                                 params->version_info.available_versions,
11558
0
                                 params->version_info.available_versionslen,
11559
0
                                 /* fallback_version = */ 0)) {
11560
0
      return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11561
0
    }
11562
0
  }
11563
11564
0
  return 0;
11565
0
}
11566
11567
uint32_t
11568
ngtcp2_conn_server_negotiate_version(ngtcp2_conn *conn,
11569
0
                                     const ngtcp2_version_info *version_info) {
11570
0
  assert(conn->server);
11571
0
  assert(conn->client_chosen_version == version_info->chosen_version);
11572
11573
0
  return select_preferred_version(
11574
0
    conn->vneg.preferred_versions, conn->vneg.preferred_versionslen,
11575
0
    version_info->chosen_version, version_info->available_versions,
11576
0
    version_info->available_versionslen, version_info->chosen_version);
11577
0
}
11578
11579
int ngtcp2_conn_set_remote_transport_params(
11580
0
  ngtcp2_conn *conn, const ngtcp2_transport_params *params) {
11581
0
  int rv;
11582
11583
  /* We expect this function is called once per QUIC connection, but
11584
     GnuTLS server seems to call TLS extension callback twice if it
11585
     sends HelloRetryRequest.  In practice, same QUIC transport
11586
     parameters are sent in the 2nd client flight, just returning 0
11587
     would cause no harm. */
11588
0
  if (conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED) {
11589
0
    return 0;
11590
0
  }
11591
11592
0
  if (!params->initial_scid_present) {
11593
0
    return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
11594
0
  }
11595
11596
  /* Assume that ngtcp2_transport_params_decode sets default value if
11597
     active_connection_id_limit is omitted. */
11598
0
  if (params->active_connection_id_limit <
11599
0
      NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT) {
11600
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11601
0
  }
11602
11603
  /* We assume that conn->dcid.current.cid is still the initial one.
11604
     This requires that transport parameter must be fed into
11605
     ngtcp2_conn as early as possible. */
11606
0
  if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &params->initial_scid)) {
11607
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11608
0
  }
11609
11610
0
  if (params->max_udp_payload_size < NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
11611
0
    return NGTCP2_ERR_TRANSPORT_PARAM;
11612
0
  }
11613
11614
0
  if (conn->server) {
11615
0
    if (params->original_dcid_present ||
11616
0
        params->stateless_reset_token_present ||
11617
0
        params->preferred_addr_present || params->retry_scid_present) {
11618
0
      return NGTCP2_ERR_TRANSPORT_PARAM;
11619
0
    }
11620
11621
0
    if (params->version_info_present) {
11622
0
      if (!vneg_available_versions_includes(
11623
0
            params->version_info.available_versions,
11624
0
            params->version_info.available_versionslen,
11625
0
            params->version_info.chosen_version)) {
11626
0
        return NGTCP2_ERR_TRANSPORT_PARAM;
11627
0
      }
11628
11629
0
      if (params->version_info.chosen_version != conn->client_chosen_version) {
11630
0
        return NGTCP2_ERR_VERSION_NEGOTIATION_FAILURE;
11631
0
      }
11632
11633
0
      conn->negotiated_version =
11634
0
        ngtcp2_conn_server_negotiate_version(conn, &params->version_info);
11635
0
      if (conn->negotiated_version != conn->client_chosen_version) {
11636
0
        rv = conn_call_version_negotiation(conn, conn->negotiated_version,
11637
0
                                           &conn->rcid);
11638
0
        if (rv != 0) {
11639
0
          return rv;
11640
0
        }
11641
0
      }
11642
0
    } else {
11643
0
      conn->negotiated_version = conn->client_chosen_version;
11644
0
    }
11645
11646
0
    conn->local.transport_params.version_info.chosen_version =
11647
0
      conn->negotiated_version;
11648
11649
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
11650
0
                     "the negotiated version is 0x%08x",
11651
0
                     conn->negotiated_version);
11652
0
  } else {
11653
0
    rv = conn_client_validate_transport_params(conn, params);
11654
0
    if (rv != 0) {
11655
0
      return rv;
11656
0
    }
11657
0
  }
11658
11659
0
  ngtcp2_log_remote_tp(&conn->log, params);
11660
11661
0
  ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, params, conn->server,
11662
0
                                              NGTCP2_QLOG_SIDE_REMOTE);
11663
11664
0
  if ((conn->server && conn->pktns.crypto.tx.ckm) ||
11665
0
      (!conn->server && conn->pktns.crypto.rx.ckm)) {
11666
0
    ngtcp2_transport_params_del(conn->remote.transport_params, conn->mem);
11667
0
    conn->remote.transport_params = NULL;
11668
11669
0
    rv = ngtcp2_transport_params_copy_new(&conn->remote.transport_params,
11670
0
                                          params, conn->mem);
11671
0
    if (rv != 0) {
11672
0
      return rv;
11673
0
    }
11674
0
    conn_sync_stream_id_limit(conn);
11675
0
    conn->tx.max_offset = conn->remote.transport_params->initial_max_data;
11676
0
  } else {
11677
0
    assert(!conn->remote.pending_transport_params);
11678
11679
0
    rv = ngtcp2_transport_params_copy_new(
11680
0
      &conn->remote.pending_transport_params, params, conn->mem);
11681
0
    if (rv != 0) {
11682
0
      return rv;
11683
0
    }
11684
0
  }
11685
11686
0
  conn->flags |= NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED;
11687
11688
0
  return 0;
11689
0
}
11690
11691
int ngtcp2_conn_decode_and_set_remote_transport_params(ngtcp2_conn *conn,
11692
                                                       const uint8_t *data,
11693
0
                                                       size_t datalen) {
11694
0
  ngtcp2_transport_params params;
11695
0
  int rv;
11696
11697
0
  rv = ngtcp2_transport_params_decode(&params, data, datalen);
11698
0
  if (rv != 0) {
11699
0
    return rv;
11700
0
  }
11701
11702
0
  return ngtcp2_conn_set_remote_transport_params(conn, &params);
11703
0
}
11704
11705
const ngtcp2_transport_params *
11706
0
ngtcp2_conn_get_remote_transport_params(ngtcp2_conn *conn) {
11707
0
  if (conn->remote.pending_transport_params) {
11708
0
    return conn->remote.pending_transport_params;
11709
0
  }
11710
11711
0
  return conn->remote.transport_params;
11712
0
}
11713
11714
ngtcp2_ssize ngtcp2_conn_encode_0rtt_transport_params(ngtcp2_conn *conn,
11715
                                                      uint8_t *dest,
11716
0
                                                      size_t destlen) {
11717
0
  ngtcp2_transport_params params, *src;
11718
11719
0
  if (conn->server) {
11720
0
    src = &conn->local.transport_params;
11721
0
  } else {
11722
0
    assert(conn->remote.transport_params);
11723
11724
0
    src = conn->remote.transport_params;
11725
0
  }
11726
11727
0
  ngtcp2_transport_params_default(&params);
11728
11729
0
  params.initial_max_streams_bidi = src->initial_max_streams_bidi;
11730
0
  params.initial_max_streams_uni = src->initial_max_streams_uni;
11731
0
  params.initial_max_stream_data_bidi_local =
11732
0
    src->initial_max_stream_data_bidi_local;
11733
0
  params.initial_max_stream_data_bidi_remote =
11734
0
    src->initial_max_stream_data_bidi_remote;
11735
0
  params.initial_max_stream_data_uni = src->initial_max_stream_data_uni;
11736
0
  params.initial_max_data = src->initial_max_data;
11737
0
  params.active_connection_id_limit = src->active_connection_id_limit;
11738
0
  params.max_datagram_frame_size = src->max_datagram_frame_size;
11739
11740
0
  if (conn->server) {
11741
0
    params.max_idle_timeout = src->max_idle_timeout;
11742
0
    params.max_udp_payload_size = src->max_udp_payload_size;
11743
0
    params.disable_active_migration = src->disable_active_migration;
11744
0
  }
11745
11746
0
  return ngtcp2_transport_params_encode(dest, destlen, &params);
11747
0
}
11748
11749
int ngtcp2_conn_decode_and_set_0rtt_transport_params(ngtcp2_conn *conn,
11750
                                                     const uint8_t *data,
11751
0
                                                     size_t datalen) {
11752
0
  ngtcp2_transport_params params;
11753
0
  int rv;
11754
11755
0
  rv = ngtcp2_transport_params_decode(&params, data, datalen);
11756
0
  if (rv != 0) {
11757
0
    return rv;
11758
0
  }
11759
11760
0
  return ngtcp2_conn_set_0rtt_remote_transport_params(conn, &params);
11761
0
}
11762
11763
int ngtcp2_conn_set_0rtt_remote_transport_params(
11764
0
  ngtcp2_conn *conn, const ngtcp2_transport_params *params) {
11765
0
  ngtcp2_transport_params *p;
11766
11767
0
  assert(!conn->server);
11768
0
  assert(!conn->remote.transport_params);
11769
11770
  /* Assume that all pointer fields in p are NULL */
11771
0
  p = ngtcp2_mem_calloc(conn->mem, 1, sizeof(*p));
11772
0
  if (p == NULL) {
11773
0
    return NGTCP2_ERR_NOMEM;
11774
0
  }
11775
11776
0
  conn->remote.transport_params = p;
11777
11778
0
  ngtcp2_transport_params_default(conn->remote.transport_params);
11779
11780
0
  p->initial_max_streams_bidi = params->initial_max_streams_bidi;
11781
0
  p->initial_max_streams_uni = params->initial_max_streams_uni;
11782
0
  p->initial_max_stream_data_bidi_local =
11783
0
    params->initial_max_stream_data_bidi_local;
11784
0
  p->initial_max_stream_data_bidi_remote =
11785
0
    params->initial_max_stream_data_bidi_remote;
11786
0
  p->initial_max_stream_data_uni = params->initial_max_stream_data_uni;
11787
0
  p->initial_max_data = params->initial_max_data;
11788
  /* we might hit garbage, then set the sane default. */
11789
0
  p->active_connection_id_limit =
11790
0
    ngtcp2_max_uint64(NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT,
11791
0
                      params->active_connection_id_limit);
11792
0
  p->max_datagram_frame_size = params->max_datagram_frame_size;
11793
11794
  /* we might hit garbage, then set the sane default. */
11795
0
  if (params->max_udp_payload_size) {
11796
0
    p->max_udp_payload_size = ngtcp2_max_uint64(NGTCP2_MAX_UDP_PAYLOAD_SIZE,
11797
0
                                                params->max_udp_payload_size);
11798
0
  }
11799
11800
  /* These parameters are treated specially.  If server accepts early
11801
     data, it must not set values for these parameters that are
11802
     smaller than these remembered values. */
11803
0
  conn->early.transport_params = (ngtcp2_early_transport_params){
11804
0
    .initial_max_streams_bidi = params->initial_max_streams_bidi,
11805
0
    .initial_max_streams_uni = params->initial_max_streams_uni,
11806
0
    .initial_max_stream_data_bidi_local =
11807
0
      params->initial_max_stream_data_bidi_local,
11808
0
    .initial_max_stream_data_bidi_remote =
11809
0
      params->initial_max_stream_data_bidi_remote,
11810
0
    .initial_max_stream_data_uni = params->initial_max_stream_data_uni,
11811
0
    .initial_max_data = params->initial_max_data,
11812
0
    .active_connection_id_limit = params->active_connection_id_limit,
11813
0
    .max_datagram_frame_size = params->max_datagram_frame_size,
11814
0
  };
11815
11816
0
  conn_sync_stream_id_limit(conn);
11817
11818
0
  conn->tx.max_offset = p->initial_max_data;
11819
11820
0
  ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, p, conn->server,
11821
0
                                              NGTCP2_QLOG_SIDE_REMOTE);
11822
11823
0
  return 0;
11824
0
}
11825
11826
int ngtcp2_conn_set_local_transport_params_versioned(
11827
  ngtcp2_conn *conn, int transport_params_version,
11828
0
  const ngtcp2_transport_params *params) {
11829
0
  ngtcp2_transport_params paramsbuf;
11830
11831
0
  params = ngtcp2_transport_params_convert_to_latest(
11832
0
    &paramsbuf, transport_params_version, params);
11833
11834
0
  assert(conn->server);
11835
0
  assert(params->active_connection_id_limit >=
11836
0
         NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT);
11837
0
  assert(params->active_connection_id_limit <=
11838
0
         NGTCP2_DCIDTR_MAX_UNUSED_DCID_SIZE);
11839
11840
0
  if (conn->hs_pktns == NULL || conn->hs_pktns->crypto.tx.ckm) {
11841
0
    return NGTCP2_ERR_INVALID_STATE;
11842
0
  }
11843
11844
0
  conn_set_local_transport_params(conn, params);
11845
11846
0
  return 0;
11847
0
}
11848
11849
0
int ngtcp2_conn_commit_local_transport_params(ngtcp2_conn *conn) {
11850
0
  const ngtcp2_mem *mem = conn->mem;
11851
0
  ngtcp2_transport_params *params = &conn->local.transport_params;
11852
0
  ngtcp2_scid *scident;
11853
0
  int rv;
11854
11855
0
  assert(1 == ngtcp2_ksl_len(&conn->scid.set));
11856
11857
0
  params->initial_scid = conn->oscid;
11858
0
  params->initial_scid_present = 1;
11859
11860
0
  if (conn->oscid.datalen == 0) {
11861
0
    params->preferred_addr_present = 0;
11862
0
  }
11863
11864
0
  if (conn->server && params->preferred_addr_present) {
11865
0
    scident = ngtcp2_mem_malloc(mem, sizeof(*scident));
11866
0
    if (scident == NULL) {
11867
0
      return NGTCP2_ERR_NOMEM;
11868
0
    }
11869
11870
0
    ngtcp2_scid_init(scident, 1, &params->preferred_addr.cid);
11871
11872
0
    rv = ngtcp2_ksl_insert(&conn->scid.set, NULL, &scident->cid, scident);
11873
0
    if (rv != 0) {
11874
0
      ngtcp2_mem_free(mem, scident);
11875
0
      return rv;
11876
0
    }
11877
11878
0
    conn->scid.last_seq = 1;
11879
0
  }
11880
11881
0
  conn->rx.window = conn->rx.unsent_max_offset = conn->rx.max_offset =
11882
0
    params->initial_max_data;
11883
0
  conn->remote.bidi.unsent_max_streams = params->initial_max_streams_bidi;
11884
0
  conn->remote.bidi.max_streams = params->initial_max_streams_bidi;
11885
0
  conn->remote.uni.unsent_max_streams = params->initial_max_streams_uni;
11886
0
  conn->remote.uni.max_streams = params->initial_max_streams_uni;
11887
11888
0
  conn->flags |= NGTCP2_CONN_FLAG_LOCAL_TRANSPORT_PARAMS_COMMITTED;
11889
11890
0
  ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, params, conn->server,
11891
0
                                              NGTCP2_QLOG_SIDE_LOCAL);
11892
11893
0
  return 0;
11894
0
}
11895
11896
const ngtcp2_transport_params *
11897
0
ngtcp2_conn_get_local_transport_params(ngtcp2_conn *conn) {
11898
0
  return &conn->local.transport_params;
11899
0
}
11900
11901
ngtcp2_ssize ngtcp2_conn_encode_local_transport_params(ngtcp2_conn *conn,
11902
                                                       uint8_t *dest,
11903
0
                                                       size_t destlen) {
11904
0
  return ngtcp2_transport_params_encode(dest, destlen,
11905
0
                                        &conn->local.transport_params);
11906
0
}
11907
11908
int ngtcp2_conn_open_bidi_stream(ngtcp2_conn *conn, int64_t *pstream_id,
11909
0
                                 void *stream_user_data) {
11910
0
  int rv;
11911
0
  ngtcp2_strm *strm;
11912
11913
0
  if (ngtcp2_conn_get_streams_bidi_left(conn) == 0) {
11914
0
    return NGTCP2_ERR_STREAM_ID_BLOCKED;
11915
0
  }
11916
11917
0
  strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
11918
0
  if (strm == NULL) {
11919
0
    return NGTCP2_ERR_NOMEM;
11920
0
  }
11921
11922
0
  rv = ngtcp2_conn_init_stream(conn, strm, conn->local.bidi.next_stream_id,
11923
0
                               stream_user_data);
11924
0
  if (rv != 0) {
11925
0
    ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
11926
0
    return rv;
11927
0
  }
11928
11929
0
  *pstream_id = conn->local.bidi.next_stream_id;
11930
0
  conn->local.bidi.next_stream_id += 4;
11931
11932
0
  return 0;
11933
0
}
11934
11935
int ngtcp2_conn_open_uni_stream(ngtcp2_conn *conn, int64_t *pstream_id,
11936
0
                                void *stream_user_data) {
11937
0
  int rv;
11938
0
  ngtcp2_strm *strm;
11939
11940
0
  if (ngtcp2_conn_get_streams_uni_left(conn) == 0) {
11941
0
    return NGTCP2_ERR_STREAM_ID_BLOCKED;
11942
0
  }
11943
11944
0
  strm = ngtcp2_objalloc_strm_get(&conn->strm_objalloc);
11945
0
  if (strm == NULL) {
11946
0
    return NGTCP2_ERR_NOMEM;
11947
0
  }
11948
11949
0
  rv = ngtcp2_conn_init_stream(conn, strm, conn->local.uni.next_stream_id,
11950
0
                               stream_user_data);
11951
0
  if (rv != 0) {
11952
0
    ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
11953
0
    return rv;
11954
0
  }
11955
0
  ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_RD);
11956
11957
0
  *pstream_id = conn->local.uni.next_stream_id;
11958
0
  conn->local.uni.next_stream_id += 4;
11959
11960
0
  return 0;
11961
0
}
11962
11963
0
ngtcp2_strm *ngtcp2_conn_find_stream(ngtcp2_conn *conn, int64_t stream_id) {
11964
0
  return ngtcp2_map_find(&conn->strms, (uint64_t)stream_id);
11965
0
}
11966
11967
ngtcp2_ssize ngtcp2_conn_write_stream_versioned(
11968
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
11969
  ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, ngtcp2_ssize *pdatalen,
11970
  uint32_t flags, int64_t stream_id, const uint8_t *data, size_t datalen,
11971
0
  ngtcp2_tstamp ts) {
11972
0
  ngtcp2_vec datav, *v;
11973
0
  size_t datacnt;
11974
11975
0
  if (datalen == 0) {
11976
0
    v = NULL;
11977
0
    datacnt = 0;
11978
0
  } else {
11979
0
    datav.len = datalen;
11980
0
    datav.base = (uint8_t *)data;
11981
0
    v = &datav;
11982
0
    datacnt = 1;
11983
0
  }
11984
11985
0
  return ngtcp2_conn_writev_stream_versioned(conn, path, pkt_info_version, pi,
11986
0
                                             dest, destlen, pdatalen, flags,
11987
0
                                             stream_id, v, datacnt, ts);
11988
0
}
11989
11990
static ngtcp2_ssize
11991
conn_write_vmsg_wrapper(ngtcp2_conn *conn, ngtcp2_path *path,
11992
                        int pkt_info_version, ngtcp2_pkt_info *pi,
11993
                        uint8_t *dest, size_t destlen, uint8_t wflags,
11994
0
                        ngtcp2_vmsg *vmsg, ngtcp2_tstamp ts) {
11995
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
11996
0
  ngtcp2_ssize nwrite;
11997
11998
0
  nwrite = ngtcp2_conn_write_vmsg(conn, path, pkt_info_version, pi, dest,
11999
0
                                  destlen, wflags, vmsg, ts);
12000
0
  if (nwrite < 0) {
12001
0
    return nwrite;
12002
0
  }
12003
12004
0
  assert((size_t)nwrite <= destlen);
12005
12006
0
  if (cstat->bytes_in_flight >= cstat->cwnd) {
12007
0
    conn->rst.is_cwnd_limited = 1;
12008
0
  } else if ((cstat->cwnd >= cstat->ssthresh ||
12009
0
              cstat->bytes_in_flight * 2 < cstat->cwnd) &&
12010
0
             nwrite == 0 && conn_pacing_pkt_tx_allowed(conn, ts) &&
12011
0
             (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) &&
12012
             /* Because NGTCP2_CONN_FLAG_AGGREGATE_PKTS is set after a
12013
                packet is produced, if it is set, we are sure that we
12014
                are not app-limited. */
12015
0
             !(conn->flags & NGTCP2_CONN_FLAG_AGGREGATE_PKTS)) {
12016
0
    conn->rst.app_limited =
12017
0
      ngtcp2_max_uint64(conn->rst.delivered + cstat->bytes_in_flight, 1);
12018
0
  }
12019
12020
0
  return nwrite;
12021
0
}
12022
12023
ngtcp2_ssize ngtcp2_conn_writev_stream_versioned(
12024
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
12025
  ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, ngtcp2_ssize *pdatalen,
12026
  uint32_t flags, int64_t stream_id, const ngtcp2_vec *datav, size_t datavcnt,
12027
0
  ngtcp2_tstamp ts) {
12028
0
  ngtcp2_vmsg vmsg, *pvmsg;
12029
0
  ngtcp2_strm *strm;
12030
0
  int64_t datalen;
12031
0
  uint8_t wflags;
12032
12033
0
  if (pdatalen) {
12034
0
    *pdatalen = -1;
12035
0
  }
12036
12037
0
  if (stream_id != -1) {
12038
0
    strm = ngtcp2_conn_find_stream(conn, stream_id);
12039
0
    if (strm == NULL) {
12040
0
      return NGTCP2_ERR_STREAM_NOT_FOUND;
12041
0
    }
12042
12043
0
    if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
12044
0
      return NGTCP2_ERR_STREAM_SHUT_WR;
12045
0
    }
12046
12047
0
    datalen = ngtcp2_vec_len_varint(datav, datavcnt);
12048
0
    if (datalen == -1) {
12049
0
      return NGTCP2_ERR_INVALID_ARGUMENT;
12050
0
    }
12051
12052
0
    if (datalen == 0 && !(flags & NGTCP2_WRITE_STREAM_FLAG_FIN) &&
12053
0
        (strm->flags & NGTCP2_STRM_FLAG_ANY_SENT)) {
12054
0
      pvmsg = NULL;
12055
0
    } else {
12056
0
      if ((uint64_t)datalen > NGTCP2_MAX_VARINT - strm->tx.offset ||
12057
0
          (uint64_t)datalen > NGTCP2_MAX_VARINT - conn->tx.offset) {
12058
0
        return NGTCP2_ERR_INVALID_ARGUMENT;
12059
0
      }
12060
12061
0
      vmsg = (ngtcp2_vmsg){
12062
0
        .type = NGTCP2_VMSG_TYPE_STREAM,
12063
0
        .stream =
12064
0
          {
12065
0
            .strm = strm,
12066
0
            .data = datav,
12067
0
            .datacnt = datavcnt,
12068
0
            .pdatalen = pdatalen,
12069
0
            .flags = flags,
12070
0
          },
12071
0
      };
12072
12073
0
      pvmsg = &vmsg;
12074
0
    }
12075
0
  } else {
12076
0
    pvmsg = NULL;
12077
0
  }
12078
12079
0
  if (flags & NGTCP2_WRITE_STREAM_FLAG_PADDING) {
12080
0
    wflags = NGTCP2_WRITE_PKT_FLAG_PADDING_IF_NOT_EMPTY;
12081
0
  } else {
12082
0
    wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
12083
0
  }
12084
12085
0
  return conn_write_vmsg_wrapper(conn, path, pkt_info_version, pi, dest,
12086
0
                                 destlen, wflags, pvmsg, ts);
12087
0
}
12088
12089
ngtcp2_ssize ngtcp2_conn_write_datagram_versioned(
12090
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
12091
  ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, int *paccepted,
12092
  uint32_t flags, uint64_t dgram_id, const uint8_t *data, size_t datalen,
12093
0
  ngtcp2_tstamp ts) {
12094
0
  ngtcp2_vec datav, *v;
12095
0
  size_t datacnt;
12096
12097
0
  if (datalen == 0) {
12098
0
    v = NULL;
12099
0
    datacnt = 0;
12100
0
  } else {
12101
0
    datav.len = datalen;
12102
0
    datav.base = (uint8_t *)data;
12103
0
    v = &datav;
12104
0
    datacnt = 1;
12105
0
  }
12106
12107
0
  return ngtcp2_conn_writev_datagram_versioned(conn, path, pkt_info_version, pi,
12108
0
                                               dest, destlen, paccepted, flags,
12109
0
                                               dgram_id, v, datacnt, ts);
12110
0
}
12111
12112
ngtcp2_ssize ngtcp2_conn_writev_datagram_versioned(
12113
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
12114
  ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, int *paccepted,
12115
  uint32_t flags, uint64_t dgram_id, const ngtcp2_vec *datav, size_t datavcnt,
12116
0
  ngtcp2_tstamp ts) {
12117
0
  ngtcp2_vmsg vmsg;
12118
0
  int64_t datalen;
12119
0
  uint8_t wflags;
12120
12121
0
  if (paccepted) {
12122
0
    *paccepted = 0;
12123
0
  }
12124
12125
0
  if (conn->remote.transport_params == NULL ||
12126
0
      conn->remote.transport_params->max_datagram_frame_size == 0) {
12127
0
    return NGTCP2_ERR_INVALID_STATE;
12128
0
  }
12129
12130
0
  datalen = ngtcp2_vec_len_varint(datav, datavcnt);
12131
0
  if (datalen == -1
12132
#if SIZE_MAX < UINT64_MAX
12133
      || (uint64_t)datalen > SIZE_MAX
12134
#endif /* SIZE_MAX < UINT64_MAX */
12135
0
  ) {
12136
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
12137
0
  }
12138
12139
0
  if (conn->remote.transport_params->max_datagram_frame_size <
12140
0
      ngtcp2_pkt_datagram_framelen((size_t)datalen)) {
12141
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
12142
0
  }
12143
12144
0
  vmsg = (ngtcp2_vmsg){
12145
0
    .type = NGTCP2_VMSG_TYPE_DATAGRAM,
12146
0
    .datagram =
12147
0
      {
12148
0
        .data = datav,
12149
0
        .datacnt = datavcnt,
12150
0
        .dgram_id = dgram_id,
12151
0
        .paccepted = paccepted,
12152
0
        .flags = flags,
12153
0
      },
12154
0
  };
12155
12156
0
  if (flags & NGTCP2_WRITE_DATAGRAM_FLAG_PADDING) {
12157
0
    wflags = NGTCP2_WRITE_PKT_FLAG_PADDING_IF_NOT_EMPTY;
12158
0
  } else {
12159
0
    wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
12160
0
  }
12161
12162
0
  return conn_write_vmsg_wrapper(conn, path, pkt_info_version, pi, dest,
12163
0
                                 destlen, wflags, &vmsg, ts);
12164
0
}
12165
12166
ngtcp2_ssize ngtcp2_conn_write_vmsg(ngtcp2_conn *conn, ngtcp2_path *path,
12167
                                    int pkt_info_version, ngtcp2_pkt_info *pi,
12168
                                    uint8_t *dest, size_t destlen,
12169
                                    uint8_t wflags, ngtcp2_vmsg *vmsg,
12170
0
                                    ngtcp2_tstamp ts) {
12171
0
  ngtcp2_ssize nwrite;
12172
0
  size_t origlen;
12173
0
  size_t origdestlen = destlen;
12174
0
  int rv;
12175
0
  int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
12176
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
12177
0
  ngtcp2_ssize res = 0;
12178
0
  uint64_t server_tx_left;
12179
0
  int64_t prev_in_pkt_num = -1;
12180
0
  ngtcp2_ksl_it it;
12181
0
  ngtcp2_rtb_entry *rtbent;
12182
0
  (void)pkt_info_version;
12183
12184
0
  conn_update_timestamp(conn, ts);
12185
12186
0
  if (path) {
12187
0
    ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
12188
0
  }
12189
12190
0
  origlen = destlen =
12191
0
    conn_shape_udp_payload(conn, &conn->dcid.current, destlen);
12192
12193
0
  if (!ppe_pending && pi) {
12194
0
    pi->ecn = NGTCP2_ECN_NOT_ECT;
12195
0
  }
12196
12197
0
  switch (conn->state) {
12198
0
  case NGTCP2_CS_CLIENT_INITIAL:
12199
0
  case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
12200
0
    if (!conn_pacing_pkt_tx_allowed(conn, ts)) {
12201
0
      assert(!ppe_pending);
12202
12203
0
      return conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
12204
0
    }
12205
12206
0
    nwrite =
12207
0
      conn_client_write_handshake(conn, pi, dest, destlen, wflags, vmsg, ts);
12208
    /* We might be unable to write a packet because of depletion of
12209
       congestion window budget, perhaps due to packet loss that
12210
       shrinks the window drastically.  Then continue if we are in
12211
       post-handshake.  There, we might be able to write packets
12212
       exceeding CWND to avoid deadlock. */
12213
0
    if (nwrite < 0) {
12214
0
      return nwrite;
12215
0
    }
12216
0
    if (conn->state != NGTCP2_CS_POST_HANDSHAKE) {
12217
0
      return nwrite;
12218
0
    }
12219
12220
0
    if (nwrite) {
12221
0
      assert(dest[0] & NGTCP2_HEADER_FORM_BIT);
12222
0
      assert(conn->negotiated_version);
12223
12224
0
      if (ngtcp2_pkt_get_type_long(conn->negotiated_version, dest[0]) ==
12225
0
          NGTCP2_PKT_INITIAL) {
12226
0
        wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
12227
0
      }
12228
12229
0
      res = nwrite;
12230
0
      dest += nwrite;
12231
0
      destlen -= (size_t)nwrite;
12232
0
    }
12233
    /* Break here so that we can coalesces 1RTT packet. */
12234
0
    break;
12235
0
  case NGTCP2_CS_SERVER_INITIAL:
12236
0
  case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
12237
0
    if (!conn_pacing_pkt_tx_allowed(conn, ts)) {
12238
0
      assert(!ppe_pending);
12239
12240
0
      if (!(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
12241
0
        server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12242
0
        if (server_tx_left == 0) {
12243
0
          return 0;
12244
0
        }
12245
12246
0
        origlen = (size_t)ngtcp2_min_uint64((uint64_t)origlen, server_tx_left);
12247
0
      }
12248
12249
0
      return conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
12250
0
    }
12251
12252
0
    if (!ppe_pending) {
12253
0
      if (!(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
12254
0
        server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12255
0
        if (server_tx_left == 0) {
12256
0
          if (cstat->loss_detection_timer != UINT64_MAX) {
12257
0
            ngtcp2_log_info(
12258
0
              &conn->log, NGTCP2_LOG_EVENT_LDC,
12259
0
              "loss detection timer canceled due to amplification limit");
12260
0
            ngtcp2_conn_cancel_loss_detection_timer(conn);
12261
0
          }
12262
12263
0
          return 0;
12264
0
        }
12265
12266
0
        destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, server_tx_left);
12267
0
      }
12268
12269
0
      if (conn->in_pktns) {
12270
0
        it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
12271
0
        if (!ngtcp2_ksl_it_end(&it)) {
12272
0
          rtbent = ngtcp2_ksl_it_get(&it);
12273
0
          prev_in_pkt_num = rtbent->hd.pkt_num;
12274
0
        }
12275
0
      }
12276
12277
0
      nwrite = conn_write_handshake(conn, pi, dest, destlen, wflags,
12278
0
                                    /* write_datalen = */ 0, ts);
12279
0
      if (nwrite < 0) {
12280
0
        return nwrite;
12281
0
      }
12282
12283
0
      res = nwrite;
12284
0
      dest += nwrite;
12285
0
      destlen -= (size_t)nwrite;
12286
12287
0
      if (conn->in_pktns && nwrite > 0) {
12288
0
        it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
12289
0
        if (!ngtcp2_ksl_it_end(&it)) {
12290
0
          rtbent = ngtcp2_ksl_it_get(&it);
12291
0
          if (rtbent->hd.pkt_num != prev_in_pkt_num &&
12292
0
              (rtbent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
12293
0
            wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
12294
0
          }
12295
0
        }
12296
0
      }
12297
0
    }
12298
0
    if (conn->pktns.crypto.tx.ckm == NULL) {
12299
0
      return res;
12300
0
    }
12301
0
    break;
12302
0
  case NGTCP2_CS_POST_HANDSHAKE:
12303
0
    if (!conn_pacing_pkt_tx_allowed(conn, ts)) {
12304
0
      assert(!ppe_pending);
12305
12306
0
      if (conn->server &&
12307
0
          !(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
12308
0
        server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12309
0
        if (server_tx_left == 0) {
12310
0
          return 0;
12311
0
        }
12312
12313
0
        origlen = (size_t)ngtcp2_min_uint64((uint64_t)origlen, server_tx_left);
12314
0
      }
12315
12316
0
      return conn_write_ack_pkt(conn, pi, dest, origlen, NGTCP2_PKT_1RTT, ts);
12317
0
    }
12318
12319
0
    break;
12320
0
  case NGTCP2_CS_CLOSING:
12321
0
    return NGTCP2_ERR_CLOSING;
12322
0
  case NGTCP2_CS_DRAINING:
12323
0
    return NGTCP2_ERR_DRAINING;
12324
0
  default:
12325
0
    return 0;
12326
0
  }
12327
12328
0
  assert(conn->pktns.crypto.tx.ckm);
12329
12330
0
  if (conn_check_pkt_num_exhausted(conn)) {
12331
0
    return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
12332
0
  }
12333
12334
0
  if (vmsg) {
12335
0
    switch (vmsg->type) {
12336
0
    case NGTCP2_VMSG_TYPE_STREAM:
12337
0
      if (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_MORE) {
12338
0
        wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
12339
0
      }
12340
0
      break;
12341
0
    case NGTCP2_VMSG_TYPE_DATAGRAM:
12342
0
      if (vmsg->datagram.flags & NGTCP2_WRITE_DATAGRAM_FLAG_MORE) {
12343
0
        wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
12344
0
      }
12345
0
      break;
12346
0
    default:
12347
0
      break;
12348
0
    }
12349
0
  }
12350
12351
0
  if (ppe_pending) {
12352
0
    res = conn->pkt.hs_spktlen;
12353
    /* dest and destlen have already been adjusted in ppe in the first
12354
       run.  They are adjusted for probe packet later. */
12355
0
    nwrite = conn_write_pkt(conn, pi, dest, destlen, (size_t)res, vmsg,
12356
0
                            NGTCP2_PKT_1RTT, wflags, ts);
12357
0
    goto fin;
12358
0
  } else {
12359
0
    conn->pkt.require_padding =
12360
0
      (wflags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING);
12361
12362
0
    if (conn->state == NGTCP2_CS_POST_HANDSHAKE) {
12363
0
      rv = conn_prepare_key_update(conn, ts);
12364
0
      if (rv != 0) {
12365
0
        return rv;
12366
0
      }
12367
0
    }
12368
12369
0
    if (!conn->pktns.rtb.probe_pkt_left && conn_cwnd_is_zero(conn)) {
12370
0
      destlen = 0;
12371
0
    } else {
12372
0
      if (res == 0 && !(conn->flags & NGTCP2_CONN_FLAG_AGGREGATE_PKTS)) {
12373
0
        nwrite =
12374
0
          conn_write_path_response(conn, path, pi, dest, origdestlen, ts);
12375
0
        if (nwrite) {
12376
0
          goto fin;
12377
0
        }
12378
12379
0
        if (conn->pv) {
12380
0
          nwrite =
12381
0
            conn_write_path_challenge(conn, path, pi, dest, origdestlen, ts);
12382
0
          if (nwrite) {
12383
0
            goto fin;
12384
0
          }
12385
0
        }
12386
12387
0
        if (conn->pmtud &&
12388
0
            (conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) &&
12389
0
            (!conn->hs_pktns ||
12390
0
             ngtcp2_strm_streamfrq_empty(&conn->hs_pktns->crypto.strm))) {
12391
0
          nwrite = conn_write_pmtud_probe(conn, pi, dest, origdestlen, ts);
12392
0
          if (nwrite) {
12393
0
            goto fin;
12394
0
          }
12395
0
        }
12396
0
      }
12397
0
    }
12398
12399
0
    if (conn->server &&
12400
0
        !(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
12401
0
      server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12402
0
      origlen = (size_t)ngtcp2_min_uint64((uint64_t)origlen, server_tx_left);
12403
0
      destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, server_tx_left);
12404
12405
0
      if (server_tx_left == 0 &&
12406
0
          conn->cstat.loss_detection_timer != UINT64_MAX) {
12407
0
        ngtcp2_log_info(
12408
0
          &conn->log, NGTCP2_LOG_EVENT_LDC,
12409
0
          "loss detection timer canceled due to amplification limit");
12410
0
        ngtcp2_conn_cancel_loss_detection_timer(conn);
12411
0
      }
12412
0
    }
12413
0
  }
12414
12415
0
  if (res == 0) {
12416
0
    if (conn_handshake_remnants_left(conn)) {
12417
0
      if (conn_handshake_probe_left(conn) ||
12418
          /* Allow exceeding CWND if an Handshake packet needs to be
12419
             sent in order to avoid dead lock.  In some situation,
12420
             typically for client, 1 RTT packets may occupy in-flight
12421
             bytes (e.g., some large requests and PMTUD), and
12422
             Handshake packet loss shrinks CWND, and we may get in the
12423
             situation that we are unable to send Handshake packet. */
12424
0
          (conn->hs_pktns->rtb.num_pto_eliciting == 0 &&
12425
0
           !ngtcp2_strm_streamfrq_empty(&conn->hs_pktns->crypto.strm))) {
12426
0
        destlen = origlen;
12427
0
      }
12428
0
      nwrite = conn_write_handshake_pkts(conn, pi, dest, destlen,
12429
0
                                         /* write_datalen = */ 0, ts);
12430
0
      if (nwrite < 0) {
12431
0
        return nwrite;
12432
0
      }
12433
0
      if (nwrite > 0) {
12434
        /* This makes 1RTT packet padded.  If 1RTT packet is not going
12435
           to be sent, packet is already padded. */
12436
0
        if (ngtcp2_pkt_get_type_long(conn->negotiated_version, dest[0]) ==
12437
0
            NGTCP2_PKT_INITIAL) {
12438
0
          wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
12439
0
        }
12440
12441
0
        res = nwrite;
12442
0
        dest += nwrite;
12443
0
        destlen -= (size_t)nwrite;
12444
12445
        /* We only exceed CWND to avoid deadlock.  Do no write 1RTT
12446
           packet if CWND is depleted. */
12447
0
        if (conn_cwnd_is_zero(conn) && conn->pktns.rtb.probe_pkt_left == 0) {
12448
0
          return res;
12449
0
        }
12450
0
      } else if (destlen == 0) {
12451
0
        res = conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
12452
0
        if (res) {
12453
0
          return res;
12454
0
        }
12455
0
      }
12456
0
    }
12457
0
  }
12458
12459
0
  if (conn->pktns.rtb.probe_pkt_left) {
12460
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_CON,
12461
0
                     "transmit probe pkt left=%zu",
12462
0
                     conn->pktns.rtb.probe_pkt_left);
12463
12464
0
    nwrite = conn_write_pkt(conn, pi, dest, destlen, (size_t)res, vmsg,
12465
0
                            NGTCP2_PKT_1RTT, wflags, ts);
12466
12467
0
    goto fin;
12468
0
  }
12469
12470
0
  nwrite = conn_write_pkt(conn, pi, dest, destlen, (size_t)res, vmsg,
12471
0
                          NGTCP2_PKT_1RTT, wflags, ts);
12472
0
  if (nwrite) {
12473
0
    assert(nwrite != NGTCP2_ERR_NOBUF);
12474
0
    goto fin;
12475
0
  }
12476
12477
0
  if (res == 0) {
12478
0
    nwrite = conn_write_ack_pkt(conn, pi, dest, origlen, NGTCP2_PKT_1RTT, ts);
12479
0
  }
12480
12481
0
fin:
12482
0
  if (nwrite >= 0) {
12483
0
    res += nwrite;
12484
0
    return res;
12485
0
  }
12486
12487
0
  switch (nwrite) {
12488
0
  case NGTCP2_ERR_STREAM_DATA_BLOCKED:
12489
0
    if (!(wflags & NGTCP2_WRITE_PKT_FLAG_MORE)) {
12490
0
      if (res) {
12491
0
        return res;
12492
0
      }
12493
12494
0
      break;
12495
0
    }
12496
    /* fall through */
12497
0
  case NGTCP2_ERR_WRITE_MORE:
12498
0
    conn->pkt.hs_spktlen = res;
12499
0
    break;
12500
0
  }
12501
12502
0
  return nwrite;
12503
0
}
12504
12505
static ngtcp2_ssize
12506
conn_write_connection_close(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
12507
                            uint8_t *dest, size_t destlen, uint8_t pkt_type,
12508
                            uint64_t error_code, const uint8_t *reason,
12509
0
                            size_t reasonlen, ngtcp2_tstamp ts) {
12510
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
12511
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
12512
0
  ngtcp2_ssize res = 0, nwrite;
12513
0
  ngtcp2_frame fr;
12514
0
  uint8_t flags = NGTCP2_WRITE_PKT_FLAG_NONE;
12515
12516
0
  fr.connection_close = (ngtcp2_connection_close){
12517
0
    .type = NGTCP2_FRAME_CONNECTION_CLOSE,
12518
0
    .error_code = error_code,
12519
0
    .reasonlen = reasonlen,
12520
0
    .reason = (uint8_t *)reason,
12521
0
  };
12522
12523
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) &&
12524
0
      pkt_type != NGTCP2_PKT_INITIAL) {
12525
0
    if (in_pktns && conn->server) {
12526
0
      nwrite = ngtcp2_conn_write_single_frame_pkt(
12527
0
        conn, pi, dest, destlen, NGTCP2_PKT_INITIAL, NGTCP2_WRITE_PKT_FLAG_NONE,
12528
0
        &conn->dcid.current.cid, &fr, NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
12529
0
      if (nwrite < 0) {
12530
0
        return nwrite;
12531
0
      }
12532
12533
0
      dest += nwrite;
12534
0
      destlen -= (size_t)nwrite;
12535
0
      res += nwrite;
12536
0
    }
12537
12538
0
    if (pkt_type != NGTCP2_PKT_HANDSHAKE && hs_pktns &&
12539
0
        hs_pktns->crypto.tx.ckm) {
12540
0
      nwrite = ngtcp2_conn_write_single_frame_pkt(
12541
0
        conn, pi, dest, destlen, NGTCP2_PKT_HANDSHAKE,
12542
0
        NGTCP2_WRITE_PKT_FLAG_NONE, &conn->dcid.current.cid, &fr,
12543
0
        NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
12544
0
      if (nwrite < 0) {
12545
0
        return nwrite;
12546
0
      }
12547
12548
0
      dest += nwrite;
12549
0
      destlen -= (size_t)nwrite;
12550
0
      res += nwrite;
12551
0
    }
12552
0
  }
12553
12554
0
  if (!conn->server && pkt_type == NGTCP2_PKT_INITIAL) {
12555
0
    flags = NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
12556
0
  }
12557
12558
0
  nwrite = ngtcp2_conn_write_single_frame_pkt(
12559
0
    conn, pi, dest, destlen, pkt_type, flags, &conn->dcid.current.cid, &fr,
12560
0
    NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
12561
12562
0
  if (nwrite < 0) {
12563
0
    return nwrite;
12564
0
  }
12565
12566
0
  res += nwrite;
12567
12568
0
  if (res == 0) {
12569
0
    return NGTCP2_ERR_NOBUF;
12570
0
  }
12571
12572
0
  return res;
12573
0
}
12574
12575
ngtcp2_ssize ngtcp2_conn_write_connection_close_pkt(
12576
  ngtcp2_conn *conn, ngtcp2_path *path, ngtcp2_pkt_info *pi, uint8_t *dest,
12577
  size_t destlen, uint64_t error_code, const uint8_t *reason, size_t reasonlen,
12578
0
  ngtcp2_tstamp ts) {
12579
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
12580
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
12581
0
  uint8_t pkt_type;
12582
0
  ngtcp2_ssize nwrite;
12583
0
  uint64_t server_tx_left;
12584
12585
0
  if (conn_check_pkt_num_exhausted(conn)) {
12586
0
    return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
12587
0
  }
12588
12589
0
  switch (conn->state) {
12590
0
  case NGTCP2_CS_CLIENT_INITIAL:
12591
0
    return NGTCP2_ERR_INVALID_STATE;
12592
0
  case NGTCP2_CS_CLOSING:
12593
0
  case NGTCP2_CS_DRAINING:
12594
0
    return 0;
12595
0
  default:
12596
0
    break;
12597
0
  }
12598
12599
0
  if (path) {
12600
0
    ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
12601
0
  }
12602
12603
0
  destlen = conn_shape_udp_payload(conn, &conn->dcid.current, destlen);
12604
12605
0
  if (pi) {
12606
0
    pi->ecn = NGTCP2_ECN_NOT_ECT;
12607
0
  }
12608
12609
0
  if (conn->server) {
12610
0
    server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12611
0
    destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, server_tx_left);
12612
0
  }
12613
12614
0
  if (conn->state == NGTCP2_CS_POST_HANDSHAKE ||
12615
0
      (conn->server && conn->pktns.crypto.tx.ckm)) {
12616
0
    pkt_type = NGTCP2_PKT_1RTT;
12617
0
  } else if (hs_pktns && hs_pktns->crypto.tx.ckm) {
12618
0
    pkt_type = NGTCP2_PKT_HANDSHAKE;
12619
0
  } else if (in_pktns && in_pktns->crypto.tx.ckm) {
12620
0
    pkt_type = NGTCP2_PKT_INITIAL;
12621
0
  } else {
12622
    /* This branch is taken if server has not read any Initial packet
12623
       from client. */
12624
0
    return NGTCP2_ERR_INVALID_STATE;
12625
0
  }
12626
12627
0
  nwrite = conn_write_connection_close(conn, pi, dest, destlen, pkt_type,
12628
0
                                       error_code, reason, reasonlen, ts);
12629
0
  if (nwrite < 0) {
12630
0
    return nwrite;
12631
0
  }
12632
12633
0
  conn->state = NGTCP2_CS_CLOSING;
12634
12635
0
  return nwrite;
12636
0
}
12637
12638
ngtcp2_ssize ngtcp2_conn_write_application_close_pkt(
12639
  ngtcp2_conn *conn, ngtcp2_path *path, ngtcp2_pkt_info *pi, uint8_t *dest,
12640
  size_t destlen, uint64_t app_error_code, const uint8_t *reason,
12641
0
  size_t reasonlen, ngtcp2_tstamp ts) {
12642
0
  ngtcp2_ssize nwrite;
12643
0
  ngtcp2_ssize res = 0;
12644
0
  ngtcp2_frame fr;
12645
0
  uint64_t server_tx_left;
12646
12647
0
  if (conn_check_pkt_num_exhausted(conn)) {
12648
0
    return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
12649
0
  }
12650
12651
0
  switch (conn->state) {
12652
0
  case NGTCP2_CS_CLIENT_INITIAL:
12653
0
    return NGTCP2_ERR_INVALID_STATE;
12654
0
  case NGTCP2_CS_CLOSING:
12655
0
  case NGTCP2_CS_DRAINING:
12656
0
    return 0;
12657
0
  default:
12658
0
    break;
12659
0
  }
12660
12661
0
  if (path) {
12662
0
    ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
12663
0
  }
12664
12665
0
  destlen = conn_shape_udp_payload(conn, &conn->dcid.current, destlen);
12666
12667
0
  if (pi) {
12668
0
    pi->ecn = NGTCP2_ECN_NOT_ECT;
12669
0
  }
12670
12671
0
  if (conn->server) {
12672
0
    server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
12673
0
    destlen = (size_t)ngtcp2_min_uint64((uint64_t)destlen, server_tx_left);
12674
0
  }
12675
12676
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)) {
12677
0
    nwrite = conn_write_connection_close(
12678
0
      conn, pi, dest, destlen,
12679
0
      conn->hs_pktns->crypto.tx.ckm ? NGTCP2_PKT_HANDSHAKE : NGTCP2_PKT_INITIAL,
12680
0
      NGTCP2_APPLICATION_ERROR, NULL, 0, ts);
12681
0
    if (nwrite < 0) {
12682
0
      return nwrite;
12683
0
    }
12684
0
    res = nwrite;
12685
0
    dest += nwrite;
12686
0
    destlen -= (size_t)nwrite;
12687
0
  }
12688
12689
0
  if (conn->state != NGTCP2_CS_POST_HANDSHAKE &&
12690
0
      (!conn->server || !conn->pktns.crypto.tx.ckm)) {
12691
0
    return res;
12692
0
  }
12693
12694
0
  assert(conn->pktns.crypto.tx.ckm);
12695
12696
0
  fr.connection_close = (ngtcp2_connection_close){
12697
0
    .type = NGTCP2_FRAME_CONNECTION_CLOSE_APP,
12698
0
    .error_code = app_error_code,
12699
0
    .reasonlen = reasonlen,
12700
0
    .reason = (uint8_t *)reason,
12701
0
  };
12702
12703
0
  nwrite = ngtcp2_conn_write_single_frame_pkt(
12704
0
    conn, pi, dest, destlen, NGTCP2_PKT_1RTT, NGTCP2_WRITE_PKT_FLAG_NONE,
12705
0
    &conn->dcid.current.cid, &fr, NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
12706
12707
0
  if (nwrite < 0) {
12708
0
    return nwrite;
12709
0
  }
12710
12711
0
  res += nwrite;
12712
12713
0
  if (res == 0) {
12714
0
    return NGTCP2_ERR_NOBUF;
12715
0
  }
12716
12717
0
  conn->state = NGTCP2_CS_CLOSING;
12718
12719
0
  return res;
12720
0
}
12721
12722
static void ccerr_init(ngtcp2_ccerr *ccerr, ngtcp2_ccerr_type type,
12723
                       uint64_t error_code, const uint8_t *reason,
12724
0
                       size_t reasonlen) {
12725
0
  *ccerr = (ngtcp2_ccerr){
12726
0
    .type = type,
12727
0
    .error_code = error_code,
12728
0
    .reason = (uint8_t *)reason,
12729
0
    .reasonlen = reasonlen,
12730
0
  };
12731
0
}
12732
12733
0
void ngtcp2_ccerr_default(ngtcp2_ccerr *ccerr) {
12734
0
  ccerr_init(ccerr, NGTCP2_CCERR_TYPE_TRANSPORT, NGTCP2_NO_ERROR, NULL, 0);
12735
0
}
12736
12737
void ngtcp2_ccerr_set_transport_error(ngtcp2_ccerr *ccerr, uint64_t error_code,
12738
0
                                      const uint8_t *reason, size_t reasonlen) {
12739
0
  ccerr_init(ccerr, NGTCP2_CCERR_TYPE_TRANSPORT, error_code, reason, reasonlen);
12740
0
}
12741
12742
void ngtcp2_ccerr_set_liberr(ngtcp2_ccerr *ccerr, int liberr,
12743
0
                             const uint8_t *reason, size_t reasonlen) {
12744
0
  switch (liberr) {
12745
0
  case NGTCP2_ERR_RECV_VERSION_NEGOTIATION:
12746
0
    ccerr_init(ccerr, NGTCP2_CCERR_TYPE_VERSION_NEGOTIATION, NGTCP2_NO_ERROR,
12747
0
               reason, reasonlen);
12748
12749
0
    return;
12750
0
  case NGTCP2_ERR_IDLE_CLOSE:
12751
0
    ccerr_init(ccerr, NGTCP2_CCERR_TYPE_IDLE_CLOSE, NGTCP2_NO_ERROR, reason,
12752
0
               reasonlen);
12753
12754
0
    return;
12755
0
  case NGTCP2_ERR_DROP_CONN:
12756
0
    ccerr_init(ccerr, NGTCP2_CCERR_TYPE_DROP_CONN, NGTCP2_NO_ERROR, reason,
12757
0
               reasonlen);
12758
12759
0
    return;
12760
0
  case NGTCP2_ERR_RETRY:
12761
0
    ccerr_init(ccerr, NGTCP2_CCERR_TYPE_RETRY, NGTCP2_NO_ERROR, reason,
12762
0
               reasonlen);
12763
12764
0
    return;
12765
0
  }
12766
12767
0
  ngtcp2_ccerr_set_transport_error(
12768
0
    ccerr, ngtcp2_err_infer_quic_transport_error_code(liberr), reason,
12769
0
    reasonlen);
12770
0
}
12771
12772
void ngtcp2_ccerr_set_tls_alert(ngtcp2_ccerr *ccerr, uint8_t tls_alert,
12773
0
                                const uint8_t *reason, size_t reasonlen) {
12774
0
  ngtcp2_ccerr_set_transport_error(ccerr, NGTCP2_CRYPTO_ERROR | tls_alert,
12775
0
                                   reason, reasonlen);
12776
0
}
12777
12778
void ngtcp2_ccerr_set_application_error(ngtcp2_ccerr *ccerr,
12779
                                        uint64_t error_code,
12780
                                        const uint8_t *reason,
12781
0
                                        size_t reasonlen) {
12782
0
  ccerr_init(ccerr, NGTCP2_CCERR_TYPE_APPLICATION, error_code, reason,
12783
0
             reasonlen);
12784
0
}
12785
12786
ngtcp2_ssize ngtcp2_conn_write_connection_close_versioned(
12787
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
12788
  ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, const ngtcp2_ccerr *ccerr,
12789
0
  ngtcp2_tstamp ts) {
12790
0
  (void)pkt_info_version;
12791
12792
0
  conn_update_timestamp(conn, ts);
12793
12794
0
  switch (ccerr->type) {
12795
0
  case NGTCP2_CCERR_TYPE_TRANSPORT:
12796
0
    return ngtcp2_conn_write_connection_close_pkt(
12797
0
      conn, path, pi, dest, destlen, ccerr->error_code, ccerr->reason,
12798
0
      ccerr->reasonlen, ts);
12799
0
  case NGTCP2_CCERR_TYPE_APPLICATION:
12800
0
    return ngtcp2_conn_write_application_close_pkt(
12801
0
      conn, path, pi, dest, destlen, ccerr->error_code, ccerr->reason,
12802
0
      ccerr->reasonlen, ts);
12803
0
  default:
12804
0
    return 0;
12805
0
  }
12806
0
}
12807
12808
0
int ngtcp2_conn_in_closing_period(ngtcp2_conn *conn) {
12809
0
  return conn->state == NGTCP2_CS_CLOSING;
12810
0
}
12811
12812
0
int ngtcp2_conn_in_draining_period(ngtcp2_conn *conn) {
12813
0
  return conn->state == NGTCP2_CS_DRAINING;
12814
0
}
12815
12816
0
int ngtcp2_conn_close_stream(ngtcp2_conn *conn, ngtcp2_strm *strm) {
12817
0
  int rv;
12818
12819
0
  rv = conn_call_stream_close(conn, strm);
12820
0
  if (rv != 0) {
12821
0
    return rv;
12822
0
  }
12823
12824
0
  rv = ngtcp2_map_remove(&conn->strms, (ngtcp2_map_key_type)strm->stream_id);
12825
0
  if (rv != 0) {
12826
0
    assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
12827
0
    return rv;
12828
0
  }
12829
12830
0
  if (ngtcp2_strm_is_tx_queued(strm)) {
12831
0
    ngtcp2_pq_remove(&conn->tx.strmq, &strm->pe);
12832
0
  }
12833
12834
0
  ngtcp2_strm_free(strm);
12835
0
  ngtcp2_objalloc_strm_release(&conn->strm_objalloc, strm);
12836
12837
0
  return 0;
12838
0
}
12839
12840
int ngtcp2_conn_close_stream_if_shut_rdwr(ngtcp2_conn *conn,
12841
0
                                          ngtcp2_strm *strm) {
12842
0
  if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RDWR) ==
12843
0
        NGTCP2_STRM_FLAG_SHUT_RDWR &&
12844
0
      ((strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_RECVED) ||
12845
0
       ngtcp2_strm_rx_offset(strm) == strm->rx.last_offset) &&
12846
0
      (((strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM) &&
12847
0
        (strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_ACKED)) ||
12848
0
       ngtcp2_strm_is_all_tx_data_fin_acked(strm))) {
12849
0
    return ngtcp2_conn_close_stream(conn, strm);
12850
0
  }
12851
0
  return 0;
12852
0
}
12853
12854
/*
12855
 * conn_shutdown_stream_write closes send stream with error code
12856
 * |app_error_code|.  RESET_STREAM frame is scheduled.
12857
 *
12858
 * This function returns 0 if it succeeds, or one of the following
12859
 * negative error codes:
12860
 *
12861
 * NGTCP2_ERR_NOMEM
12862
 *     Out of memory.
12863
 */
12864
static int conn_shutdown_stream_write(ngtcp2_conn *conn, ngtcp2_strm *strm,
12865
0
                                      uint64_t app_error_code) {
12866
0
  ngtcp2_strm_set_app_error_code(strm, app_error_code);
12867
12868
0
  if ((strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM) ||
12869
0
      ngtcp2_strm_is_all_tx_data_fin_acked(strm)) {
12870
0
    return 0;
12871
0
  }
12872
12873
  /* Set this flag so that we don't accidentally send DATA to this
12874
     stream. */
12875
0
  strm->flags |= NGTCP2_STRM_FLAG_SHUT_WR | NGTCP2_STRM_FLAG_RESET_STREAM;
12876
12877
0
  ngtcp2_strm_streamfrq_clear(strm);
12878
12879
0
  return conn_reset_stream(conn, strm, app_error_code);
12880
0
}
12881
12882
/*
12883
 * conn_shutdown_stream_read closes read stream with error code
12884
 * |app_error_code|.  STOP_SENDING frame is scheduled.
12885
 *
12886
 * This function returns 0 if it succeeds, or one of the following
12887
 * negative error codes:
12888
 *
12889
 * NGTCP2_ERR_NOMEM
12890
 *     Out of memory.
12891
 */
12892
static int conn_shutdown_stream_read(ngtcp2_conn *conn, ngtcp2_strm *strm,
12893
0
                                     uint64_t app_error_code) {
12894
0
  ngtcp2_strm_set_app_error_code(strm, app_error_code);
12895
12896
0
  if (strm->flags &
12897
0
      (NGTCP2_STRM_FLAG_STOP_SENDING | NGTCP2_STRM_FLAG_RESET_STREAM_RECVED)) {
12898
0
    return 0;
12899
0
  }
12900
0
  if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
12901
0
      ngtcp2_strm_rx_offset(strm) == strm->rx.last_offset) {
12902
0
    return 0;
12903
0
  }
12904
12905
  /* Extend connection flow control window for the amount of data
12906
     which are not passed to application. */
12907
0
  if (!(strm->flags & NGTCP2_STRM_FLAG_RESET_STREAM_RECVED)) {
12908
0
    ngtcp2_conn_extend_max_offset(conn, strm->rx.last_offset -
12909
0
                                          ngtcp2_strm_rx_offset(strm));
12910
0
  }
12911
12912
0
  strm->flags |= NGTCP2_STRM_FLAG_STOP_SENDING;
12913
12914
0
  ngtcp2_strm_discard_reordered_data(strm);
12915
12916
0
  return conn_stop_sending(conn, strm, app_error_code);
12917
0
}
12918
12919
int ngtcp2_conn_shutdown_stream(ngtcp2_conn *conn, uint32_t flags,
12920
0
                                int64_t stream_id, uint64_t app_error_code) {
12921
0
  int rv;
12922
0
  ngtcp2_strm *strm;
12923
0
  (void)flags;
12924
12925
0
  strm = ngtcp2_conn_find_stream(conn, stream_id);
12926
0
  if (strm == NULL) {
12927
0
    return 0;
12928
0
  }
12929
12930
0
  if (bidi_stream(stream_id) || !conn_local_stream(conn, stream_id)) {
12931
0
    rv = conn_shutdown_stream_read(conn, strm, app_error_code);
12932
0
    if (rv != 0) {
12933
0
      return rv;
12934
0
    }
12935
0
  }
12936
12937
0
  if (bidi_stream(stream_id) || conn_local_stream(conn, stream_id)) {
12938
0
    rv = conn_shutdown_stream_write(conn, strm, app_error_code);
12939
0
    if (rv != 0) {
12940
0
      return rv;
12941
0
    }
12942
0
  }
12943
12944
0
  return 0;
12945
0
}
12946
12947
int ngtcp2_conn_shutdown_stream_write(ngtcp2_conn *conn, uint32_t flags,
12948
                                      int64_t stream_id,
12949
0
                                      uint64_t app_error_code) {
12950
0
  ngtcp2_strm *strm;
12951
0
  (void)flags;
12952
12953
0
  if (!bidi_stream(stream_id) && !conn_local_stream(conn, stream_id)) {
12954
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
12955
0
  }
12956
12957
0
  strm = ngtcp2_conn_find_stream(conn, stream_id);
12958
0
  if (strm == NULL) {
12959
0
    return 0;
12960
0
  }
12961
12962
0
  return conn_shutdown_stream_write(conn, strm, app_error_code);
12963
0
}
12964
12965
int ngtcp2_conn_shutdown_stream_read(ngtcp2_conn *conn, uint32_t flags,
12966
                                     int64_t stream_id,
12967
0
                                     uint64_t app_error_code) {
12968
0
  ngtcp2_strm *strm;
12969
0
  (void)flags;
12970
12971
0
  if (!bidi_stream(stream_id) && conn_local_stream(conn, stream_id)) {
12972
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
12973
0
  }
12974
12975
0
  strm = ngtcp2_conn_find_stream(conn, stream_id);
12976
0
  if (strm == NULL) {
12977
0
    return 0;
12978
0
  }
12979
12980
0
  return conn_shutdown_stream_read(conn, strm, app_error_code);
12981
0
}
12982
12983
/*
12984
 * conn_extend_max_stream_offset extends stream level flow control
12985
 * window by |datalen| of the stream denoted by |strm|.
12986
 *
12987
 * This function returns 0 if it succeeds, or one of the following
12988
 * negative error codes:
12989
 *
12990
 * NGTCP2_ERR_NOMEM
12991
 *     Out of memory.
12992
 */
12993
static int conn_extend_max_stream_offset(ngtcp2_conn *conn, ngtcp2_strm *strm,
12994
0
                                         uint64_t datalen) {
12995
0
  ngtcp2_strm *top;
12996
12997
0
  if (datalen > NGTCP2_MAX_VARINT ||
12998
0
      strm->rx.unsent_max_offset > NGTCP2_MAX_VARINT - datalen) {
12999
0
    strm->rx.unsent_max_offset = NGTCP2_MAX_VARINT;
13000
0
  } else {
13001
0
    strm->rx.unsent_max_offset += datalen;
13002
0
  }
13003
13004
0
  if (!(strm->flags &
13005
0
        (NGTCP2_STRM_FLAG_SHUT_RD | NGTCP2_STRM_FLAG_STOP_SENDING)) &&
13006
0
      !ngtcp2_strm_is_tx_queued(strm) &&
13007
0
      conn_should_send_max_stream_data(conn, strm)) {
13008
0
    if (!ngtcp2_pq_empty(&conn->tx.strmq)) {
13009
0
      top = ngtcp2_conn_tx_strmq_top(conn);
13010
0
      strm->cycle = top->cycle;
13011
0
    }
13012
0
    strm->cycle = conn_tx_strmq_first_cycle(conn);
13013
0
    return ngtcp2_conn_tx_strmq_push(conn, strm);
13014
0
  }
13015
13016
0
  return 0;
13017
0
}
13018
13019
int ngtcp2_conn_extend_max_stream_offset(ngtcp2_conn *conn, int64_t stream_id,
13020
0
                                         uint64_t datalen) {
13021
0
  ngtcp2_strm *strm;
13022
13023
0
  if (!bidi_stream(stream_id) && conn_local_stream(conn, stream_id)) {
13024
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
13025
0
  }
13026
13027
0
  strm = ngtcp2_conn_find_stream(conn, stream_id);
13028
0
  if (strm == NULL) {
13029
0
    return 0;
13030
0
  }
13031
13032
0
  return conn_extend_max_stream_offset(conn, strm, datalen);
13033
0
}
13034
13035
0
void ngtcp2_conn_extend_max_offset(ngtcp2_conn *conn, uint64_t datalen) {
13036
0
  if (NGTCP2_MAX_VARINT < datalen ||
13037
0
      conn->rx.unsent_max_offset > NGTCP2_MAX_VARINT - datalen) {
13038
0
    conn->rx.unsent_max_offset = NGTCP2_MAX_VARINT;
13039
0
    return;
13040
0
  }
13041
13042
0
  conn->rx.unsent_max_offset += datalen;
13043
0
}
13044
13045
0
void ngtcp2_conn_extend_max_streams_bidi(ngtcp2_conn *conn, size_t n) {
13046
0
  handle_max_remote_streams_extension(&conn->remote.bidi.unsent_max_streams, n);
13047
0
}
13048
13049
0
void ngtcp2_conn_extend_max_streams_uni(ngtcp2_conn *conn, size_t n) {
13050
0
  handle_max_remote_streams_extension(&conn->remote.uni.unsent_max_streams, n);
13051
0
}
13052
13053
0
const ngtcp2_cid *ngtcp2_conn_get_dcid(ngtcp2_conn *conn) {
13054
0
  return &conn->dcid.current.cid;
13055
0
}
13056
13057
0
const ngtcp2_cid *ngtcp2_conn_get_client_initial_dcid(ngtcp2_conn *conn) {
13058
0
  return &conn->rcid;
13059
0
}
13060
13061
0
uint32_t ngtcp2_conn_get_client_chosen_version(ngtcp2_conn *conn) {
13062
0
  return conn->client_chosen_version;
13063
0
}
13064
13065
0
uint32_t ngtcp2_conn_get_negotiated_version(ngtcp2_conn *conn) {
13066
0
  return conn->negotiated_version;
13067
0
}
13068
13069
0
static int delete_strms_pq_each(void *data, void *ptr) {
13070
0
  ngtcp2_conn *conn = ptr;
13071
0
  ngtcp2_strm *s = data;
13072
13073
0
  if (ngtcp2_strm_is_tx_queued(s)) {
13074
0
    ngtcp2_pq_remove(&conn->tx.strmq, &s->pe);
13075
0
  }
13076
13077
0
  ngtcp2_strm_free(s);
13078
0
  ngtcp2_objalloc_strm_release(&conn->strm_objalloc, s);
13079
13080
0
  return 0;
13081
0
}
13082
13083
/*
13084
 * conn_discard_early_data_state discards any connection states which
13085
 * are altered by any operations during early data transfer.
13086
 */
13087
0
static void conn_discard_early_data_state(ngtcp2_conn *conn) {
13088
0
  ngtcp2_frame_chain **pfrc, *frc;
13089
13090
0
  ngtcp2_rtb_remove_early_data(&conn->pktns.rtb, &conn->cstat);
13091
13092
0
  ngtcp2_map_each(&conn->strms, delete_strms_pq_each, conn);
13093
0
  ngtcp2_map_clear(&conn->strms);
13094
13095
0
  conn->tx.offset = 0;
13096
0
  conn->tx.last_blocked_offset = UINT64_MAX;
13097
13098
0
  conn->rx.unsent_max_offset = conn->rx.max_offset =
13099
0
    conn->local.transport_params.initial_max_data;
13100
13101
0
  conn->remote.bidi.unsent_max_streams = conn->remote.bidi.max_streams =
13102
0
    conn->local.transport_params.initial_max_streams_bidi;
13103
13104
0
  conn->remote.uni.unsent_max_streams = conn->remote.uni.max_streams =
13105
0
    conn->local.transport_params.initial_max_streams_uni;
13106
13107
0
  if (conn->server) {
13108
0
    conn->local.bidi.next_stream_id = 1;
13109
0
    conn->local.uni.next_stream_id = 3;
13110
0
  } else {
13111
0
    conn->local.bidi.next_stream_id = 0;
13112
0
    conn->local.uni.next_stream_id = 2;
13113
0
  }
13114
13115
0
  for (pfrc = &conn->pktns.tx.frq; *pfrc;) {
13116
0
    frc = *pfrc;
13117
0
    *pfrc = (*pfrc)->next;
13118
0
    ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
13119
0
  }
13120
0
}
13121
13122
0
int ngtcp2_conn_tls_early_data_rejected(ngtcp2_conn *conn) {
13123
0
  if (conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) {
13124
0
    return 0;
13125
0
  }
13126
13127
0
  conn->flags |= NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED;
13128
13129
0
  conn_discard_early_data_state(conn);
13130
13131
0
  if (conn->callbacks.tls_early_data_rejected) {
13132
0
    return conn->callbacks.tls_early_data_rejected(conn, conn->user_data);
13133
0
  }
13134
13135
0
  if (conn->early.ckm) {
13136
0
    conn_discard_early_key(conn);
13137
0
  }
13138
13139
0
  return 0;
13140
0
}
13141
13142
0
int ngtcp2_conn_get_tls_early_data_rejected(ngtcp2_conn *conn) {
13143
0
  return (conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) != 0;
13144
0
}
13145
13146
void ngtcp2_conn_update_rtt(ngtcp2_conn *conn, ngtcp2_duration rtt,
13147
0
                            ngtcp2_duration ack_delay, ngtcp2_tstamp ts) {
13148
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13149
13150
0
  assert(rtt > 0);
13151
13152
0
  if (cstat->min_rtt == UINT64_MAX) {
13153
0
    cstat->latest_rtt = rtt;
13154
0
    cstat->min_rtt = rtt;
13155
0
    cstat->smoothed_rtt = rtt;
13156
0
    cstat->rttvar = rtt / 2;
13157
0
    cstat->first_rtt_sample_ts = ts;
13158
0
  } else {
13159
0
    if (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) {
13160
0
      assert(conn->remote.transport_params);
13161
13162
0
      ack_delay = ngtcp2_min_uint64(
13163
0
        ack_delay, conn->remote.transport_params->max_ack_delay);
13164
0
    } else if (ack_delay > 0 && rtt >= cstat->min_rtt &&
13165
0
               rtt < cstat->min_rtt + ack_delay) {
13166
      /* Ignore RTT sample if adjusting ack_delay causes the sample
13167
         less than min_rtt before handshake confirmation. */
13168
0
      ngtcp2_log_infof(
13169
0
        &conn->log, NGTCP2_LOG_EVENT_LDC,
13170
0
        "ignore rtt sample because ack_delay is too large latest_rtt=%" PRIu64
13171
0
        " min_rtt=%" PRIu64 " ack_delay=%" PRIu64,
13172
0
        rtt / NGTCP2_MILLISECONDS, cstat->min_rtt / NGTCP2_MILLISECONDS,
13173
0
        ack_delay / NGTCP2_MILLISECONDS);
13174
0
      return;
13175
0
    }
13176
13177
0
    cstat->latest_rtt = rtt;
13178
0
    cstat->min_rtt = ngtcp2_min_uint64(cstat->min_rtt, rtt);
13179
13180
0
    if (rtt >= cstat->min_rtt + ack_delay) {
13181
0
      rtt -= ack_delay;
13182
0
    }
13183
13184
0
    cstat->rttvar = (cstat->rttvar * 3 + (cstat->smoothed_rtt < rtt
13185
0
                                            ? rtt - cstat->smoothed_rtt
13186
0
                                            : cstat->smoothed_rtt - rtt)) /
13187
0
                    4;
13188
0
    cstat->smoothed_rtt = (cstat->smoothed_rtt * 7 + rtt) / 8;
13189
0
  }
13190
13191
0
  ngtcp2_log_infof(
13192
0
    &conn->log, NGTCP2_LOG_EVENT_LDC,
13193
0
    "latest_rtt=%" PRIu64 " min_rtt=%" PRIu64 " smoothed_rtt=%" PRIu64
13194
0
    " rttvar=%" PRIu64 " ack_delay=%" PRIu64,
13195
0
    cstat->latest_rtt / NGTCP2_MILLISECONDS,
13196
0
    cstat->min_rtt / NGTCP2_MILLISECONDS,
13197
0
    cstat->smoothed_rtt / NGTCP2_MILLISECONDS,
13198
0
    cstat->rttvar / NGTCP2_MILLISECONDS, ack_delay / NGTCP2_MILLISECONDS);
13199
0
}
13200
13201
void ngtcp2_conn_get_conn_info_versioned(ngtcp2_conn *conn,
13202
                                         int conn_info_version,
13203
0
                                         ngtcp2_conn_info *cinfo) {
13204
0
  ngtcp2_conn_info_init_versioned(conn_info_version, cinfo, &conn->cstat);
13205
0
}
13206
13207
static void conn_get_loss_time_and_pktns(ngtcp2_conn *conn,
13208
                                         ngtcp2_tstamp *ploss_time,
13209
0
                                         ngtcp2_pktns **ppktns) {
13210
0
  ngtcp2_pktns *const ns[] = {conn->hs_pktns, &conn->pktns};
13211
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13212
0
  ngtcp2_duration *loss_time = cstat->loss_time + 1;
13213
0
  ngtcp2_tstamp earliest_loss_time = cstat->loss_time[NGTCP2_PKTNS_ID_INITIAL];
13214
0
  ngtcp2_pktns *pktns = conn->in_pktns;
13215
0
  size_t i;
13216
13217
0
  for (i = 0; i < ngtcp2_arraylen(ns); ++i) {
13218
0
    if (ns[i] == NULL || loss_time[i] >= earliest_loss_time) {
13219
0
      continue;
13220
0
    }
13221
13222
0
    earliest_loss_time = loss_time[i];
13223
0
    pktns = ns[i];
13224
0
  }
13225
13226
0
  if (ploss_time) {
13227
0
    *ploss_time = earliest_loss_time;
13228
0
  }
13229
0
  if (ppktns) {
13230
0
    *ppktns = pktns;
13231
0
  }
13232
0
}
13233
13234
static ngtcp2_tstamp conn_get_earliest_pto_expiry(ngtcp2_conn *conn,
13235
0
                                                  ngtcp2_tstamp ts) {
13236
0
  ngtcp2_pktns *const ns[] = {conn->in_pktns, conn->hs_pktns, &conn->pktns};
13237
0
  size_t i;
13238
0
  ngtcp2_tstamp earliest_ts = UINT64_MAX, t;
13239
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13240
0
  ngtcp2_tstamp *times = cstat->last_tx_pkt_ts;
13241
0
  ngtcp2_duration duration =
13242
0
    compute_pto(cstat->smoothed_rtt, cstat->rttvar, /* max_ack_delay = */ 0) *
13243
0
    (1ULL << cstat->pto_count);
13244
13245
0
  for (i = NGTCP2_PKTNS_ID_INITIAL; i < NGTCP2_PKTNS_ID_MAX; ++i) {
13246
0
    if (ns[i] == NULL || ns[i]->rtb.num_pto_eliciting == 0 ||
13247
0
        (times[i] == UINT64_MAX ||
13248
0
         (i == NGTCP2_PKTNS_ID_APPLICATION &&
13249
0
          !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
13250
0
      continue;
13251
0
    }
13252
13253
0
    t = times[i] + duration;
13254
13255
0
    if (i == NGTCP2_PKTNS_ID_APPLICATION) {
13256
0
      assert(conn->remote.transport_params);
13257
0
      t += conn->remote.transport_params->max_ack_delay *
13258
0
           (1ULL << cstat->pto_count);
13259
0
    }
13260
13261
0
    if (t < earliest_ts) {
13262
0
      earliest_ts = t;
13263
0
    }
13264
0
  }
13265
13266
0
  if (earliest_ts == UINT64_MAX) {
13267
0
    return ts + duration;
13268
0
  }
13269
13270
0
  return earliest_ts;
13271
0
}
13272
13273
0
void ngtcp2_conn_set_loss_detection_timer(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
13274
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13275
0
  ngtcp2_duration timeout;
13276
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
13277
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
13278
0
  ngtcp2_pktns *pktns = &conn->pktns;
13279
0
  ngtcp2_tstamp earliest_loss_time;
13280
13281
0
  conn_get_loss_time_and_pktns(conn, &earliest_loss_time, NULL);
13282
13283
0
  if (earliest_loss_time != UINT64_MAX) {
13284
0
    cstat->loss_detection_timer = earliest_loss_time;
13285
13286
0
    ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_LDC,
13287
0
                     "loss_detection_timer=%" PRIu64
13288
0
                     " nonzero crypto loss time",
13289
0
                     cstat->loss_detection_timer);
13290
0
    return;
13291
0
  }
13292
13293
0
  if ((!in_pktns || in_pktns->rtb.num_pto_eliciting == 0) &&
13294
0
      (!hs_pktns || hs_pktns->rtb.num_pto_eliciting == 0) &&
13295
0
      (pktns->rtb.num_pto_eliciting == 0 ||
13296
0
       !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)) &&
13297
0
      (conn->server ||
13298
0
       (conn->flags & (NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED |
13299
0
                       NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
13300
0
    if (cstat->loss_detection_timer != UINT64_MAX) {
13301
0
      ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_LDC,
13302
0
                      "loss detection timer canceled");
13303
0
      ngtcp2_conn_cancel_loss_detection_timer(conn);
13304
0
    }
13305
0
    return;
13306
0
  }
13307
13308
0
  cstat->loss_detection_timer = conn_get_earliest_pto_expiry(conn, ts);
13309
13310
0
  timeout =
13311
0
    cstat->loss_detection_timer > ts ? cstat->loss_detection_timer - ts : 0;
13312
13313
0
  ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_LDC,
13314
0
                   "loss_detection_timer=%" PRIu64 " timeout=%" PRIu64,
13315
0
                   cstat->loss_detection_timer, timeout / NGTCP2_MILLISECONDS);
13316
0
}
13317
13318
0
void ngtcp2_conn_cancel_loss_detection_timer(ngtcp2_conn *conn) {
13319
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13320
13321
0
  cstat->loss_detection_timer = UINT64_MAX;
13322
0
  cstat->pto_count = 0;
13323
0
}
13324
13325
0
int ngtcp2_conn_on_loss_detection_timer(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
13326
0
  ngtcp2_conn_stat *cstat = &conn->cstat;
13327
0
  int rv;
13328
0
  ngtcp2_pktns *in_pktns = conn->in_pktns;
13329
0
  ngtcp2_pktns *hs_pktns = conn->hs_pktns;
13330
0
  ngtcp2_tstamp earliest_loss_time;
13331
0
  ngtcp2_pktns *loss_pktns = NULL;
13332
13333
0
  switch (conn->state) {
13334
0
  case NGTCP2_CS_CLOSING:
13335
0
  case NGTCP2_CS_DRAINING:
13336
0
    ngtcp2_conn_cancel_loss_detection_timer(conn);
13337
0
    return 0;
13338
0
  default:
13339
0
    break;
13340
0
  }
13341
13342
0
  if (cstat->loss_detection_timer == UINT64_MAX) {
13343
0
    return 0;
13344
0
  }
13345
13346
0
  conn_get_loss_time_and_pktns(conn, &earliest_loss_time, &loss_pktns);
13347
13348
0
  ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_LDC,
13349
0
                  "loss detection timer fired");
13350
13351
0
  if (earliest_loss_time != UINT64_MAX) {
13352
0
    assert(loss_pktns);
13353
13354
0
    rv = ngtcp2_conn_detect_lost_pkt(conn, loss_pktns, cstat, ts);
13355
0
    if (rv != 0) {
13356
0
      return rv;
13357
0
    }
13358
0
    ngtcp2_conn_set_loss_detection_timer(conn, ts);
13359
0
    return 0;
13360
0
  }
13361
13362
0
  if (!conn->server && !conn_is_tls_handshake_completed(conn)) {
13363
0
    if (hs_pktns->crypto.tx.ckm) {
13364
0
      hs_pktns->rtb.probe_pkt_left = 1;
13365
0
    } else {
13366
0
      in_pktns->rtb.probe_pkt_left = 1;
13367
0
    }
13368
0
  } else {
13369
0
    if (in_pktns && in_pktns->rtb.num_pto_eliciting) {
13370
0
      in_pktns->rtb.probe_pkt_left = 1;
13371
13372
0
      assert(hs_pktns);
13373
13374
0
      if (conn->server && hs_pktns->rtb.num_pto_eliciting) {
13375
        /* let server coalesce packets */
13376
0
        hs_pktns->rtb.probe_pkt_left = 1;
13377
0
      }
13378
0
    } else if (hs_pktns && hs_pktns->rtb.num_pto_eliciting) {
13379
0
      hs_pktns->rtb.probe_pkt_left = 2;
13380
0
    } else {
13381
0
      conn->pktns.rtb.probe_pkt_left = 2;
13382
0
    }
13383
0
  }
13384
13385
0
  ++cstat->pto_count;
13386
13387
0
  ngtcp2_log_infof(&conn->log, NGTCP2_LOG_EVENT_LDC, "pto_count=%zu",
13388
0
                   cstat->pto_count);
13389
13390
0
  ngtcp2_conn_set_loss_detection_timer(conn, ts);
13391
13392
0
  return 0;
13393
0
}
13394
13395
static int conn_buffer_crypto_data(ngtcp2_conn *conn, const uint8_t **pdata,
13396
                                   ngtcp2_pktns *pktns, const uint8_t *data,
13397
0
                                   size_t datalen) {
13398
0
  int rv;
13399
0
  ngtcp2_buf_chain **pbufchain = &pktns->crypto.tx.data;
13400
13401
0
  if (*pbufchain) {
13402
0
    for (; (*pbufchain)->next; pbufchain = &(*pbufchain)->next)
13403
0
      ;
13404
13405
0
    if (ngtcp2_buf_left(&(*pbufchain)->buf) < datalen) {
13406
0
      pbufchain = &(*pbufchain)->next;
13407
0
    }
13408
0
  }
13409
13410
0
  if (!*pbufchain) {
13411
0
    rv = ngtcp2_buf_chain_new(pbufchain, ngtcp2_max_size(1024, datalen),
13412
0
                              conn->mem);
13413
0
    if (rv != 0) {
13414
0
      return rv;
13415
0
    }
13416
0
  }
13417
13418
0
  *pdata = (*pbufchain)->buf.last;
13419
0
  (*pbufchain)->buf.last = ngtcp2_cpymem((*pbufchain)->buf.last, data, datalen);
13420
13421
0
  return 0;
13422
0
}
13423
13424
int ngtcp2_conn_submit_crypto_data(ngtcp2_conn *conn,
13425
                                   ngtcp2_encryption_level encryption_level,
13426
0
                                   const uint8_t *data, const size_t datalen) {
13427
0
  ngtcp2_pktns *pktns;
13428
0
  ngtcp2_frame_chain *frc;
13429
0
  int rv;
13430
13431
0
  if (datalen == 0) {
13432
0
    return 0;
13433
0
  }
13434
13435
0
  switch (encryption_level) {
13436
0
  case NGTCP2_ENCRYPTION_LEVEL_INITIAL:
13437
0
    assert(conn->in_pktns);
13438
0
    pktns = conn->in_pktns;
13439
0
    break;
13440
0
  case NGTCP2_ENCRYPTION_LEVEL_HANDSHAKE:
13441
0
    assert(conn->hs_pktns);
13442
0
    pktns = conn->hs_pktns;
13443
0
    break;
13444
0
  case NGTCP2_ENCRYPTION_LEVEL_1RTT:
13445
0
    pktns = &conn->pktns;
13446
0
    break;
13447
0
  default:
13448
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
13449
0
  }
13450
13451
0
  rv = conn_buffer_crypto_data(conn, &data, pktns, data, datalen);
13452
0
  if (rv != 0) {
13453
0
    return rv;
13454
0
  }
13455
13456
0
  rv = ngtcp2_frame_chain_stream_datacnt_objalloc_new(
13457
0
    &frc, 1, &conn->frc_objalloc, conn->mem);
13458
0
  if (rv != 0) {
13459
0
    return rv;
13460
0
  }
13461
13462
0
  frc->fr.stream.type = NGTCP2_FRAME_CRYPTO;
13463
0
  frc->fr.stream.flags = 0;
13464
0
  frc->fr.stream.fin = 0;
13465
0
  frc->fr.stream.stream_id = 0;
13466
0
  frc->fr.stream.offset = pktns->crypto.tx.offset;
13467
0
  frc->fr.stream.datacnt = 1;
13468
0
  frc->fr.stream.data[0] = (ngtcp2_vec){
13469
0
    .base = (uint8_t *)data,
13470
0
    .len = datalen,
13471
0
  };
13472
13473
0
  rv = ngtcp2_strm_streamfrq_push(&pktns->crypto.strm, frc);
13474
0
  if (rv != 0) {
13475
0
    ngtcp2_frame_chain_objalloc_del(frc, &conn->frc_objalloc, conn->mem);
13476
0
    return rv;
13477
0
  }
13478
13479
0
  pktns->crypto.strm.tx.offset += datalen;
13480
0
  pktns->crypto.tx.offset += datalen;
13481
13482
0
  return 0;
13483
0
}
13484
13485
int ngtcp2_conn_submit_new_token(ngtcp2_conn *conn, const uint8_t *token,
13486
0
                                 size_t tokenlen) {
13487
0
  int rv;
13488
0
  ngtcp2_frame_chain *nfrc;
13489
13490
0
  assert(conn->server);
13491
0
  assert(token);
13492
0
  assert(tokenlen);
13493
13494
0
  rv = ngtcp2_frame_chain_new_token_objalloc_new(
13495
0
    &nfrc, token, tokenlen, &conn->frc_objalloc, conn->mem);
13496
0
  if (rv != 0) {
13497
0
    return rv;
13498
0
  }
13499
13500
0
  nfrc->next = conn->pktns.tx.frq;
13501
0
  conn->pktns.tx.frq = nfrc;
13502
13503
0
  return 0;
13504
0
}
13505
13506
0
ngtcp2_strm *ngtcp2_conn_tx_strmq_top(ngtcp2_conn *conn) {
13507
0
  assert(!ngtcp2_pq_empty(&conn->tx.strmq));
13508
0
  return ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
13509
0
}
13510
13511
0
void ngtcp2_conn_tx_strmq_pop(ngtcp2_conn *conn) {
13512
0
  ngtcp2_strm *strm = ngtcp2_conn_tx_strmq_top(conn);
13513
0
  assert(strm);
13514
0
  ngtcp2_pq_pop(&conn->tx.strmq);
13515
0
  strm->pe.index = NGTCP2_PQ_BAD_INDEX;
13516
0
}
13517
13518
0
int ngtcp2_conn_tx_strmq_push(ngtcp2_conn *conn, ngtcp2_strm *strm) {
13519
0
  return ngtcp2_pq_push(&conn->tx.strmq, &strm->pe);
13520
0
}
13521
13522
0
static int conn_has_uncommitted_preferred_addr_cid(ngtcp2_conn *conn) {
13523
0
  return conn->server &&
13524
0
         !(conn->flags & NGTCP2_CONN_FLAG_LOCAL_TRANSPORT_PARAMS_COMMITTED) &&
13525
0
         conn->oscid.datalen &&
13526
0
         conn->local.transport_params.preferred_addr_present;
13527
0
}
13528
13529
0
size_t ngtcp2_conn_get_scid(ngtcp2_conn *conn, ngtcp2_cid *dest) {
13530
0
  ngtcp2_cid *origdest = dest;
13531
0
  ngtcp2_ksl_it it;
13532
0
  ngtcp2_scid *scid;
13533
13534
0
  if (dest == NULL) {
13535
0
    return ngtcp2_ksl_len(&conn->scid.set) +
13536
0
           (size_t)conn_has_uncommitted_preferred_addr_cid(conn);
13537
0
  }
13538
13539
0
  for (it = ngtcp2_ksl_begin(&conn->scid.set); !ngtcp2_ksl_it_end(&it);
13540
0
       ngtcp2_ksl_it_next(&it)) {
13541
0
    scid = ngtcp2_ksl_it_get(&it);
13542
0
    *dest++ = scid->cid;
13543
0
  }
13544
13545
0
  if (conn_has_uncommitted_preferred_addr_cid(conn)) {
13546
0
    *dest++ = conn->local.transport_params.preferred_addr.cid;
13547
0
  }
13548
13549
0
  return (size_t)(dest - origdest);
13550
0
}
13551
13552
0
static size_t conn_get_num_active_dcid(ngtcp2_conn *conn) {
13553
0
  size_t n = 1; /* for conn->dcid.current */
13554
0
  ngtcp2_pv *pv = conn->pv;
13555
13556
0
  if (conn->dcid.current.cid.datalen == 0) {
13557
0
    return n;
13558
0
  }
13559
13560
0
  if (pv) {
13561
0
    if (pv->dcid.seq != conn->dcid.current.seq) {
13562
0
      ++n;
13563
0
    }
13564
0
    if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
13565
0
        pv->fallback_dcid.seq != conn->dcid.current.seq &&
13566
0
        pv->fallback_dcid.seq != pv->dcid.seq) {
13567
0
      ++n;
13568
0
    }
13569
0
  }
13570
13571
0
  n += ngtcp2_dcidtr_retired_len(&conn->dcid.dtr);
13572
13573
0
  return n;
13574
0
}
13575
13576
0
size_t ngtcp2_conn_get_active_dcid(ngtcp2_conn *conn, ngtcp2_cid_token *dest) {
13577
0
  ngtcp2_cid_token2 cid_tokens[/* current */ 1 + /* pv */ 2 +
13578
0
                               NGTCP2_DCIDTR_MAX_RETIRED_DCID_SIZE];
13579
0
  size_t n, i;
13580
13581
0
  if (!dest) {
13582
0
    return ngtcp2_conn_get_active_dcid2(conn, NULL);
13583
0
  }
13584
13585
0
  n = ngtcp2_conn_get_active_dcid2(conn, cid_tokens);
13586
13587
0
  for (i = 0; i < n; ++i) {
13588
0
    dest[i].seq = cid_tokens[i].seq;
13589
0
    dest[i].cid = cid_tokens[i].cid;
13590
0
    ngtcp2_path_storage_init2(&dest[i].ps, &cid_tokens[i].ps.path);
13591
0
    dest[i].token_present = cid_tokens[i].token_present;
13592
13593
0
    if (dest[i].token_present) {
13594
0
      memcpy(dest[i].token, cid_tokens[i].token.data, sizeof(dest[i].token));
13595
0
    }
13596
0
  }
13597
13598
0
  return n;
13599
0
}
13600
13601
static void copy_dcid_to_cid_token(ngtcp2_cid_token2 *dest,
13602
0
                                   const ngtcp2_dcid *src) {
13603
0
  dest->seq = src->seq;
13604
0
  dest->cid = src->cid;
13605
0
  ngtcp2_path_storage_init2(&dest->ps, &src->ps.path);
13606
0
  if ((dest->token_present =
13607
0
         (src->flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT) != 0)) {
13608
0
    dest->token = src->token;
13609
0
  }
13610
0
}
13611
13612
size_t ngtcp2_conn_get_active_dcid2(ngtcp2_conn *conn,
13613
0
                                    ngtcp2_cid_token2 *dest) {
13614
0
  ngtcp2_pv *pv = conn->pv;
13615
0
  ngtcp2_cid_token2 *orig = dest;
13616
0
  ngtcp2_dcid *dcid;
13617
0
  size_t len, i;
13618
13619
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
13620
0
    return 0;
13621
0
  }
13622
13623
0
  if (dest == NULL) {
13624
0
    return conn_get_num_active_dcid(conn);
13625
0
  }
13626
13627
0
  copy_dcid_to_cid_token(dest, &conn->dcid.current);
13628
0
  ++dest;
13629
13630
0
  if (conn->dcid.current.cid.datalen == 0) {
13631
0
    return 1;
13632
0
  }
13633
13634
0
  if (pv) {
13635
0
    if (pv->dcid.seq != conn->dcid.current.seq) {
13636
0
      copy_dcid_to_cid_token(dest, &pv->dcid);
13637
0
      ++dest;
13638
0
    }
13639
0
    if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_PRESENT) &&
13640
0
        pv->fallback_dcid.seq != conn->dcid.current.seq &&
13641
0
        pv->fallback_dcid.seq != pv->dcid.seq) {
13642
0
      copy_dcid_to_cid_token(dest, &pv->fallback_dcid);
13643
0
      ++dest;
13644
0
    }
13645
0
  }
13646
13647
0
  len = ngtcp2_ringbuf_len(&conn->dcid.dtr.retired.rb);
13648
0
  for (i = 0; i < len; ++i) {
13649
0
    dcid = ngtcp2_ringbuf_get(&conn->dcid.dtr.retired.rb, i);
13650
0
    copy_dcid_to_cid_token(dest, dcid);
13651
0
    ++dest;
13652
0
  }
13653
13654
0
  return (size_t)(dest - orig);
13655
0
}
13656
13657
0
void ngtcp2_conn_set_local_addr(ngtcp2_conn *conn, const ngtcp2_addr *addr) {
13658
0
  ngtcp2_addr *dest = &conn->dcid.current.ps.path.local;
13659
13660
0
  assert(addr->addrlen <=
13661
0
         (ngtcp2_socklen)sizeof(conn->dcid.current.ps.local_addrbuf));
13662
0
  ngtcp2_addr_copy(dest, addr);
13663
0
}
13664
13665
0
void ngtcp2_conn_set_path_user_data(ngtcp2_conn *conn, void *path_user_data) {
13666
0
  conn->dcid.current.ps.path.user_data = path_user_data;
13667
0
}
13668
13669
0
const ngtcp2_path *ngtcp2_conn_get_path(ngtcp2_conn *conn) {
13670
0
  return &conn->dcid.current.ps.path;
13671
0
}
13672
13673
0
size_t ngtcp2_conn_get_max_tx_udp_payload_size(ngtcp2_conn *conn) {
13674
0
  return conn->local.settings.max_tx_udp_payload_size;
13675
0
}
13676
13677
0
size_t ngtcp2_conn_get_path_max_tx_udp_payload_size(ngtcp2_conn *conn) {
13678
0
  if (conn->local.settings.no_tx_udp_payload_size_shaping) {
13679
0
    return ngtcp2_conn_get_max_tx_udp_payload_size(conn);
13680
0
  }
13681
13682
0
  return conn->dcid.current.max_udp_payload_size;
13683
0
}
13684
13685
static int conn_initiate_migration_precheck(ngtcp2_conn *conn,
13686
0
                                            const ngtcp2_addr *local_addr) {
13687
0
  if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) ||
13688
0
      conn->remote.transport_params->disable_active_migration ||
13689
0
      conn->dcid.current.cid.datalen == 0 ||
13690
0
      (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_PREFERRED_ADDR))) {
13691
0
    return NGTCP2_ERR_INVALID_STATE;
13692
0
  }
13693
13694
0
  if (ngtcp2_dcidtr_unused_empty(&conn->dcid.dtr)) {
13695
0
    return NGTCP2_ERR_CONN_ID_BLOCKED;
13696
0
  }
13697
13698
0
  if (ngtcp2_addr_eq(&conn->dcid.current.ps.path.local, local_addr)) {
13699
0
    return NGTCP2_ERR_INVALID_ARGUMENT;
13700
0
  }
13701
13702
0
  return 0;
13703
0
}
13704
13705
int ngtcp2_conn_initiate_immediate_migration(ngtcp2_conn *conn,
13706
                                             const ngtcp2_path *path,
13707
0
                                             ngtcp2_tstamp ts) {
13708
0
  int rv;
13709
0
  ngtcp2_dcid dcid;
13710
0
  ngtcp2_pv *pv;
13711
0
  const ngtcp2_path_history_entry *validated_path;
13712
13713
0
  assert(!conn->server);
13714
13715
0
  conn_update_timestamp(conn, ts);
13716
13717
0
  rv = conn_initiate_migration_precheck(conn, &path->local);
13718
0
  if (rv != 0) {
13719
0
    return rv;
13720
0
  }
13721
13722
0
  ngtcp2_conn_stop_pmtud(conn);
13723
13724
0
  if (conn->pv) {
13725
0
    rv = conn_abort_pv(conn, ts);
13726
0
    if (rv != 0) {
13727
0
      return rv;
13728
0
    }
13729
0
  }
13730
13731
0
  rv = conn_retire_active_dcid(conn, &conn->dcid.current, ts);
13732
0
  if (rv != 0) {
13733
0
    return rv;
13734
0
  }
13735
13736
0
  ngtcp2_dcidtr_pop_unused(&conn->dcid.dtr, &dcid);
13737
0
  ngtcp2_dcid_set_path(&dcid, path);
13738
13739
0
  if (conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) {
13740
0
    ngtcp2_conn_add_path_history(conn, &conn->dcid.current, ts);
13741
0
  }
13742
13743
0
  ngtcp2_dcid_copy(&conn->dcid.current, &dcid);
13744
13745
0
  conn_reset_congestion_state(conn, ts);
13746
0
  conn_reset_ecn_validation_state(conn);
13747
13748
0
  validated_path = ngtcp2_conn_find_path_history(conn, path, ts);
13749
0
  if (validated_path) {
13750
0
    ngtcp2_dcid_apply_validated_path(&conn->dcid.current, validated_path);
13751
13752
0
    if (!conn->local.settings.no_pmtud) {
13753
0
      rv = conn_start_pmtud(conn);
13754
0
      if (rv != 0) {
13755
0
        return rv;
13756
0
      }
13757
0
    }
13758
0
  } else {
13759
    /* TODO It might be better to add a new flag which indicates that
13760
       a connection should be closed if this path validation failed.
13761
       The current design allows an application to continue, by
13762
       migrating into yet another path. */
13763
0
    rv = ngtcp2_pv_new(&pv, &dcid, conn_compute_pv_timeout(conn),
13764
0
                       NGTCP2_PV_FLAG_NONE, &conn->log, conn->mem);
13765
0
    if (rv != 0) {
13766
0
      return rv;
13767
0
    }
13768
13769
0
    conn->pv = pv;
13770
0
  }
13771
13772
0
  rv = conn_call_activate_dcid(conn, &conn->dcid.current);
13773
0
  if (rv != 0) {
13774
0
    return rv;
13775
0
  }
13776
13777
0
  return conn_call_begin_path_validation(conn, conn->pv);
13778
0
}
13779
13780
int ngtcp2_conn_initiate_migration(ngtcp2_conn *conn, const ngtcp2_path *path,
13781
0
                                   ngtcp2_tstamp ts) {
13782
0
  int rv;
13783
0
  ngtcp2_dcid dcid;
13784
0
  ngtcp2_pv *pv;
13785
13786
0
  assert(!conn->server);
13787
13788
0
  if (ngtcp2_conn_find_path_history(conn, path, ts)) {
13789
0
    return ngtcp2_conn_initiate_immediate_migration(conn, path, ts);
13790
0
  }
13791
13792
0
  conn_update_timestamp(conn, ts);
13793
13794
0
  rv = conn_initiate_migration_precheck(conn, &path->local);
13795
0
  if (rv != 0) {
13796
0
    return rv;
13797
0
  }
13798
13799
0
  if (conn->pv) {
13800
0
    rv = conn_abort_pv(conn, ts);
13801
0
    if (rv != 0) {
13802
0
      return rv;
13803
0
    }
13804
0
  }
13805
13806
0
  ngtcp2_dcidtr_pop_unused(&conn->dcid.dtr, &dcid);
13807
0
  ngtcp2_dcid_set_path(&dcid, path);
13808
13809
0
  rv = ngtcp2_pv_new(&pv, &dcid, conn_compute_pv_timeout(conn),
13810
0
                     NGTCP2_PV_FLAG_NONE, &conn->log, conn->mem);
13811
0
  if (rv != 0) {
13812
0
    return rv;
13813
0
  }
13814
13815
0
  conn->pv = pv;
13816
13817
0
  rv = conn_call_activate_dcid(conn, &pv->dcid);
13818
0
  if (rv != 0) {
13819
0
    return rv;
13820
0
  }
13821
13822
0
  return conn_call_begin_path_validation(conn, conn->pv);
13823
0
}
13824
13825
0
uint64_t ngtcp2_conn_get_max_data_left(ngtcp2_conn *conn) {
13826
0
  return conn->tx.max_offset - conn->tx.offset;
13827
0
}
13828
13829
uint64_t ngtcp2_conn_get_max_stream_data_left(ngtcp2_conn *conn,
13830
0
                                              int64_t stream_id) {
13831
0
  ngtcp2_strm *strm = ngtcp2_conn_find_stream(conn, stream_id);
13832
13833
0
  if (strm == NULL) {
13834
0
    return 0;
13835
0
  }
13836
13837
0
  return strm->tx.max_offset - strm->tx.offset;
13838
0
}
13839
13840
0
uint64_t ngtcp2_conn_get_streams_bidi_left(ngtcp2_conn *conn) {
13841
0
  uint64_t n = ngtcp2_ord_stream_id(conn->local.bidi.next_stream_id);
13842
13843
0
  return n > conn->local.bidi.max_streams
13844
0
           ? 0
13845
0
           : conn->local.bidi.max_streams - n + 1;
13846
0
}
13847
13848
0
uint64_t ngtcp2_conn_get_streams_uni_left(ngtcp2_conn *conn) {
13849
0
  uint64_t n = ngtcp2_ord_stream_id(conn->local.uni.next_stream_id);
13850
13851
0
  return n > conn->local.uni.max_streams ? 0
13852
0
                                         : conn->local.uni.max_streams - n + 1;
13853
0
}
13854
13855
0
uint64_t ngtcp2_conn_get_cwnd_left(ngtcp2_conn *conn) {
13856
0
  uint64_t bytes_in_flight = conn->cstat.bytes_in_flight;
13857
0
  uint64_t cwnd = conn->cstat.cwnd;
13858
13859
0
  if (cwnd > bytes_in_flight) {
13860
0
    return cwnd - bytes_in_flight;
13861
0
  }
13862
13863
0
  return 0;
13864
0
}
13865
13866
0
ngtcp2_tstamp ngtcp2_conn_get_idle_expiry(ngtcp2_conn *conn) {
13867
0
  ngtcp2_duration trpto;
13868
0
  ngtcp2_duration idle_timeout;
13869
13870
  /* TODO Remote max_idle_timeout becomes effective after handshake
13871
     completion. */
13872
13873
0
  if (!conn_is_tls_handshake_completed(conn) ||
13874
0
      conn->remote.transport_params->max_idle_timeout == 0 ||
13875
0
      (conn->local.transport_params.max_idle_timeout &&
13876
0
       conn->local.transport_params.max_idle_timeout <
13877
0
         conn->remote.transport_params->max_idle_timeout)) {
13878
0
    idle_timeout = conn->local.transport_params.max_idle_timeout;
13879
0
  } else {
13880
0
    idle_timeout = conn->remote.transport_params->max_idle_timeout;
13881
0
  }
13882
13883
0
  if (idle_timeout == 0) {
13884
0
    return UINT64_MAX;
13885
0
  }
13886
13887
0
  trpto = 3 * conn_compute_pto(conn, conn_is_tls_handshake_completed(conn)
13888
0
                                       ? &conn->pktns
13889
0
                                       : conn->hs_pktns);
13890
13891
0
  idle_timeout = ngtcp2_max_uint64(idle_timeout, trpto);
13892
13893
0
  if (conn->idle_ts >= UINT64_MAX - idle_timeout) {
13894
0
    return UINT64_MAX;
13895
0
  }
13896
13897
0
  return conn->idle_ts + idle_timeout;
13898
0
}
13899
13900
0
ngtcp2_duration ngtcp2_conn_get_pto(ngtcp2_conn *conn) {
13901
0
  return conn_compute_pto(conn, conn_is_tls_handshake_completed(conn)
13902
0
                                  ? &conn->pktns
13903
0
                                  : conn->hs_pktns);
13904
0
}
13905
13906
void ngtcp2_conn_set_initial_crypto_ctx(ngtcp2_conn *conn,
13907
0
                                        const ngtcp2_crypto_ctx *ctx) {
13908
0
  assert(conn->in_pktns);
13909
0
  conn->in_pktns->crypto.ctx = *ctx;
13910
0
}
13911
13912
0
const ngtcp2_crypto_ctx *ngtcp2_conn_get_initial_crypto_ctx(ngtcp2_conn *conn) {
13913
0
  assert(conn->in_pktns);
13914
0
  return &conn->in_pktns->crypto.ctx;
13915
0
}
13916
13917
void ngtcp2_conn_set_retry_aead(ngtcp2_conn *conn,
13918
                                const ngtcp2_crypto_aead *aead,
13919
0
                                const ngtcp2_crypto_aead_ctx *aead_ctx) {
13920
0
  assert(!conn->crypto.retry_aead_ctx.native_handle);
13921
13922
0
  conn->crypto.retry_aead = *aead;
13923
0
  conn->crypto.retry_aead_ctx = *aead_ctx;
13924
0
}
13925
13926
void ngtcp2_conn_set_crypto_ctx(ngtcp2_conn *conn,
13927
0
                                const ngtcp2_crypto_ctx *ctx) {
13928
0
  assert(conn->hs_pktns);
13929
0
  conn->hs_pktns->crypto.ctx = *ctx;
13930
0
  conn->pktns.crypto.ctx = *ctx;
13931
0
}
13932
13933
0
const ngtcp2_crypto_ctx *ngtcp2_conn_get_crypto_ctx(ngtcp2_conn *conn) {
13934
0
  return &conn->pktns.crypto.ctx;
13935
0
}
13936
13937
void ngtcp2_conn_set_0rtt_crypto_ctx(ngtcp2_conn *conn,
13938
0
                                     const ngtcp2_crypto_ctx *ctx) {
13939
0
  conn->early.ctx = *ctx;
13940
0
}
13941
13942
0
const ngtcp2_crypto_ctx *ngtcp2_conn_get_0rtt_crypto_ctx(ngtcp2_conn *conn) {
13943
0
  return &conn->early.ctx;
13944
0
}
13945
13946
0
void *ngtcp2_conn_get_tls_native_handle(ngtcp2_conn *conn) {
13947
0
  return conn->crypto.tls_native_handle;
13948
0
}
13949
13950
void ngtcp2_conn_set_tls_native_handle(ngtcp2_conn *conn,
13951
0
                                       void *tls_native_handle) {
13952
0
  conn->crypto.tls_native_handle = tls_native_handle;
13953
0
}
13954
13955
0
const ngtcp2_ccerr *ngtcp2_conn_get_ccerr(ngtcp2_conn *conn) {
13956
0
  return &conn->rx.ccerr;
13957
0
}
13958
13959
0
void ngtcp2_conn_set_tls_error(ngtcp2_conn *conn, int liberr) {
13960
0
  conn->crypto.tls_error = liberr;
13961
0
}
13962
13963
0
int ngtcp2_conn_get_tls_error(ngtcp2_conn *conn) {
13964
0
  return conn->crypto.tls_error;
13965
0
}
13966
13967
0
void ngtcp2_conn_set_tls_alert(ngtcp2_conn *conn, uint8_t alert) {
13968
0
  conn->crypto.tls_alert = alert;
13969
0
}
13970
13971
0
uint8_t ngtcp2_conn_get_tls_alert(ngtcp2_conn *conn) {
13972
0
  return conn->crypto.tls_alert;
13973
0
}
13974
13975
0
int ngtcp2_conn_is_local_stream(ngtcp2_conn *conn, int64_t stream_id) {
13976
0
  return conn_local_stream(conn, stream_id);
13977
0
}
13978
13979
0
int ngtcp2_conn_is_server(ngtcp2_conn *conn) { return conn->server; }
13980
13981
0
int ngtcp2_conn_after_retry(ngtcp2_conn *conn) {
13982
0
  return (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) != 0;
13983
0
}
13984
13985
int ngtcp2_conn_set_stream_user_data(ngtcp2_conn *conn, int64_t stream_id,
13986
0
                                     void *stream_user_data) {
13987
0
  ngtcp2_strm *strm = ngtcp2_conn_find_stream(conn, stream_id);
13988
13989
0
  if (strm == NULL) {
13990
0
    return NGTCP2_ERR_STREAM_NOT_FOUND;
13991
0
  }
13992
13993
0
  strm->stream_user_data = stream_user_data;
13994
13995
0
  return 0;
13996
0
}
13997
13998
0
void *ngtcp2_conn_get_stream_user_data(ngtcp2_conn *conn, int64_t stream_id) {
13999
0
  ngtcp2_strm *strm = ngtcp2_conn_find_stream(conn, stream_id);
14000
14001
0
  if (strm == NULL) {
14002
0
    return NULL;
14003
0
  }
14004
14005
0
  return strm->stream_user_data;
14006
0
}
14007
14008
0
void ngtcp2_conn_update_pkt_tx_time(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
14009
0
  ngtcp2_duration wait, d;
14010
14011
0
  conn_update_timestamp(conn, ts);
14012
14013
0
  if (conn->tx.pacing.pktlen == 0) {
14014
0
    return;
14015
0
  }
14016
14017
0
  wait = (ngtcp2_duration)((conn->tx.pacing.pktlen *
14018
0
                            conn->cstat.pacing_interval_m) >>
14019
0
                           10);
14020
14021
0
  d = ngtcp2_min_uint64(wait / 2, conn->tx.pacing.compensation);
14022
0
  wait -= d;
14023
0
  conn->tx.pacing.compensation -= d;
14024
14025
0
  conn->tx.pacing.next_ts = ts + wait;
14026
0
  conn->tx.pacing.pktlen = 0;
14027
0
}
14028
14029
0
size_t ngtcp2_conn_get_send_quantum(ngtcp2_conn *conn) {
14030
0
  return conn->cstat.send_quantum;
14031
0
}
14032
14033
0
size_t ngtcp2_conn_get_stream_loss_count(ngtcp2_conn *conn, int64_t stream_id) {
14034
0
  ngtcp2_strm *strm = ngtcp2_conn_find_stream(conn, stream_id);
14035
14036
0
  if (strm == NULL) {
14037
0
    return 0;
14038
0
  }
14039
14040
0
  return strm->tx.loss_count;
14041
0
}
14042
14043
void ngtcp2_conn_add_path_history(ngtcp2_conn *conn, const ngtcp2_dcid *dcid,
14044
0
                                  ngtcp2_tstamp ts) {
14045
0
  ngtcp2_path_history_entry *ent;
14046
14047
0
  ent = ngtcp2_ringbuf_push_front(&conn->path_history.rb);
14048
0
  ngtcp2_path_storage_init2(&ent->ps, &dcid->ps.path);
14049
0
  ent->max_udp_payload_size = dcid->max_udp_payload_size;
14050
0
  ent->ts = ts;
14051
0
}
14052
14053
ngtcp2_ssize ngtcp2_conn_write_aggregate_pkt_versioned(
14054
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
14055
  ngtcp2_pkt_info *pi, uint8_t *buf, size_t buflen, size_t *pgsolen,
14056
0
  ngtcp2_write_pkt write_pkt, ngtcp2_tstamp ts) {
14057
0
  ngtcp2_ssize nwrite;
14058
14059
0
  buflen = ngtcp2_min_size(buflen, ngtcp2_conn_get_send_quantum(conn));
14060
14061
0
  nwrite = ngtcp2_conn_write_aggregate_pkt2_versioned(
14062
0
    conn, path, pkt_info_version, pi, buf, buflen, pgsolen, write_pkt, 0, ts);
14063
0
  if (nwrite < 0) {
14064
0
    return nwrite;
14065
0
  }
14066
14067
0
  ngtcp2_conn_update_pkt_tx_time(conn, ts);
14068
14069
0
  return nwrite;
14070
0
}
14071
14072
ngtcp2_ssize ngtcp2_conn_write_aggregate_pkt2_versioned(
14073
  ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
14074
  ngtcp2_pkt_info *pi, uint8_t *buf, size_t buflen, size_t *pgsolen,
14075
0
  ngtcp2_write_pkt write_pkt, size_t num_pkts, ngtcp2_tstamp ts) {
14076
0
  size_t max_udp_payloadlen = ngtcp2_conn_get_max_tx_udp_payload_size(conn);
14077
0
  size_t path_max_udp_payloadlen =
14078
0
    ngtcp2_conn_get_path_max_tx_udp_payload_size(conn);
14079
0
  ngtcp2_ssize nwrite;
14080
0
  uint8_t *wbuf = buf;
14081
0
  size_t wbuflen;
14082
0
  ngtcp2_ecn_state ecn_state;
14083
0
  int first_pkt;
14084
0
  ngtcp2_pkt_info pi_discard;
14085
0
  ngtcp2_path_storage path_discard;
14086
0
  (void)pkt_info_version;
14087
14088
0
  assert(buflen >= path_max_udp_payloadlen);
14089
14090
0
  if (num_pkts == 0) {
14091
0
    num_pkts = SIZE_MAX;
14092
0
  }
14093
14094
0
  for (;;) {
14095
0
    ecn_state = conn->tx.ecn.state;
14096
14097
0
    wbuflen = buflen >= max_udp_payloadlen ? max_udp_payloadlen
14098
0
                                           : path_max_udp_payloadlen;
14099
14100
0
    nwrite = write_pkt(conn, path, pi, wbuf, wbuflen, ts, conn->user_data);
14101
0
    if (nwrite < 0) {
14102
0
      break;
14103
0
    }
14104
14105
0
    if (nwrite == 0) {
14106
0
      nwrite = wbuf - buf;
14107
0
      break;
14108
0
    }
14109
14110
0
    first_pkt = buf == wbuf;
14111
0
    wbuf += nwrite;
14112
0
    buflen -= (size_t)nwrite;
14113
14114
0
    --num_pkts;
14115
14116
0
    if (first_pkt) {
14117
0
      assert(!(conn->flags & NGTCP2_CONN_FLAG_AGGREGATE_PKTS));
14118
14119
0
      *pgsolen = (size_t)nwrite;
14120
14121
0
      if ((size_t)nwrite != path_max_udp_payloadlen ||
14122
0
          buflen < path_max_udp_payloadlen || ecn_state != conn->tx.ecn.state ||
14123
0
          num_pkts == 0) {
14124
0
        nwrite = wbuf - buf;
14125
0
        break;
14126
0
      }
14127
14128
      /* All aggregated packets should share the same path and pi.
14129
         Pass the placeholder values to the callback because they
14130
         might be overwritten by later calls, especially pi is set to
14131
         empty when no packet is produced. */
14132
0
      if (path) {
14133
0
        ngtcp2_path_storage_zero(&path_discard);
14134
0
        path = &path_discard.path;
14135
0
      }
14136
14137
0
      if (pi) {
14138
0
        pi = &pi_discard;
14139
0
      }
14140
14141
0
      conn->flags |= NGTCP2_CONN_FLAG_AGGREGATE_PKTS;
14142
14143
0
      continue;
14144
0
    }
14145
14146
0
    if (buflen < path_max_udp_payloadlen || (size_t)nwrite < *pgsolen ||
14147
0
        ecn_state != conn->tx.ecn.state || num_pkts == 0) {
14148
0
      nwrite = wbuf - buf;
14149
0
      break;
14150
0
    }
14151
0
  }
14152
14153
0
  conn->flags &= ~NGTCP2_CONN_FLAG_AGGREGATE_PKTS;
14154
14155
0
  return nwrite;
14156
0
}
14157
14158
0
ngtcp2_tstamp ngtcp2_conn_get_timestamp(const ngtcp2_conn *conn) {
14159
0
  return conn->log.last_ts;
14160
0
}
14161
14162
const ngtcp2_path_history_entry *
14163
ngtcp2_conn_find_path_history(ngtcp2_conn *conn, const ngtcp2_path *path,
14164
0
                              ngtcp2_tstamp ts) {
14165
0
  ngtcp2_ringbuf *rb = &conn->path_history.rb;
14166
0
  size_t i, len = ngtcp2_ringbuf_len(rb);
14167
0
  ngtcp2_path_history_entry *ent;
14168
14169
0
  for (i = 0; i < len; ++i) {
14170
0
    ent = ngtcp2_ringbuf_get(rb, i);
14171
0
    if (ngtcp2_tstamp_elapsed(ent->ts, 10 * NGTCP2_MINUTES, ts)) {
14172
0
      return NULL;
14173
0
    }
14174
14175
0
    if (ngtcp2_path_eq(path, &ent->ps.path)) {
14176
0
      return ent;
14177
0
    }
14178
0
  }
14179
14180
0
  return NULL;
14181
0
}
14182
14183
void ngtcp2_path_challenge_entry_init(ngtcp2_path_challenge_entry *pcent,
14184
                                      const ngtcp2_path *path,
14185
0
                                      const ngtcp2_path_challenge_data *data) {
14186
0
  ngtcp2_path_storage_init2(&pcent->ps, path);
14187
0
  pcent->data = *data;
14188
0
}
14189
14190
/* The functions prefixed with ngtcp2_pkt_ are usually put inside
14191
   ngtcp2_pkt.c.  This function uses encryption construct and uses
14192
   test data defined only in ngtcp2_conn_test.c, so it is written
14193
   here. */
14194
ngtcp2_ssize ngtcp2_pkt_write_connection_close(
14195
  uint8_t *dest, size_t destlen, uint32_t version, const ngtcp2_cid *dcid,
14196
  const ngtcp2_cid *scid, uint64_t error_code, const uint8_t *reason,
14197
  size_t reasonlen, ngtcp2_encrypt encrypt, const ngtcp2_crypto_aead *aead,
14198
  const ngtcp2_crypto_aead_ctx *aead_ctx, const uint8_t *iv,
14199
  ngtcp2_hp_mask hp_mask, const ngtcp2_crypto_cipher *hp,
14200
0
  const ngtcp2_crypto_cipher_ctx *hp_ctx) {
14201
0
  ngtcp2_pkt_hd hd;
14202
0
  ngtcp2_crypto_km ckm;
14203
0
  ngtcp2_crypto_cc cc;
14204
0
  ngtcp2_ppe ppe;
14205
0
  ngtcp2_frame fr;
14206
0
  int rv;
14207
14208
0
  ngtcp2_pkt_hd_init(&hd, NGTCP2_PKT_FLAG_LONG_FORM, NGTCP2_PKT_INITIAL, dcid,
14209
0
                     scid, /* pkt_num = */ 0, /* pkt_numlen = */ 1, version);
14210
14211
0
  ngtcp2_vec_init(&ckm.secret, NULL, 0);
14212
0
  ngtcp2_vec_init(&ckm.iv, iv, 12);
14213
0
  ckm.aead_ctx = *aead_ctx;
14214
0
  ckm.pkt_num = 0;
14215
0
  ckm.flags = NGTCP2_CRYPTO_KM_FLAG_NONE;
14216
14217
0
  cc.aead = *aead;
14218
0
  cc.hp = *hp;
14219
0
  cc.ckm = &ckm;
14220
0
  cc.hp_ctx = *hp_ctx;
14221
0
  cc.encrypt = encrypt;
14222
0
  cc.hp_mask = hp_mask;
14223
14224
0
  ngtcp2_ppe_init(&ppe, dest, destlen, 0, &cc);
14225
14226
0
  rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
14227
0
  if (rv != 0) {
14228
0
    assert(NGTCP2_ERR_NOBUF == rv);
14229
0
    return rv;
14230
0
  }
14231
14232
0
  if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
14233
0
    return NGTCP2_ERR_NOBUF;
14234
0
  }
14235
14236
0
  fr.connection_close = (ngtcp2_connection_close){
14237
0
    .type = NGTCP2_FRAME_CONNECTION_CLOSE,
14238
0
    .error_code = error_code,
14239
0
    .reasonlen = reasonlen,
14240
0
    .reason = (uint8_t *)reason,
14241
0
  };
14242
14243
0
  rv = ngtcp2_ppe_encode_frame(&ppe, &fr);
14244
0
  if (rv != 0) {
14245
0
    assert(NGTCP2_ERR_NOBUF == rv);
14246
0
    return rv;
14247
0
  }
14248
14249
0
  return ngtcp2_ppe_final(&ppe, NULL);
14250
0
}
14251
14252
0
int ngtcp2_is_bidi_stream(int64_t stream_id) { return bidi_stream(stream_id); }
14253
14254
uint32_t ngtcp2_select_version(const uint32_t *preferred_versions,
14255
                               size_t preferred_versionslen,
14256
                               const uint32_t *offered_versions,
14257
0
                               size_t offered_versionslen) {
14258
0
  size_t i, j;
14259
14260
0
  if (!preferred_versionslen || !offered_versionslen) {
14261
0
    return 0;
14262
0
  }
14263
14264
0
  for (i = 0; i < preferred_versionslen; ++i) {
14265
0
    assert(ngtcp2_is_supported_version(preferred_versions[i]));
14266
14267
0
    for (j = 0; j < offered_versionslen; ++j) {
14268
0
      if (preferred_versions[i] == offered_versions[j]) {
14269
0
        return preferred_versions[i];
14270
0
      }
14271
0
    }
14272
0
  }
14273
14274
0
  return 0;
14275
0
}