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 
39 /* NGTCP2_FLOW_WINDOW_RTT_FACTOR is the factor of RTT when flow
40    control window auto-tuning is triggered. */
41 #define NGTCP2_FLOW_WINDOW_RTT_FACTOR 2
42 /* NGTCP2_FLOW_WINDOW_SCALING_FACTOR is the growth factor of flow
43    control window. */
44 #define NGTCP2_FLOW_WINDOW_SCALING_FACTOR 2
45 /* NGTCP2_MIN_COALESCED_PAYLOADLEN is the minimum length of QUIC
46    packet payload that should be coalesced to a long packet. */
47 #define NGTCP2_MIN_COALESCED_PAYLOADLEN 128
48 
49 /*
50  * conn_local_stream returns nonzero if |stream_id| indicates that it
51  * is the stream initiated by local endpoint.
52  */
conn_local_stream(ngtcp2_conn * conn,int64_t stream_id)53 static int conn_local_stream(ngtcp2_conn *conn, int64_t stream_id) {
54   return (uint8_t)(stream_id & 1) == conn->server;
55 }
56 
57 /*
58  * bidi_stream returns nonzero if |stream_id| is a bidirectional
59  * stream ID.
60  */
bidi_stream(int64_t stream_id)61 static int bidi_stream(int64_t stream_id) { return (stream_id & 0x2) == 0; }
62 
conn_call_recv_client_initial(ngtcp2_conn * conn,const ngtcp2_cid * dcid)63 static int conn_call_recv_client_initial(ngtcp2_conn *conn,
64                                          const ngtcp2_cid *dcid) {
65   int rv;
66 
67   assert(conn->callbacks.recv_client_initial);
68 
69   rv = conn->callbacks.recv_client_initial(conn, dcid, conn->user_data);
70   if (rv != 0) {
71     return NGTCP2_ERR_CALLBACK_FAILURE;
72   }
73 
74   return 0;
75 }
76 
conn_call_handshake_completed(ngtcp2_conn * conn)77 static int conn_call_handshake_completed(ngtcp2_conn *conn) {
78   int rv;
79 
80   if (!conn->callbacks.handshake_completed) {
81     return 0;
82   }
83 
84   rv = conn->callbacks.handshake_completed(conn, conn->user_data);
85   if (rv != 0) {
86     return NGTCP2_ERR_CALLBACK_FAILURE;
87   }
88 
89   return 0;
90 }
91 
conn_call_recv_stream_data(ngtcp2_conn * conn,ngtcp2_strm * strm,uint32_t flags,uint64_t offset,const uint8_t * data,size_t datalen)92 static int conn_call_recv_stream_data(ngtcp2_conn *conn, ngtcp2_strm *strm,
93                                       uint32_t flags, uint64_t offset,
94                                       const uint8_t *data, size_t datalen) {
95   int rv;
96 
97   if (!conn->callbacks.recv_stream_data) {
98     return 0;
99   }
100 
101   rv = conn->callbacks.recv_stream_data(conn, flags, strm->stream_id, offset,
102                                         data, datalen, conn->user_data,
103                                         strm->stream_user_data);
104   if (rv != 0) {
105     return NGTCP2_ERR_CALLBACK_FAILURE;
106   }
107 
108   return 0;
109 }
110 
conn_call_recv_crypto_data(ngtcp2_conn * conn,ngtcp2_crypto_level crypto_level,uint64_t offset,const uint8_t * data,size_t datalen)111 static int conn_call_recv_crypto_data(ngtcp2_conn *conn,
112                                       ngtcp2_crypto_level crypto_level,
113                                       uint64_t offset, const uint8_t *data,
114                                       size_t datalen) {
115   int rv;
116 
117   assert(conn->callbacks.recv_crypto_data);
118 
119   rv = conn->callbacks.recv_crypto_data(conn, crypto_level, offset, data,
120                                         datalen, conn->user_data);
121   switch (rv) {
122   case 0:
123   case NGTCP2_ERR_CRYPTO:
124   case NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM:
125   case NGTCP2_ERR_MALFORMED_TRANSPORT_PARAM:
126   case NGTCP2_ERR_TRANSPORT_PARAM:
127   case NGTCP2_ERR_PROTO:
128   case NGTCP2_ERR_CALLBACK_FAILURE:
129     return rv;
130   default:
131     return NGTCP2_ERR_CALLBACK_FAILURE;
132   }
133 }
134 
conn_call_stream_open(ngtcp2_conn * conn,ngtcp2_strm * strm)135 static int conn_call_stream_open(ngtcp2_conn *conn, ngtcp2_strm *strm) {
136   int rv;
137 
138   if (!conn->callbacks.stream_open) {
139     return 0;
140   }
141 
142   rv = conn->callbacks.stream_open(conn, strm->stream_id, conn->user_data);
143   if (rv != 0) {
144     return NGTCP2_ERR_CALLBACK_FAILURE;
145   }
146 
147   return 0;
148 }
149 
conn_call_stream_close(ngtcp2_conn * conn,ngtcp2_strm * strm)150 static int conn_call_stream_close(ngtcp2_conn *conn, ngtcp2_strm *strm) {
151   int rv;
152   uint32_t flags = NGTCP2_STREAM_CLOSE_FLAG_NONE;
153 
154   if (!conn->callbacks.stream_close) {
155     return 0;
156   }
157 
158   if (strm->flags & NGTCP2_STRM_FLAG_APP_ERROR_CODE_SET) {
159     flags |= NGTCP2_STREAM_CLOSE_FLAG_APP_ERROR_CODE_SET;
160   }
161 
162   rv = conn->callbacks.stream_close(conn, flags, strm->stream_id,
163                                     strm->app_error_code, conn->user_data,
164                                     strm->stream_user_data);
165   if (rv != 0) {
166     return NGTCP2_ERR_CALLBACK_FAILURE;
167   }
168 
169   return 0;
170 }
171 
conn_call_stream_reset(ngtcp2_conn * conn,int64_t stream_id,uint64_t final_size,uint64_t app_error_code,void * stream_user_data)172 static int conn_call_stream_reset(ngtcp2_conn *conn, int64_t stream_id,
173                                   uint64_t final_size, uint64_t app_error_code,
174                                   void *stream_user_data) {
175   int rv;
176 
177   if (!conn->callbacks.stream_reset) {
178     return 0;
179   }
180 
181   rv = conn->callbacks.stream_reset(conn, stream_id, final_size, app_error_code,
182                                     conn->user_data, stream_user_data);
183   if (rv != 0) {
184     return NGTCP2_ERR_CALLBACK_FAILURE;
185   }
186 
187   return 0;
188 }
189 
conn_call_extend_max_local_streams_bidi(ngtcp2_conn * conn,uint64_t max_streams)190 static int conn_call_extend_max_local_streams_bidi(ngtcp2_conn *conn,
191                                                    uint64_t max_streams) {
192   int rv;
193 
194   if (!conn->callbacks.extend_max_local_streams_bidi) {
195     return 0;
196   }
197 
198   rv = conn->callbacks.extend_max_local_streams_bidi(conn, max_streams,
199                                                      conn->user_data);
200   if (rv != 0) {
201     return NGTCP2_ERR_CALLBACK_FAILURE;
202   }
203 
204   return 0;
205 }
206 
conn_call_extend_max_local_streams_uni(ngtcp2_conn * conn,uint64_t max_streams)207 static int conn_call_extend_max_local_streams_uni(ngtcp2_conn *conn,
208                                                   uint64_t max_streams) {
209   int rv;
210 
211   if (!conn->callbacks.extend_max_local_streams_uni) {
212     return 0;
213   }
214 
215   rv = conn->callbacks.extend_max_local_streams_uni(conn, max_streams,
216                                                     conn->user_data);
217   if (rv != 0) {
218     return NGTCP2_ERR_CALLBACK_FAILURE;
219   }
220 
221   return 0;
222 }
223 
conn_call_get_new_connection_id(ngtcp2_conn * conn,ngtcp2_cid * cid,uint8_t * token,size_t cidlen)224 static int conn_call_get_new_connection_id(ngtcp2_conn *conn, ngtcp2_cid *cid,
225                                            uint8_t *token, size_t cidlen) {
226   int rv;
227 
228   assert(conn->callbacks.get_new_connection_id);
229 
230   rv = conn->callbacks.get_new_connection_id(conn, cid, token, cidlen,
231                                              conn->user_data);
232   if (rv != 0) {
233     return NGTCP2_ERR_CALLBACK_FAILURE;
234   }
235 
236   return 0;
237 }
238 
conn_call_remove_connection_id(ngtcp2_conn * conn,const ngtcp2_cid * cid)239 static int conn_call_remove_connection_id(ngtcp2_conn *conn,
240                                           const ngtcp2_cid *cid) {
241   int rv;
242 
243   if (!conn->callbacks.remove_connection_id) {
244     return 0;
245   }
246 
247   rv = conn->callbacks.remove_connection_id(conn, cid, conn->user_data);
248   if (rv != 0) {
249     return NGTCP2_ERR_CALLBACK_FAILURE;
250   }
251 
252   return 0;
253 }
254 
conn_call_path_validation(ngtcp2_conn * conn,const ngtcp2_pv * pv,ngtcp2_path_validation_result res)255 static int conn_call_path_validation(ngtcp2_conn *conn, const ngtcp2_pv *pv,
256                                      ngtcp2_path_validation_result res) {
257   int rv;
258   uint32_t flags = NGTCP2_PATH_VALIDATION_FLAG_NONE;
259 
260   if (!conn->callbacks.path_validation) {
261     return 0;
262   }
263 
264   if (pv->flags & NGTCP2_PV_FLAG_PREFERRED_ADDR) {
265     flags |= NGTCP2_PATH_VALIDATION_FLAG_PREFERRED_ADDR;
266   }
267 
268   rv = conn->callbacks.path_validation(conn, flags, &pv->dcid.ps.path, res,
269                                        conn->user_data);
270   if (rv != 0) {
271     return NGTCP2_ERR_CALLBACK_FAILURE;
272   }
273 
274   return 0;
275 }
276 
conn_call_select_preferred_addr(ngtcp2_conn * conn,ngtcp2_path * dest)277 static int conn_call_select_preferred_addr(ngtcp2_conn *conn,
278                                            ngtcp2_path *dest) {
279   int rv;
280 
281   if (!conn->callbacks.select_preferred_addr) {
282     return 0;
283   }
284 
285   assert(conn->remote.transport_params.preferred_address_present);
286 
287   rv = conn->callbacks.select_preferred_addr(
288       conn, dest, &conn->remote.transport_params.preferred_address,
289       conn->user_data);
290   if (rv != 0) {
291     return NGTCP2_ERR_CALLBACK_FAILURE;
292   }
293 
294   return 0;
295 }
296 
conn_call_extend_max_remote_streams_bidi(ngtcp2_conn * conn,uint64_t max_streams)297 static int conn_call_extend_max_remote_streams_bidi(ngtcp2_conn *conn,
298                                                     uint64_t max_streams) {
299   int rv;
300 
301   if (!conn->callbacks.extend_max_remote_streams_bidi) {
302     return 0;
303   }
304 
305   rv = conn->callbacks.extend_max_remote_streams_bidi(conn, max_streams,
306                                                       conn->user_data);
307   if (rv != 0) {
308     return NGTCP2_ERR_CALLBACK_FAILURE;
309   }
310 
311   return 0;
312 }
313 
conn_call_extend_max_remote_streams_uni(ngtcp2_conn * conn,uint64_t max_streams)314 static int conn_call_extend_max_remote_streams_uni(ngtcp2_conn *conn,
315                                                    uint64_t max_streams) {
316   int rv;
317 
318   if (!conn->callbacks.extend_max_remote_streams_uni) {
319     return 0;
320   }
321 
322   rv = conn->callbacks.extend_max_remote_streams_uni(conn, max_streams,
323                                                      conn->user_data);
324   if (rv != 0) {
325     return NGTCP2_ERR_CALLBACK_FAILURE;
326   }
327 
328   return 0;
329 }
330 
conn_call_extend_max_stream_data(ngtcp2_conn * conn,ngtcp2_strm * strm,int64_t stream_id,uint64_t datalen)331 static int conn_call_extend_max_stream_data(ngtcp2_conn *conn,
332                                             ngtcp2_strm *strm,
333                                             int64_t stream_id,
334                                             uint64_t datalen) {
335   int rv;
336 
337   if (!conn->callbacks.extend_max_stream_data) {
338     return 0;
339   }
340 
341   rv = conn->callbacks.extend_max_stream_data(
342       conn, stream_id, datalen, conn->user_data, strm->stream_user_data);
343   if (rv != 0) {
344     return NGTCP2_ERR_CALLBACK_FAILURE;
345   }
346 
347   return 0;
348 }
349 
conn_call_dcid_status(ngtcp2_conn * conn,ngtcp2_connection_id_status_type type,const ngtcp2_dcid * dcid)350 static int conn_call_dcid_status(ngtcp2_conn *conn,
351                                  ngtcp2_connection_id_status_type type,
352                                  const ngtcp2_dcid *dcid) {
353   int rv;
354 
355   if (!conn->callbacks.dcid_status) {
356     return 0;
357   }
358 
359   rv = conn->callbacks.dcid_status(
360       conn, (int)type, dcid->seq, &dcid->cid,
361       (dcid->flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT) ? dcid->token : NULL,
362       conn->user_data);
363   if (rv != 0) {
364     return NGTCP2_ERR_CALLBACK_FAILURE;
365   }
366 
367   return 0;
368 }
369 
conn_call_activate_dcid(ngtcp2_conn * conn,const ngtcp2_dcid * dcid)370 static int conn_call_activate_dcid(ngtcp2_conn *conn, const ngtcp2_dcid *dcid) {
371   return conn_call_dcid_status(conn, NGTCP2_CONNECTION_ID_STATUS_TYPE_ACTIVATE,
372                                dcid);
373 }
374 
conn_call_deactivate_dcid(ngtcp2_conn * conn,const ngtcp2_dcid * dcid)375 static int conn_call_deactivate_dcid(ngtcp2_conn *conn,
376                                      const ngtcp2_dcid *dcid) {
377   return conn_call_dcid_status(
378       conn, NGTCP2_CONNECTION_ID_STATUS_TYPE_DEACTIVATE, dcid);
379 }
380 
conn_call_stream_stop_sending(ngtcp2_conn * conn,int64_t stream_id,uint64_t app_error_code,void * stream_user_data)381 static int conn_call_stream_stop_sending(ngtcp2_conn *conn, int64_t stream_id,
382                                          uint64_t app_error_code,
383                                          void *stream_user_data) {
384   int rv;
385 
386   if (!conn->callbacks.stream_stop_sending) {
387     return 0;
388   }
389 
390   rv = conn->callbacks.stream_stop_sending(conn, stream_id, app_error_code,
391                                            conn->user_data, stream_user_data);
392   if (rv != 0) {
393     return NGTCP2_ERR_CALLBACK_FAILURE;
394   }
395 
396   return 0;
397 }
398 
conn_call_delete_crypto_aead_ctx(ngtcp2_conn * conn,ngtcp2_crypto_aead_ctx * aead_ctx)399 static void conn_call_delete_crypto_aead_ctx(ngtcp2_conn *conn,
400                                              ngtcp2_crypto_aead_ctx *aead_ctx) {
401   if (!aead_ctx->native_handle) {
402     return;
403   }
404 
405   assert(conn->callbacks.delete_crypto_aead_ctx);
406 
407   conn->callbacks.delete_crypto_aead_ctx(conn, aead_ctx, conn->user_data);
408 }
409 
410 static void
conn_call_delete_crypto_cipher_ctx(ngtcp2_conn * conn,ngtcp2_crypto_cipher_ctx * cipher_ctx)411 conn_call_delete_crypto_cipher_ctx(ngtcp2_conn *conn,
412                                    ngtcp2_crypto_cipher_ctx *cipher_ctx) {
413   if (!cipher_ctx->native_handle) {
414     return;
415   }
416 
417   assert(conn->callbacks.delete_crypto_cipher_ctx);
418 
419   conn->callbacks.delete_crypto_cipher_ctx(conn, cipher_ctx, conn->user_data);
420 }
421 
conn_call_client_initial(ngtcp2_conn * conn)422 static int conn_call_client_initial(ngtcp2_conn *conn) {
423   int rv;
424 
425   assert(conn->callbacks.client_initial);
426 
427   rv = conn->callbacks.client_initial(conn, conn->user_data);
428   if (rv != 0) {
429     return NGTCP2_ERR_CALLBACK_FAILURE;
430   }
431 
432   return 0;
433 }
434 
conn_call_get_path_challenge_data(ngtcp2_conn * conn,uint8_t * data)435 static int conn_call_get_path_challenge_data(ngtcp2_conn *conn, uint8_t *data) {
436   int rv;
437 
438   assert(conn->callbacks.get_path_challenge_data);
439 
440   rv = conn->callbacks.get_path_challenge_data(conn, data, conn->user_data);
441   if (rv != 0) {
442     return NGTCP2_ERR_CALLBACK_FAILURE;
443   }
444 
445   return 0;
446 }
447 
conn_call_recv_version_negotiation(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd,const uint32_t * sv,size_t nsv)448 static int conn_call_recv_version_negotiation(ngtcp2_conn *conn,
449                                               const ngtcp2_pkt_hd *hd,
450                                               const uint32_t *sv, size_t nsv) {
451   int rv;
452 
453   if (!conn->callbacks.recv_version_negotiation) {
454     return 0;
455   }
456 
457   rv = conn->callbacks.recv_version_negotiation(conn, hd, sv, nsv,
458                                                 conn->user_data);
459   if (rv != 0) {
460     return NGTCP2_ERR_CALLBACK_FAILURE;
461   }
462 
463   return 0;
464 }
465 
conn_call_recv_retry(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd)466 static int conn_call_recv_retry(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd) {
467   int rv;
468 
469   assert(conn->callbacks.recv_retry);
470 
471   rv = conn->callbacks.recv_retry(conn, hd, conn->user_data);
472   if (rv != 0) {
473     return NGTCP2_ERR_CALLBACK_FAILURE;
474   }
475 
476   return 0;
477 }
478 
479 static int
conn_call_recv_stateless_reset(ngtcp2_conn * conn,const ngtcp2_pkt_stateless_reset * sr)480 conn_call_recv_stateless_reset(ngtcp2_conn *conn,
481                                const ngtcp2_pkt_stateless_reset *sr) {
482   int rv;
483 
484   if (!conn->callbacks.recv_stateless_reset) {
485     return 0;
486   }
487 
488   rv = conn->callbacks.recv_stateless_reset(conn, sr, conn->user_data);
489   if (rv != 0) {
490     return NGTCP2_ERR_CALLBACK_FAILURE;
491   }
492 
493   return 0;
494 }
495 
conn_call_recv_new_token(ngtcp2_conn * conn,const ngtcp2_vec * token)496 static int conn_call_recv_new_token(ngtcp2_conn *conn,
497                                     const ngtcp2_vec *token) {
498   int rv;
499 
500   if (!conn->callbacks.recv_new_token) {
501     return 0;
502   }
503 
504   rv = conn->callbacks.recv_new_token(conn, token, conn->user_data);
505   if (rv != 0) {
506     return NGTCP2_ERR_CALLBACK_FAILURE;
507   }
508 
509   return 0;
510 }
511 
conn_call_handshake_confirmed(ngtcp2_conn * conn)512 static int conn_call_handshake_confirmed(ngtcp2_conn *conn) {
513   int rv;
514 
515   if (!conn->callbacks.handshake_confirmed) {
516     return 0;
517   }
518 
519   rv = conn->callbacks.handshake_confirmed(conn, conn->user_data);
520   if (rv != 0) {
521     return NGTCP2_ERR_CALLBACK_FAILURE;
522   }
523 
524   return 0;
525 }
526 
conn_call_recv_datagram(ngtcp2_conn * conn,const ngtcp2_datagram * fr)527 static int conn_call_recv_datagram(ngtcp2_conn *conn,
528                                    const ngtcp2_datagram *fr) {
529   const uint8_t *data;
530   size_t datalen;
531   int rv;
532   uint32_t flags = NGTCP2_DATAGRAM_FLAG_NONE;
533 
534   if (!conn->callbacks.recv_datagram) {
535     return 0;
536   }
537 
538   if (fr->datacnt) {
539     assert(fr->datacnt == 1);
540 
541     data = fr->data->base;
542     datalen = fr->data->len;
543   } else {
544     data = NULL;
545     datalen = 0;
546   }
547 
548   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
549     flags |= NGTCP2_DATAGRAM_FLAG_EARLY;
550   }
551 
552   rv = conn->callbacks.recv_datagram(conn, flags, data, datalen,
553                                      conn->user_data);
554   if (rv != 0) {
555     return NGTCP2_ERR_CALLBACK_FAILURE;
556   }
557 
558   return 0;
559 }
560 
561 static int
conn_call_update_key(ngtcp2_conn * conn,uint8_t * rx_secret,uint8_t * tx_secret,ngtcp2_crypto_aead_ctx * rx_aead_ctx,uint8_t * rx_iv,ngtcp2_crypto_aead_ctx * tx_aead_ctx,uint8_t * tx_iv,const uint8_t * current_rx_secret,const uint8_t * current_tx_secret,size_t secretlen)562 conn_call_update_key(ngtcp2_conn *conn, uint8_t *rx_secret, uint8_t *tx_secret,
563                      ngtcp2_crypto_aead_ctx *rx_aead_ctx, uint8_t *rx_iv,
564                      ngtcp2_crypto_aead_ctx *tx_aead_ctx, uint8_t *tx_iv,
565                      const uint8_t *current_rx_secret,
566                      const uint8_t *current_tx_secret, size_t secretlen) {
567   int rv;
568 
569   assert(conn->callbacks.update_key);
570 
571   rv = conn->callbacks.update_key(
572       conn, rx_secret, tx_secret, rx_aead_ctx, rx_iv, tx_aead_ctx, tx_iv,
573       current_rx_secret, current_tx_secret, secretlen, conn->user_data);
574   if (rv != 0) {
575     return NGTCP2_ERR_CALLBACK_FAILURE;
576   }
577 
578   return 0;
579 }
580 
crypto_offset_less(const ngtcp2_ksl_key * lhs,const ngtcp2_ksl_key * rhs)581 static int crypto_offset_less(const ngtcp2_ksl_key *lhs,
582                               const ngtcp2_ksl_key *rhs) {
583   return *(int64_t *)lhs < *(int64_t *)rhs;
584 }
585 
pktns_init(ngtcp2_pktns * pktns,ngtcp2_pktns_id pktns_id,ngtcp2_rst * rst,ngtcp2_cc * cc,ngtcp2_log * log,ngtcp2_qlog * qlog,const ngtcp2_mem * mem)586 static int pktns_init(ngtcp2_pktns *pktns, ngtcp2_pktns_id pktns_id,
587                       ngtcp2_rst *rst, ngtcp2_cc *cc, ngtcp2_log *log,
588                       ngtcp2_qlog *qlog, const ngtcp2_mem *mem) {
589   int rv;
590 
591   memset(pktns, 0, sizeof(*pktns));
592 
593   rv = ngtcp2_gaptr_init(&pktns->rx.pngap, mem);
594   if (rv != 0) {
595     return rv;
596   }
597 
598   pktns->tx.last_pkt_num = -1;
599   pktns->rx.max_pkt_num = -1;
600   pktns->rx.max_ack_eliciting_pkt_num = -1;
601 
602   rv = ngtcp2_acktr_init(&pktns->acktr, log, mem);
603   if (rv != 0) {
604     goto fail_acktr_init;
605   }
606 
607   rv = ngtcp2_strm_init(&pktns->crypto.strm, 0, NGTCP2_STRM_FLAG_NONE, 0, 0,
608                         NULL, mem);
609   if (rv != 0) {
610     goto fail_crypto_init;
611   }
612 
613   rv = ngtcp2_ksl_init(&pktns->crypto.tx.frq, crypto_offset_less,
614                        sizeof(uint64_t), mem);
615   if (rv != 0) {
616     goto fail_tx_frq_init;
617   }
618 
619   ngtcp2_rtb_init(&pktns->rtb, pktns_id, &pktns->crypto.strm, rst, cc, log,
620                   qlog, mem);
621 
622   return 0;
623 
624 fail_tx_frq_init:
625   ngtcp2_strm_free(&pktns->crypto.strm);
626 fail_crypto_init:
627   ngtcp2_acktr_free(&pktns->acktr);
628 fail_acktr_init:
629   ngtcp2_gaptr_free(&pktns->rx.pngap);
630 
631   return rv;
632 }
633 
pktns_new(ngtcp2_pktns ** ppktns,ngtcp2_pktns_id pktns_id,ngtcp2_rst * rst,ngtcp2_cc * cc,ngtcp2_log * log,ngtcp2_qlog * qlog,const ngtcp2_mem * mem)634 static int pktns_new(ngtcp2_pktns **ppktns, ngtcp2_pktns_id pktns_id,
635                      ngtcp2_rst *rst, ngtcp2_cc *cc, ngtcp2_log *log,
636                      ngtcp2_qlog *qlog, const ngtcp2_mem *mem) {
637   int rv;
638 
639   *ppktns = ngtcp2_mem_malloc(mem, sizeof(ngtcp2_pktns));
640   if (*ppktns == NULL) {
641     return NGTCP2_ERR_NOMEM;
642   }
643 
644   rv = pktns_init(*ppktns, pktns_id, rst, cc, log, qlog, mem);
645   if (rv != 0) {
646     ngtcp2_mem_free(mem, *ppktns);
647   }
648 
649   return rv;
650 }
651 
cycle_less(const ngtcp2_pq_entry * lhs,const ngtcp2_pq_entry * rhs)652 static int cycle_less(const ngtcp2_pq_entry *lhs, const ngtcp2_pq_entry *rhs) {
653   ngtcp2_strm *ls = ngtcp2_struct_of(lhs, ngtcp2_strm, pe);
654   ngtcp2_strm *rs = ngtcp2_struct_of(rhs, ngtcp2_strm, pe);
655 
656   if (ls->cycle == rs->cycle) {
657     return ls->stream_id < rs->stream_id;
658   }
659 
660   return rs->cycle - ls->cycle <= 1;
661 }
662 
delete_buffed_pkts(ngtcp2_pkt_chain * pc,const ngtcp2_mem * mem)663 static void delete_buffed_pkts(ngtcp2_pkt_chain *pc, const ngtcp2_mem *mem) {
664   ngtcp2_pkt_chain *next;
665 
666   for (; pc;) {
667     next = pc->next;
668     ngtcp2_pkt_chain_del(pc, mem);
669     pc = next;
670   }
671 }
672 
delete_buf_chain(ngtcp2_buf_chain * bufchain,const ngtcp2_mem * mem)673 static void delete_buf_chain(ngtcp2_buf_chain *bufchain,
674                              const ngtcp2_mem *mem) {
675   ngtcp2_buf_chain *next;
676 
677   for (; bufchain;) {
678     next = bufchain->next;
679     ngtcp2_buf_chain_del(bufchain, mem);
680     bufchain = next;
681   }
682 }
683 
pktns_free(ngtcp2_pktns * pktns,const ngtcp2_mem * mem)684 static void pktns_free(ngtcp2_pktns *pktns, const ngtcp2_mem *mem) {
685   ngtcp2_frame_chain *frc;
686   ngtcp2_ksl_it it;
687 
688   delete_buf_chain(pktns->crypto.tx.data, mem);
689 
690   delete_buffed_pkts(pktns->rx.buffed_pkts, mem);
691 
692   ngtcp2_frame_chain_list_del(pktns->tx.frq, mem);
693 
694   ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, mem);
695   ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, mem);
696 
697   for (it = ngtcp2_ksl_begin(&pktns->crypto.tx.frq); !ngtcp2_ksl_it_end(&it);
698        ngtcp2_ksl_it_next(&it)) {
699     frc = ngtcp2_ksl_it_get(&it);
700     ngtcp2_frame_chain_del(frc, mem);
701   }
702 
703   ngtcp2_ksl_free(&pktns->crypto.tx.frq);
704   ngtcp2_rtb_free(&pktns->rtb);
705   ngtcp2_strm_free(&pktns->crypto.strm);
706   ngtcp2_acktr_free(&pktns->acktr);
707   ngtcp2_gaptr_free(&pktns->rx.pngap);
708 }
709 
pktns_del(ngtcp2_pktns * pktns,const ngtcp2_mem * mem)710 static void pktns_del(ngtcp2_pktns *pktns, const ngtcp2_mem *mem) {
711   if (pktns == NULL) {
712     return;
713   }
714 
715   pktns_free(pktns, mem);
716 
717   ngtcp2_mem_free(mem, pktns);
718 }
719 
cc_del(ngtcp2_cc * cc,ngtcp2_cc_algo cc_algo,const ngtcp2_mem * mem)720 static void cc_del(ngtcp2_cc *cc, ngtcp2_cc_algo cc_algo,
721                    const ngtcp2_mem *mem) {
722   switch (cc_algo) {
723   case NGTCP2_CC_ALGO_RENO:
724     ngtcp2_cc_reno_cc_free(cc, mem);
725     break;
726   case NGTCP2_CC_ALGO_CUBIC:
727     ngtcp2_cc_cubic_cc_free(cc, mem);
728     break;
729   case NGTCP2_CC_ALGO_BBR:
730     ngtcp2_cc_bbr_cc_free(cc, mem);
731     break;
732   default:
733     break;
734   }
735 }
736 
cid_less(const ngtcp2_ksl_key * lhs,const ngtcp2_ksl_key * rhs)737 static int cid_less(const ngtcp2_ksl_key *lhs, const ngtcp2_ksl_key *rhs) {
738   return ngtcp2_cid_less(lhs, rhs);
739 }
740 
retired_ts_less(const ngtcp2_pq_entry * lhs,const ngtcp2_pq_entry * rhs)741 static int retired_ts_less(const ngtcp2_pq_entry *lhs,
742                            const ngtcp2_pq_entry *rhs) {
743   const ngtcp2_scid *a = ngtcp2_struct_of(lhs, ngtcp2_scid, pe);
744   const ngtcp2_scid *b = ngtcp2_struct_of(rhs, ngtcp2_scid, pe);
745 
746   return a->retired_ts < b->retired_ts;
747 }
748 
749 /*
750  * conn_reset_conn_stat_cc resets congestion state in |cstat|.
751  */
conn_reset_conn_stat_cc(ngtcp2_conn * conn,ngtcp2_conn_stat * cstat)752 static void conn_reset_conn_stat_cc(ngtcp2_conn *conn,
753                                     ngtcp2_conn_stat *cstat) {
754   cstat->latest_rtt = 0;
755   cstat->min_rtt = UINT64_MAX;
756   cstat->smoothed_rtt = conn->local.settings.initial_rtt;
757   cstat->rttvar = conn->local.settings.initial_rtt / 2;
758   cstat->first_rtt_sample_ts = UINT64_MAX;
759   cstat->pto_count = 0;
760   cstat->loss_detection_timer = UINT64_MAX;
761   cstat->cwnd =
762       ngtcp2_cc_compute_initcwnd(conn->local.settings.max_udp_payload_size);
763   cstat->ssthresh = UINT64_MAX;
764   cstat->congestion_recovery_start_ts = UINT64_MAX;
765   cstat->bytes_in_flight = 0;
766   cstat->delivery_rate_sec = 0;
767   cstat->pacing_rate = 0.0;
768   cstat->send_quantum = SIZE_MAX;
769 }
770 
771 /*
772  * reset_conn_stat_recovery resets the fields related to the recovery
773  * function
774  */
reset_conn_stat_recovery(ngtcp2_conn_stat * cstat)775 static void reset_conn_stat_recovery(ngtcp2_conn_stat *cstat) {
776   /* Initializes them with UINT64_MAX. */
777   memset(cstat->loss_time, 0xff, sizeof(cstat->loss_time));
778   memset(cstat->last_tx_pkt_ts, 0xff, sizeof(cstat->last_tx_pkt_ts));
779 }
780 
781 /*
782  * conn_reset_conn_stat resets |cstat|.  The following fields are not
783  * reset: initial_rtt and max_udp_payload_size.
784  */
conn_reset_conn_stat(ngtcp2_conn * conn,ngtcp2_conn_stat * cstat)785 static void conn_reset_conn_stat(ngtcp2_conn *conn, ngtcp2_conn_stat *cstat) {
786   conn_reset_conn_stat_cc(conn, cstat);
787   reset_conn_stat_recovery(cstat);
788 }
789 
delete_scid(ngtcp2_ksl * scids,const ngtcp2_mem * mem)790 static void delete_scid(ngtcp2_ksl *scids, const ngtcp2_mem *mem) {
791   ngtcp2_ksl_it it;
792 
793   for (it = ngtcp2_ksl_begin(scids); !ngtcp2_ksl_it_end(&it);
794        ngtcp2_ksl_it_next(&it)) {
795     ngtcp2_mem_free(mem, ngtcp2_ksl_it_get(&it));
796   }
797 }
798 
799 /*
800  * compute_pto computes PTO.
801  */
compute_pto(ngtcp2_duration smoothed_rtt,ngtcp2_duration rttvar,ngtcp2_duration max_ack_delay)802 static ngtcp2_duration compute_pto(ngtcp2_duration smoothed_rtt,
803                                    ngtcp2_duration rttvar,
804                                    ngtcp2_duration max_ack_delay) {
805   ngtcp2_duration var = ngtcp2_max(4 * rttvar, NGTCP2_GRANULARITY);
806   return smoothed_rtt + var + max_ack_delay;
807 }
808 
809 /*
810  * conn_compute_initial_pto computes PTO using the initial RTT.
811  */
conn_compute_initial_pto(ngtcp2_conn * conn,ngtcp2_pktns * pktns)812 static ngtcp2_duration conn_compute_initial_pto(ngtcp2_conn *conn,
813                                                 ngtcp2_pktns *pktns) {
814   ngtcp2_duration initial_rtt = conn->local.settings.initial_rtt;
815   ngtcp2_duration max_ack_delay =
816       pktns->rtb.pktns_id == NGTCP2_PKTNS_ID_APPLICATION
817           ? conn->remote.transport_params.max_ack_delay
818           : 0;
819   return compute_pto(initial_rtt, initial_rtt / 2, max_ack_delay);
820 }
821 
822 /*
823  * conn_compute_pto computes the current PTO.
824  */
conn_compute_pto(ngtcp2_conn * conn,ngtcp2_pktns * pktns)825 static ngtcp2_duration conn_compute_pto(ngtcp2_conn *conn,
826                                         ngtcp2_pktns *pktns) {
827   ngtcp2_conn_stat *cstat = &conn->cstat;
828   ngtcp2_duration max_ack_delay =
829       pktns->rtb.pktns_id == NGTCP2_PKTNS_ID_APPLICATION
830           ? conn->remote.transport_params.max_ack_delay
831           : 0;
832   return compute_pto(cstat->smoothed_rtt, cstat->rttvar, max_ack_delay);
833 }
834 
ngtcp2_conn_compute_pto(ngtcp2_conn * conn,ngtcp2_pktns * pktns)835 ngtcp2_duration ngtcp2_conn_compute_pto(ngtcp2_conn *conn,
836                                         ngtcp2_pktns *pktns) {
837   return conn_compute_pto(conn, pktns);
838 }
839 
conn_handle_tx_ecn(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * prtb_entry_flags,ngtcp2_pktns * pktns,const ngtcp2_pkt_hd * hd,ngtcp2_tstamp ts)840 static void conn_handle_tx_ecn(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
841                                uint8_t *prtb_entry_flags, ngtcp2_pktns *pktns,
842                                const ngtcp2_pkt_hd *hd, ngtcp2_tstamp ts) {
843   assert(pi);
844 
845   if (pi->ecn != NGTCP2_ECN_NOT_ECT) {
846     /* We have already made a transition of validation state and
847       deceided to send UDP datagram with ECN bit set.  Coalesced QUIC
848       packets also bear ECN bits set. */
849     if (pktns->tx.ecn.start_pkt_num == INT64_MAX) {
850       pktns->tx.ecn.start_pkt_num = hd->pkt_num;
851     }
852 
853     ++pktns->tx.ecn.validation_pkt_sent;
854 
855     if (prtb_entry_flags) {
856       *prtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ECN;
857     }
858 
859     ++pktns->tx.ecn.ect0;
860 
861     return;
862   }
863 
864   switch (conn->tx.ecn.state) {
865   case NGTCP2_ECN_STATE_TESTING:
866     if (conn->tx.ecn.validation_start_ts == UINT64_MAX) {
867       assert(0 == pktns->tx.ecn.validation_pkt_sent);
868       assert(0 == pktns->tx.ecn.validation_pkt_lost);
869 
870       conn->tx.ecn.validation_start_ts = ts;
871     } else if (ts - conn->tx.ecn.validation_start_ts >=
872                3 * conn_compute_pto(conn, pktns)) {
873       conn->tx.ecn.state = NGTCP2_ECN_STATE_UNKNOWN;
874       break;
875     }
876 
877     if (pktns->tx.ecn.start_pkt_num == INT64_MAX) {
878       pktns->tx.ecn.start_pkt_num = hd->pkt_num;
879     }
880 
881     ++pktns->tx.ecn.validation_pkt_sent;
882 
883     if (++conn->tx.ecn.dgram_sent == NGTCP2_ECN_MAX_NUM_VALIDATION_PKTS) {
884       conn->tx.ecn.state = NGTCP2_ECN_STATE_UNKNOWN;
885     }
886     /* fall through */
887   case NGTCP2_ECN_STATE_CAPABLE:
888     /* pi is provided per UDP datagram. */
889     assert(NGTCP2_ECN_NOT_ECT == pi->ecn);
890 
891     pi->ecn = NGTCP2_ECN_ECT_0;
892 
893     if (prtb_entry_flags) {
894       *prtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ECN;
895     }
896 
897     ++pktns->tx.ecn.ect0;
898     break;
899   case NGTCP2_ECN_STATE_UNKNOWN:
900   case NGTCP2_ECN_STATE_FAILED:
901     break;
902   default:
903     assert(0);
904   }
905 }
906 
conn_reset_ecn_validation_state(ngtcp2_conn * conn)907 static void conn_reset_ecn_validation_state(ngtcp2_conn *conn) {
908   ngtcp2_pktns *in_pktns = conn->in_pktns;
909   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
910   ngtcp2_pktns *pktns = &conn->pktns;
911 
912   conn->tx.ecn.state = NGTCP2_ECN_STATE_TESTING;
913   conn->tx.ecn.validation_start_ts = UINT64_MAX;
914   conn->tx.ecn.dgram_sent = 0;
915 
916   if (in_pktns) {
917     in_pktns->tx.ecn.start_pkt_num = INT64_MAX;
918     in_pktns->tx.ecn.validation_pkt_sent = 0;
919     in_pktns->tx.ecn.validation_pkt_lost = 0;
920   }
921 
922   if (hs_pktns) {
923     hs_pktns->tx.ecn.start_pkt_num = INT64_MAX;
924     hs_pktns->tx.ecn.validation_pkt_sent = 0;
925     hs_pktns->tx.ecn.validation_pkt_lost = 0;
926   }
927 
928   pktns->tx.ecn.start_pkt_num = INT64_MAX;
929   pktns->tx.ecn.validation_pkt_sent = 0;
930   pktns->tx.ecn.validation_pkt_lost = 0;
931 }
932 
conn_new(ngtcp2_conn ** pconn,const ngtcp2_cid * dcid,const ngtcp2_cid * scid,const ngtcp2_path * path,uint32_t version,int callbacks_version,const ngtcp2_callbacks * callbacks,int settings_version,const ngtcp2_settings * settings,int transport_params_version,const ngtcp2_transport_params * params,const ngtcp2_mem * mem,void * user_data,int server)933 static int conn_new(ngtcp2_conn **pconn, const ngtcp2_cid *dcid,
934                     const ngtcp2_cid *scid, const ngtcp2_path *path,
935                     uint32_t version, int callbacks_version,
936                     const ngtcp2_callbacks *callbacks, int settings_version,
937                     const ngtcp2_settings *settings,
938                     int transport_params_version,
939                     const ngtcp2_transport_params *params,
940                     const ngtcp2_mem *mem, void *user_data, int server) {
941   int rv;
942   ngtcp2_scid *scident;
943   uint8_t *buf;
944   uint8_t fixed_bit_byte;
945   (void)callbacks_version;
946   (void)settings_version;
947   (void)transport_params_version;
948 
949   assert(settings->max_window <= NGTCP2_MAX_VARINT);
950   assert(settings->max_stream_window <= NGTCP2_MAX_VARINT);
951   assert(settings->max_udp_payload_size);
952   assert(params->active_connection_id_limit <= NGTCP2_MAX_DCID_POOL_SIZE);
953   assert(params->initial_max_data <= NGTCP2_MAX_VARINT);
954   assert(params->initial_max_stream_data_bidi_local <= NGTCP2_MAX_VARINT);
955   assert(params->initial_max_stream_data_bidi_remote <= NGTCP2_MAX_VARINT);
956   assert(params->initial_max_stream_data_uni <= NGTCP2_MAX_VARINT);
957   assert(server || callbacks->client_initial);
958   assert(!server || callbacks->recv_client_initial);
959   assert(callbacks->recv_crypto_data);
960   assert(callbacks->encrypt);
961   assert(callbacks->decrypt);
962   assert(callbacks->hp_mask);
963   assert(server || callbacks->recv_retry);
964   assert(callbacks->rand);
965   assert(callbacks->get_new_connection_id);
966   assert(callbacks->update_key);
967   assert(callbacks->delete_crypto_aead_ctx);
968   assert(callbacks->delete_crypto_cipher_ctx);
969   assert(callbacks->get_path_challenge_data);
970 
971   if (mem == NULL) {
972     mem = ngtcp2_mem_default();
973   }
974 
975   *pconn = ngtcp2_mem_calloc(mem, 1, sizeof(ngtcp2_conn));
976   if (*pconn == NULL) {
977     rv = NGTCP2_ERR_NOMEM;
978     goto fail_conn;
979   }
980 
981   rv = ngtcp2_ringbuf_init(&(*pconn)->dcid.bound,
982                            NGTCP2_MAX_BOUND_DCID_POOL_SIZE, sizeof(ngtcp2_dcid),
983                            mem);
984   if (rv != 0) {
985     goto fail_dcid_bound_init;
986   }
987 
988   rv = ngtcp2_ringbuf_init(&(*pconn)->dcid.unused, NGTCP2_MAX_DCID_POOL_SIZE,
989                            sizeof(ngtcp2_dcid), mem);
990   if (rv != 0) {
991     goto fail_dcid_unused_init;
992   }
993 
994   rv =
995       ngtcp2_ringbuf_init(&(*pconn)->dcid.retired, NGTCP2_MAX_DCID_RETIRED_SIZE,
996                           sizeof(ngtcp2_dcid), mem);
997   if (rv != 0) {
998     goto fail_dcid_retired_init;
999   }
1000 
1001   rv = ngtcp2_gaptr_init(&(*pconn)->dcid.seqgap, mem);
1002   if (rv != 0) {
1003     goto fail_seqgap_init;
1004   }
1005 
1006   rv = ngtcp2_ksl_init(&(*pconn)->scid.set, cid_less, sizeof(ngtcp2_cid), mem);
1007   if (rv != 0) {
1008     goto fail_scid_set_init;
1009   }
1010 
1011   ngtcp2_pq_init(&(*pconn)->scid.used, retired_ts_less, mem);
1012 
1013   rv = ngtcp2_map_init(&(*pconn)->strms, mem);
1014   if (rv != 0) {
1015     goto fail_strms_init;
1016   }
1017 
1018   ngtcp2_pq_init(&(*pconn)->tx.strmq, cycle_less, mem);
1019 
1020   rv = ngtcp2_idtr_init(&(*pconn)->remote.bidi.idtr, !server, mem);
1021   if (rv != 0) {
1022     goto fail_remote_bidi_idtr_init;
1023   }
1024 
1025   rv = ngtcp2_idtr_init(&(*pconn)->remote.uni.idtr, !server, mem);
1026   if (rv != 0) {
1027     goto fail_remote_uni_idtr_init;
1028   }
1029 
1030   rv = ngtcp2_ringbuf_init(&(*pconn)->rx.path_challenge, 4,
1031                            sizeof(ngtcp2_path_challenge_entry), mem);
1032   if (rv != 0) {
1033     goto fail_rx_path_challenge_init;
1034   }
1035 
1036   ngtcp2_log_init(&(*pconn)->log, scid, settings->log_printf,
1037                   settings->initial_ts, user_data);
1038   ngtcp2_qlog_init(&(*pconn)->qlog, settings->qlog.write, settings->initial_ts,
1039                    user_data);
1040   if ((*pconn)->qlog.write) {
1041     buf = ngtcp2_mem_malloc(mem, NGTCP2_QLOG_BUFLEN);
1042     if (buf == NULL) {
1043       goto fail_qlog_buf;
1044     }
1045     ngtcp2_buf_init(&(*pconn)->qlog.buf, buf, NGTCP2_QLOG_BUFLEN);
1046   }
1047 
1048   (*pconn)->local.settings = *settings;
1049   (*pconn)->local.transport_params = *params;
1050 
1051   /* grease_quic_bit is always enabled. */
1052   (*pconn)->local.transport_params.grease_quic_bit = 1;
1053 
1054   if (settings->token.len) {
1055     buf = ngtcp2_mem_malloc(mem, settings->token.len);
1056     if (buf == NULL) {
1057       goto fail_token;
1058     }
1059     memcpy(buf, settings->token.base, settings->token.len);
1060     (*pconn)->local.settings.token.base = buf;
1061   } else {
1062     (*pconn)->local.settings.token.base = NULL;
1063     (*pconn)->local.settings.token.len = 0;
1064   }
1065 
1066   conn_reset_conn_stat(*pconn, &(*pconn)->cstat);
1067   (*pconn)->cstat.initial_rtt = settings->initial_rtt;
1068   (*pconn)->cstat.max_udp_payload_size =
1069       (*pconn)->local.settings.max_udp_payload_size;
1070 
1071   ngtcp2_rst_init(&(*pconn)->rst);
1072 
1073   (*pconn)->cc_algo = settings->cc_algo;
1074 
1075   switch (settings->cc_algo) {
1076   case NGTCP2_CC_ALGO_RENO:
1077     rv = ngtcp2_cc_reno_cc_init(&(*pconn)->cc, &(*pconn)->log, mem);
1078     if (rv != 0) {
1079       goto fail_cc_init;
1080     }
1081     break;
1082   case NGTCP2_CC_ALGO_CUBIC:
1083     rv = ngtcp2_cc_cubic_cc_init(&(*pconn)->cc, &(*pconn)->log, mem);
1084     if (rv != 0) {
1085       goto fail_cc_init;
1086     }
1087     break;
1088   case NGTCP2_CC_ALGO_BBR:
1089     rv = ngtcp2_cc_bbr_cc_init(&(*pconn)->cc, &(*pconn)->log, &(*pconn)->cstat,
1090                                &(*pconn)->rst, settings->initial_ts,
1091                                callbacks->rand, &settings->rand_ctx, mem);
1092     if (rv != 0) {
1093       goto fail_cc_init;
1094     }
1095     break;
1096   case NGTCP2_CC_ALGO_CUSTOM:
1097     assert(settings->cc);
1098     (*pconn)->cc = *settings->cc;
1099     (*pconn)->cc.ccb->log = &(*pconn)->log;
1100     break;
1101   default:
1102     assert(0);
1103   }
1104 
1105   rv = pktns_new(&(*pconn)->in_pktns, NGTCP2_PKTNS_ID_INITIAL, &(*pconn)->rst,
1106                  &(*pconn)->cc, &(*pconn)->log, &(*pconn)->qlog, mem);
1107   if (rv != 0) {
1108     goto fail_in_pktns_init;
1109   }
1110 
1111   rv = pktns_new(&(*pconn)->hs_pktns, NGTCP2_PKTNS_ID_HANDSHAKE, &(*pconn)->rst,
1112                  &(*pconn)->cc, &(*pconn)->log, &(*pconn)->qlog, mem);
1113   if (rv != 0) {
1114     goto fail_hs_pktns_init;
1115   }
1116 
1117   rv = pktns_init(&(*pconn)->pktns, NGTCP2_PKTNS_ID_APPLICATION, &(*pconn)->rst,
1118                   &(*pconn)->cc, &(*pconn)->log, &(*pconn)->qlog, mem);
1119   if (rv != 0) {
1120     goto fail_pktns_init;
1121   }
1122 
1123   scident = ngtcp2_mem_malloc(mem, sizeof(*scident));
1124   if (scident == NULL) {
1125     rv = NGTCP2_ERR_NOMEM;
1126     goto fail_scident;
1127   }
1128 
1129   /* Set stateless reset token later if it is available in the local
1130      transport parameters */
1131   ngtcp2_scid_init(scident, 0, scid);
1132 
1133   rv = ngtcp2_ksl_insert(&(*pconn)->scid.set, NULL, &scident->cid, scident);
1134   if (rv != 0) {
1135     goto fail_scid_set_insert;
1136   }
1137 
1138   scident = NULL;
1139 
1140   ngtcp2_dcid_init(&(*pconn)->dcid.current, 0, dcid, NULL);
1141   ngtcp2_dcid_set_path(&(*pconn)->dcid.current, path);
1142 
1143   rv = ngtcp2_gaptr_push(&(*pconn)->dcid.seqgap, 0, 1);
1144   if (rv != 0) {
1145     goto fail_seqgap_push;
1146   }
1147 
1148   callbacks->rand(&fixed_bit_byte, 1, &settings->rand_ctx);
1149   if (fixed_bit_byte & 1) {
1150     (*pconn)->flags |= NGTCP2_CONN_FLAG_CLEAR_FIXED_BIT;
1151   }
1152 
1153   (*pconn)->keep_alive.last_ts = UINT64_MAX;
1154 
1155   (*pconn)->server = server;
1156   (*pconn)->oscid = *scid;
1157   (*pconn)->callbacks = *callbacks;
1158   (*pconn)->version = version;
1159   (*pconn)->mem = mem;
1160   (*pconn)->user_data = user_data;
1161   (*pconn)->idle_ts = settings->initial_ts;
1162   (*pconn)->crypto.key_update.confirmed_ts = UINT64_MAX;
1163   (*pconn)->tx.last_max_data_ts = UINT64_MAX;
1164   (*pconn)->tx.pacing.next_ts = UINT64_MAX;
1165   (*pconn)->early.discard_started_ts = UINT64_MAX;
1166 
1167   conn_reset_ecn_validation_state(*pconn);
1168 
1169   ngtcp2_qlog_start(&(*pconn)->qlog, server ? &settings->qlog.odcid : dcid,
1170                     server);
1171 
1172   return 0;
1173 
1174 fail_seqgap_push:
1175 fail_scid_set_insert:
1176   ngtcp2_mem_free(mem, scident);
1177 fail_scident:
1178   ngtcp2_mem_free(mem, (*pconn)->local.settings.token.base);
1179 fail_token:
1180   pktns_free(&(*pconn)->pktns, mem);
1181 fail_pktns_init:
1182   pktns_del((*pconn)->hs_pktns, mem);
1183 fail_hs_pktns_init:
1184   pktns_del((*pconn)->in_pktns, mem);
1185 fail_in_pktns_init:
1186   cc_del(&(*pconn)->cc, settings->cc_algo, mem);
1187 fail_cc_init:
1188   ngtcp2_mem_free(mem, (*pconn)->qlog.buf.begin);
1189 fail_qlog_buf:
1190   ngtcp2_ringbuf_free(&(*pconn)->rx.path_challenge);
1191 fail_rx_path_challenge_init:
1192   ngtcp2_idtr_free(&(*pconn)->remote.uni.idtr);
1193 fail_remote_uni_idtr_init:
1194   ngtcp2_idtr_free(&(*pconn)->remote.bidi.idtr);
1195 fail_remote_bidi_idtr_init:
1196   ngtcp2_map_free(&(*pconn)->strms);
1197 fail_strms_init:
1198   delete_scid(&(*pconn)->scid.set, mem);
1199   ngtcp2_ksl_free(&(*pconn)->scid.set);
1200 fail_scid_set_init:
1201   ngtcp2_gaptr_free(&(*pconn)->dcid.seqgap);
1202 fail_seqgap_init:
1203   ngtcp2_ringbuf_free(&(*pconn)->dcid.retired);
1204 fail_dcid_retired_init:
1205   ngtcp2_ringbuf_free(&(*pconn)->dcid.unused);
1206 fail_dcid_unused_init:
1207   ngtcp2_ringbuf_free(&(*pconn)->dcid.bound);
1208 fail_dcid_bound_init:
1209   ngtcp2_mem_free(mem, *pconn);
1210 fail_conn:
1211   return rv;
1212 }
1213 
ngtcp2_conn_client_new_versioned(ngtcp2_conn ** pconn,const ngtcp2_cid * dcid,const ngtcp2_cid * scid,const ngtcp2_path * path,uint32_t version,int callbacks_version,const ngtcp2_callbacks * callbacks,int settings_version,const ngtcp2_settings * settings,int transport_params_version,const ngtcp2_transport_params * params,const ngtcp2_mem * mem,void * user_data)1214 int ngtcp2_conn_client_new_versioned(
1215     ngtcp2_conn **pconn, const ngtcp2_cid *dcid, const ngtcp2_cid *scid,
1216     const ngtcp2_path *path, uint32_t version, int callbacks_version,
1217     const ngtcp2_callbacks *callbacks, int settings_version,
1218     const ngtcp2_settings *settings, int transport_params_version,
1219     const ngtcp2_transport_params *params, const ngtcp2_mem *mem,
1220     void *user_data) {
1221   int rv;
1222   rv = conn_new(pconn, dcid, scid, path, version, callbacks_version, callbacks,
1223                 settings_version, settings, transport_params_version, params,
1224                 mem, user_data, 0);
1225   if (rv != 0) {
1226     return rv;
1227   }
1228   (*pconn)->rcid = *dcid;
1229   (*pconn)->state = NGTCP2_CS_CLIENT_INITIAL;
1230   (*pconn)->local.bidi.next_stream_id = 0;
1231   (*pconn)->local.uni.next_stream_id = 2;
1232 
1233   rv = ngtcp2_conn_commit_local_transport_params(*pconn);
1234   if (rv != 0) {
1235     ngtcp2_conn_del(*pconn);
1236     return rv;
1237   }
1238 
1239   return 0;
1240 }
1241 
ngtcp2_conn_server_new_versioned(ngtcp2_conn ** pconn,const ngtcp2_cid * dcid,const ngtcp2_cid * scid,const ngtcp2_path * path,uint32_t version,int callbacks_version,const ngtcp2_callbacks * callbacks,int settings_version,const ngtcp2_settings * settings,int transport_params_version,const ngtcp2_transport_params * params,const ngtcp2_mem * mem,void * user_data)1242 int ngtcp2_conn_server_new_versioned(
1243     ngtcp2_conn **pconn, const ngtcp2_cid *dcid, const ngtcp2_cid *scid,
1244     const ngtcp2_path *path, uint32_t version, int callbacks_version,
1245     const ngtcp2_callbacks *callbacks, int settings_version,
1246     const ngtcp2_settings *settings, int transport_params_version,
1247     const ngtcp2_transport_params *params, const ngtcp2_mem *mem,
1248     void *user_data) {
1249   int rv;
1250   rv = conn_new(pconn, dcid, scid, path, version, callbacks_version, callbacks,
1251                 settings_version, settings, transport_params_version, params,
1252                 mem, user_data, 1);
1253   if (rv != 0) {
1254     return rv;
1255   }
1256   (*pconn)->state = NGTCP2_CS_SERVER_INITIAL;
1257   (*pconn)->local.bidi.next_stream_id = 1;
1258   (*pconn)->local.uni.next_stream_id = 3;
1259 
1260   if ((*pconn)->local.settings.token.len) {
1261     /* Usage of token lifts amplification limit */
1262     (*pconn)->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
1263   }
1264 
1265   return 0;
1266 }
1267 
1268 /*
1269  * conn_fc_credits returns the number of bytes allowed to be sent to
1270  * the given stream.  Both connection and stream level flow control
1271  * credits are considered.
1272  */
conn_fc_credits(ngtcp2_conn * conn,ngtcp2_strm * strm)1273 static uint64_t conn_fc_credits(ngtcp2_conn *conn, ngtcp2_strm *strm) {
1274   return ngtcp2_min(strm->tx.max_offset - strm->tx.offset,
1275                     conn->tx.max_offset - conn->tx.offset);
1276 }
1277 
1278 /*
1279  * conn_enforce_flow_control returns the number of bytes allowed to be
1280  * sent to the given stream.  |len| might be shorted because of
1281  * available flow control credits.
1282  */
conn_enforce_flow_control(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t len)1283 static uint64_t conn_enforce_flow_control(ngtcp2_conn *conn, ngtcp2_strm *strm,
1284                                           uint64_t len) {
1285   uint64_t fc_credits = conn_fc_credits(conn, strm);
1286   return ngtcp2_min(len, fc_credits);
1287 }
1288 
delete_strms_each(void * data,void * ptr)1289 static int delete_strms_each(void *data, void *ptr) {
1290   const ngtcp2_mem *mem = ptr;
1291   ngtcp2_strm *s = data;
1292 
1293   ngtcp2_strm_free(s);
1294   ngtcp2_mem_free(mem, s);
1295 
1296   return 0;
1297 }
1298 
ngtcp2_conn_del(ngtcp2_conn * conn)1299 void ngtcp2_conn_del(ngtcp2_conn *conn) {
1300   if (conn == NULL) {
1301     return;
1302   }
1303 
1304   ngtcp2_qlog_end(&conn->qlog);
1305 
1306   if (conn->early.ckm) {
1307     conn_call_delete_crypto_aead_ctx(conn, &conn->early.ckm->aead_ctx);
1308   }
1309   conn_call_delete_crypto_cipher_ctx(conn, &conn->early.hp_ctx);
1310 
1311   if (conn->crypto.key_update.old_rx_ckm) {
1312     conn_call_delete_crypto_aead_ctx(
1313         conn, &conn->crypto.key_update.old_rx_ckm->aead_ctx);
1314   }
1315   if (conn->crypto.key_update.new_rx_ckm) {
1316     conn_call_delete_crypto_aead_ctx(
1317         conn, &conn->crypto.key_update.new_rx_ckm->aead_ctx);
1318   }
1319   if (conn->crypto.key_update.new_tx_ckm) {
1320     conn_call_delete_crypto_aead_ctx(
1321         conn, &conn->crypto.key_update.new_tx_ckm->aead_ctx);
1322   }
1323 
1324   if (conn->pktns.crypto.rx.ckm) {
1325     conn_call_delete_crypto_aead_ctx(conn,
1326                                      &conn->pktns.crypto.rx.ckm->aead_ctx);
1327   }
1328   conn_call_delete_crypto_cipher_ctx(conn, &conn->pktns.crypto.rx.hp_ctx);
1329 
1330   if (conn->pktns.crypto.tx.ckm) {
1331     conn_call_delete_crypto_aead_ctx(conn,
1332                                      &conn->pktns.crypto.tx.ckm->aead_ctx);
1333   }
1334   conn_call_delete_crypto_cipher_ctx(conn, &conn->pktns.crypto.tx.hp_ctx);
1335 
1336   if (conn->hs_pktns) {
1337     if (conn->hs_pktns->crypto.rx.ckm) {
1338       conn_call_delete_crypto_aead_ctx(
1339           conn, &conn->hs_pktns->crypto.rx.ckm->aead_ctx);
1340     }
1341     conn_call_delete_crypto_cipher_ctx(conn, &conn->hs_pktns->crypto.rx.hp_ctx);
1342 
1343     if (conn->hs_pktns->crypto.tx.ckm) {
1344       conn_call_delete_crypto_aead_ctx(
1345           conn, &conn->hs_pktns->crypto.tx.ckm->aead_ctx);
1346     }
1347     conn_call_delete_crypto_cipher_ctx(conn, &conn->hs_pktns->crypto.tx.hp_ctx);
1348   }
1349   if (conn->in_pktns) {
1350     if (conn->in_pktns->crypto.rx.ckm) {
1351       conn_call_delete_crypto_aead_ctx(
1352           conn, &conn->in_pktns->crypto.rx.ckm->aead_ctx);
1353     }
1354     conn_call_delete_crypto_cipher_ctx(conn, &conn->in_pktns->crypto.rx.hp_ctx);
1355 
1356     if (conn->in_pktns->crypto.tx.ckm) {
1357       conn_call_delete_crypto_aead_ctx(
1358           conn, &conn->in_pktns->crypto.tx.ckm->aead_ctx);
1359     }
1360     conn_call_delete_crypto_cipher_ctx(conn, &conn->in_pktns->crypto.tx.hp_ctx);
1361   }
1362 
1363   conn_call_delete_crypto_aead_ctx(conn, &conn->crypto.retry_aead_ctx);
1364 
1365   ngtcp2_mem_free(conn->mem, conn->crypto.decrypt_buf.base);
1366   ngtcp2_mem_free(conn->mem, conn->crypto.decrypt_hp_buf.base);
1367   ngtcp2_mem_free(conn->mem, conn->local.settings.token.base);
1368 
1369   ngtcp2_crypto_km_del(conn->crypto.key_update.old_rx_ckm, conn->mem);
1370   ngtcp2_crypto_km_del(conn->crypto.key_update.new_rx_ckm, conn->mem);
1371   ngtcp2_crypto_km_del(conn->crypto.key_update.new_tx_ckm, conn->mem);
1372   ngtcp2_crypto_km_del(conn->early.ckm, conn->mem);
1373 
1374   pktns_free(&conn->pktns, conn->mem);
1375   pktns_del(conn->hs_pktns, conn->mem);
1376   pktns_del(conn->in_pktns, conn->mem);
1377 
1378   cc_del(&conn->cc, conn->cc_algo, conn->mem);
1379 
1380   ngtcp2_mem_free(conn->mem, conn->qlog.buf.begin);
1381 
1382   ngtcp2_ringbuf_free(&conn->rx.path_challenge);
1383 
1384   ngtcp2_pv_del(conn->pv);
1385 
1386   ngtcp2_idtr_free(&conn->remote.uni.idtr);
1387   ngtcp2_idtr_free(&conn->remote.bidi.idtr);
1388   ngtcp2_mem_free(conn->mem, conn->tx.ack);
1389   ngtcp2_pq_free(&conn->tx.strmq);
1390   ngtcp2_map_each_free(&conn->strms, delete_strms_each, (void *)conn->mem);
1391   ngtcp2_map_free(&conn->strms);
1392 
1393   ngtcp2_pq_free(&conn->scid.used);
1394   delete_scid(&conn->scid.set, conn->mem);
1395   ngtcp2_ksl_free(&conn->scid.set);
1396   ngtcp2_gaptr_free(&conn->dcid.seqgap);
1397   ngtcp2_ringbuf_free(&conn->dcid.retired);
1398   ngtcp2_ringbuf_free(&conn->dcid.unused);
1399   ngtcp2_ringbuf_free(&conn->dcid.bound);
1400 
1401   ngtcp2_mem_free(conn->mem, conn);
1402 }
1403 
1404 /*
1405  * conn_ensure_ack_blks makes sure that conn->tx.ack->ack.blks can
1406  * contain at least |n| additional ngtcp2_ack_blk.
1407  *
1408  * This function returns 0 if it succeeds, or one of the following
1409  * negative error codes:
1410  *
1411  * NGTCP2_ERR_NOMEM
1412  *     Out of memory.
1413  */
conn_ensure_ack_blks(ngtcp2_conn * conn,size_t n)1414 static int conn_ensure_ack_blks(ngtcp2_conn *conn, size_t n) {
1415   ngtcp2_frame *fr;
1416   size_t max = conn->tx.max_ack_blks;
1417 
1418   if (n <= max) {
1419     return 0;
1420   }
1421 
1422   max *= 2;
1423 
1424   assert(max >= n);
1425 
1426   fr = ngtcp2_mem_realloc(conn->mem, conn->tx.ack,
1427                           sizeof(ngtcp2_ack) + sizeof(ngtcp2_ack_blk) * max);
1428   if (fr == NULL) {
1429     return NGTCP2_ERR_NOMEM;
1430   }
1431 
1432   conn->tx.ack = fr;
1433   conn->tx.max_ack_blks = max;
1434 
1435   return 0;
1436 }
1437 
1438 /*
1439  * conn_compute_ack_delay computes ACK delay for outgoing protected
1440  * ACK.
1441  */
conn_compute_ack_delay(ngtcp2_conn * conn)1442 static ngtcp2_duration conn_compute_ack_delay(ngtcp2_conn *conn) {
1443   return ngtcp2_min(conn->local.transport_params.max_ack_delay,
1444                     conn->cstat.smoothed_rtt / 8);
1445 }
1446 
1447 /*
1448  * conn_create_ack_frame creates ACK frame, and assigns its pointer to
1449  * |*pfr| if there are any received packets to acknowledge.  If there
1450  * are no packets to acknowledge, this function returns 0, and |*pfr|
1451  * is untouched.  The caller is advised to set |*pfr| to NULL before
1452  * calling this function, and check it after this function returns.
1453  * If |nodelay| is nonzero, delayed ACK timer is ignored.
1454  *
1455  * The memory for ACK frame is dynamically allocated by this function.
1456  * A caller is responsible to free it.
1457  *
1458  * Call ngtcp2_acktr_commit_ack after a created ACK frame is
1459  * successfully serialized into a packet.
1460  *
1461  * This function returns 0 if it succeeds, or one of the following
1462  * negative error codes:
1463  *
1464  * NGTCP2_ERR_NOMEM
1465  *     Out of memory.
1466  */
conn_create_ack_frame(ngtcp2_conn * conn,ngtcp2_frame ** pfr,ngtcp2_pktns * pktns,uint8_t type,ngtcp2_tstamp ts,ngtcp2_duration ack_delay,uint64_t ack_delay_exponent)1467 static int conn_create_ack_frame(ngtcp2_conn *conn, ngtcp2_frame **pfr,
1468                                  ngtcp2_pktns *pktns, uint8_t type,
1469                                  ngtcp2_tstamp ts, ngtcp2_duration ack_delay,
1470                                  uint64_t ack_delay_exponent) {
1471   /* TODO Measure an actual size of ACK blocks to find the best
1472      default value. */
1473   const size_t initial_max_ack_blks = 8;
1474   int64_t last_pkt_num;
1475   ngtcp2_acktr *acktr = &pktns->acktr;
1476   ngtcp2_ack_blk *blk;
1477   ngtcp2_ksl_it it;
1478   ngtcp2_acktr_entry *rpkt;
1479   ngtcp2_ack *ack;
1480   size_t blk_idx;
1481   ngtcp2_tstamp largest_ack_ts;
1482   int rv;
1483 
1484   if (acktr->flags & NGTCP2_ACKTR_FLAG_IMMEDIATE_ACK) {
1485     ack_delay = 0;
1486   }
1487 
1488   if (!ngtcp2_acktr_require_active_ack(acktr, ack_delay, ts)) {
1489     return 0;
1490   }
1491 
1492   it = ngtcp2_acktr_get(acktr);
1493   if (ngtcp2_ksl_it_end(&it)) {
1494     ngtcp2_acktr_commit_ack(acktr);
1495     return 0;
1496   }
1497 
1498   if (conn->tx.ack == NULL) {
1499     conn->tx.ack = ngtcp2_mem_malloc(
1500         conn->mem,
1501         sizeof(ngtcp2_ack) + sizeof(ngtcp2_ack_blk) * initial_max_ack_blks);
1502     if (conn->tx.ack == NULL) {
1503       return NGTCP2_ERR_NOMEM;
1504     }
1505     conn->tx.max_ack_blks = initial_max_ack_blks;
1506   }
1507 
1508   ack = &conn->tx.ack->ack;
1509 
1510   if (pktns->rx.ecn.ect0 || pktns->rx.ecn.ect1 || pktns->rx.ecn.ce) {
1511     ack->type = NGTCP2_FRAME_ACK_ECN;
1512     ack->ecn.ect0 = pktns->rx.ecn.ect0;
1513     ack->ecn.ect1 = pktns->rx.ecn.ect1;
1514     ack->ecn.ce = pktns->rx.ecn.ce;
1515   } else {
1516     ack->type = NGTCP2_FRAME_ACK;
1517   }
1518   ack->num_blks = 0;
1519 
1520   rpkt = ngtcp2_ksl_it_get(&it);
1521 
1522   if (rpkt->pkt_num == pktns->rx.max_pkt_num) {
1523     last_pkt_num = rpkt->pkt_num - (int64_t)(rpkt->len - 1);
1524     largest_ack_ts = rpkt->tstamp;
1525     ack->largest_ack = rpkt->pkt_num;
1526     ack->first_ack_blklen = rpkt->len - 1;
1527 
1528     ngtcp2_ksl_it_next(&it);
1529   } else {
1530     assert(rpkt->pkt_num < pktns->rx.max_pkt_num);
1531 
1532     last_pkt_num = pktns->rx.max_pkt_num;
1533     largest_ack_ts = pktns->rx.max_pkt_ts;
1534     ack->largest_ack = pktns->rx.max_pkt_num;
1535     ack->first_ack_blklen = 0;
1536   }
1537 
1538   if (type == NGTCP2_PKT_SHORT) {
1539     ack->ack_delay_unscaled = ts - largest_ack_ts;
1540     ack->ack_delay = ack->ack_delay_unscaled / NGTCP2_MICROSECONDS /
1541                      (1ULL << ack_delay_exponent);
1542   } else {
1543     ack->ack_delay_unscaled = 0;
1544     ack->ack_delay = 0;
1545   }
1546 
1547   for (; !ngtcp2_ksl_it_end(&it); ngtcp2_ksl_it_next(&it)) {
1548     if (ack->num_blks == NGTCP2_MAX_ACK_BLKS) {
1549       break;
1550     }
1551 
1552     rpkt = ngtcp2_ksl_it_get(&it);
1553 
1554     blk_idx = ack->num_blks++;
1555     rv = conn_ensure_ack_blks(conn, ack->num_blks);
1556     if (rv != 0) {
1557       return rv;
1558     }
1559     ack = &conn->tx.ack->ack;
1560     blk = &ack->blks[blk_idx];
1561     blk->gap = (uint64_t)(last_pkt_num - rpkt->pkt_num - 2);
1562     blk->blklen = rpkt->len - 1;
1563 
1564     last_pkt_num = rpkt->pkt_num - (int64_t)(rpkt->len - 1);
1565   }
1566 
1567   /* TODO Just remove entries which cannot fit into a single ACK frame
1568      for now. */
1569   if (!ngtcp2_ksl_it_end(&it)) {
1570     ngtcp2_acktr_forget(acktr, ngtcp2_ksl_it_get(&it));
1571   }
1572 
1573   *pfr = conn->tx.ack;
1574 
1575   return 0;
1576 }
1577 
1578 /*
1579  * conn_ppe_write_frame writes |fr| to |ppe|.  If |hd_logged| is not
1580  * NULL and |*hd_logged| is zero, packet header is logged, and 1 is
1581  * assigned to |*hd_logged|.
1582  *
1583  * This function returns 0 if it succeeds, or one of the following
1584  * negative error codes:
1585  *
1586  * NGTCP2_ERR_NOBUF
1587  *     Buffer is too small.
1588  */
conn_ppe_write_frame_hd_log(ngtcp2_conn * conn,ngtcp2_ppe * ppe,int * hd_logged,const ngtcp2_pkt_hd * hd,ngtcp2_frame * fr)1589 static int conn_ppe_write_frame_hd_log(ngtcp2_conn *conn, ngtcp2_ppe *ppe,
1590                                        int *hd_logged, const ngtcp2_pkt_hd *hd,
1591                                        ngtcp2_frame *fr) {
1592   int rv;
1593 
1594   rv = ngtcp2_ppe_encode_frame(ppe, fr);
1595   if (rv != 0) {
1596     assert(NGTCP2_ERR_NOBUF == rv);
1597     return rv;
1598   }
1599 
1600   if (hd_logged && !*hd_logged) {
1601     *hd_logged = 1;
1602     ngtcp2_log_tx_pkt_hd(&conn->log, hd);
1603     ngtcp2_qlog_pkt_sent_start(&conn->qlog);
1604   }
1605 
1606   ngtcp2_log_tx_fr(&conn->log, hd, fr);
1607   ngtcp2_qlog_write_frame(&conn->qlog, fr);
1608 
1609   return 0;
1610 }
1611 
1612 /*
1613  * conn_ppe_write_frame writes |fr| to |ppe|.
1614  *
1615  * This function returns 0 if it succeeds, or one of the following
1616  * negative error codes:
1617  *
1618  * NGTCP2_ERR_NOBUF
1619  *     Buffer is too small.
1620  */
conn_ppe_write_frame(ngtcp2_conn * conn,ngtcp2_ppe * ppe,const ngtcp2_pkt_hd * hd,ngtcp2_frame * fr)1621 static int conn_ppe_write_frame(ngtcp2_conn *conn, ngtcp2_ppe *ppe,
1622                                 const ngtcp2_pkt_hd *hd, ngtcp2_frame *fr) {
1623   return conn_ppe_write_frame_hd_log(conn, ppe, NULL, hd, fr);
1624 }
1625 
1626 /*
1627  * conn_on_pkt_sent is called when new non-ACK-only packet is sent.
1628  *
1629  * This function returns 0 if it succeeds, or one of the following
1630  * negative error codes:
1631  *
1632  * NGTCP2_ERR_NOMEM
1633  *     Out of memory
1634  */
conn_on_pkt_sent(ngtcp2_conn * conn,ngtcp2_rtb * rtb,ngtcp2_rtb_entry * ent)1635 static int conn_on_pkt_sent(ngtcp2_conn *conn, ngtcp2_rtb *rtb,
1636                             ngtcp2_rtb_entry *ent) {
1637   int rv;
1638 
1639   /* This function implements OnPacketSent, but it handles only
1640      non-ACK-only packet. */
1641   rv = ngtcp2_rtb_add(rtb, ent, &conn->cstat);
1642   if (rv != 0) {
1643     return rv;
1644   }
1645 
1646   if (ent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
1647     conn->cstat.last_tx_pkt_ts[rtb->pktns_id] = ent->ts;
1648   }
1649 
1650   ngtcp2_conn_set_loss_detection_timer(conn, ent->ts);
1651 
1652   return 0;
1653 }
1654 
1655 /*
1656  * pktns_select_pkt_numlen selects shortest packet number encoding for
1657  * the next packet number based on the largest acknowledged packet
1658  * number.  It returns the number of bytes to encode the packet
1659  * number.
1660  */
pktns_select_pkt_numlen(ngtcp2_pktns * pktns)1661 static size_t pktns_select_pkt_numlen(ngtcp2_pktns *pktns) {
1662   int64_t pkt_num = pktns->tx.last_pkt_num + 1;
1663   ngtcp2_rtb *rtb = &pktns->rtb;
1664   int64_t n = pkt_num - rtb->largest_acked_tx_pkt_num;
1665 
1666   if (NGTCP2_MAX_PKT_NUM / 2 < n) {
1667     return 4;
1668   }
1669 
1670   n = n * 2 - 1;
1671 
1672   if (n > 0xffffff) {
1673     return 4;
1674   }
1675   if (n > 0xffff) {
1676     return 3;
1677   }
1678   if (n > 0xff) {
1679     return 2;
1680   }
1681   return 1;
1682 }
1683 
1684 /*
1685  * conn_cwnd_is_zero returns nonzero if the number of bytes the local
1686  * endpoint can sent at this time is zero.
1687  */
conn_cwnd_is_zero(ngtcp2_conn * conn)1688 static uint64_t conn_cwnd_is_zero(ngtcp2_conn *conn) {
1689   uint64_t bytes_in_flight = conn->cstat.bytes_in_flight;
1690   uint64_t cwnd =
1691       conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE)
1692           ? ngtcp2_cc_compute_initcwnd(conn->cstat.max_udp_payload_size)
1693           : conn->cstat.cwnd;
1694 
1695   return bytes_in_flight >= cwnd;
1696 }
1697 
1698 /*
1699  * conn_retry_early_payloadlen returns the estimated wire length of
1700  * the first STREAM frame of 0-RTT packet which should be
1701  * retransmitted due to Retry packet.
1702  */
conn_retry_early_payloadlen(ngtcp2_conn * conn)1703 static uint64_t conn_retry_early_payloadlen(ngtcp2_conn *conn) {
1704   ngtcp2_frame_chain *frc;
1705   ngtcp2_strm *strm;
1706   uint64_t len;
1707 
1708   if (conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) {
1709     return 0;
1710   }
1711 
1712   for (; !ngtcp2_pq_empty(&conn->tx.strmq);) {
1713     strm = ngtcp2_conn_tx_strmq_top(conn);
1714     if (ngtcp2_strm_streamfrq_empty(strm)) {
1715       ngtcp2_conn_tx_strmq_pop(conn);
1716       continue;
1717     }
1718 
1719     frc = ngtcp2_strm_streamfrq_top(strm);
1720 
1721     len = ngtcp2_vec_len(frc->fr.stream.data, frc->fr.stream.datacnt) +
1722           NGTCP2_STREAM_OVERHEAD;
1723 
1724     /* Take the min because in conn_should_pad_pkt we take max in
1725        order to deal with unbreakable DATAGRAM. */
1726     return ngtcp2_min(len, NGTCP2_MIN_COALESCED_PAYLOADLEN);
1727   }
1728 
1729   return 0;
1730 }
1731 
conn_cryptofrq_clear(ngtcp2_conn * conn,ngtcp2_pktns * pktns)1732 static void conn_cryptofrq_clear(ngtcp2_conn *conn, ngtcp2_pktns *pktns) {
1733   ngtcp2_frame_chain *frc;
1734   ngtcp2_ksl_it it;
1735 
1736   for (it = ngtcp2_ksl_begin(&pktns->crypto.tx.frq); !ngtcp2_ksl_it_end(&it);
1737        ngtcp2_ksl_it_next(&it)) {
1738     frc = ngtcp2_ksl_it_get(&it);
1739     ngtcp2_frame_chain_del(frc, conn->mem);
1740   }
1741   ngtcp2_ksl_clear(&pktns->crypto.tx.frq);
1742 }
1743 
1744 /*
1745  * conn_cryptofrq_unacked_offset returns the CRYPTO frame offset by
1746  * taking into account acknowledged offset.  If there is no data to
1747  * send, this function returns (uint64_t)-1.
1748  */
conn_cryptofrq_unacked_offset(ngtcp2_conn * conn,ngtcp2_pktns * pktns)1749 static uint64_t conn_cryptofrq_unacked_offset(ngtcp2_conn *conn,
1750                                               ngtcp2_pktns *pktns) {
1751   ngtcp2_frame_chain *frc;
1752   ngtcp2_crypto *fr;
1753   ngtcp2_range gap;
1754   ngtcp2_rtb *rtb = &pktns->rtb;
1755   ngtcp2_ksl_it it;
1756   uint64_t datalen;
1757 
1758   (void)conn;
1759 
1760   for (it = ngtcp2_ksl_begin(&pktns->crypto.tx.frq); !ngtcp2_ksl_it_end(&it);
1761        ngtcp2_ksl_it_next(&it)) {
1762     frc = ngtcp2_ksl_it_get(&it);
1763     fr = &frc->fr.crypto;
1764 
1765     gap = ngtcp2_strm_get_unacked_range_after(rtb->crypto, fr->offset);
1766 
1767     datalen = ngtcp2_vec_len(fr->data, fr->datacnt);
1768 
1769     if (gap.begin <= fr->offset) {
1770       return fr->offset;
1771     }
1772     if (gap.begin < fr->offset + datalen) {
1773       return gap.begin;
1774     }
1775   }
1776 
1777   return (uint64_t)-1;
1778 }
1779 
conn_cryptofrq_unacked_pop(ngtcp2_conn * conn,ngtcp2_pktns * pktns,ngtcp2_frame_chain ** pfrc)1780 static int conn_cryptofrq_unacked_pop(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
1781                                       ngtcp2_frame_chain **pfrc) {
1782   ngtcp2_frame_chain *frc, *nfrc;
1783   ngtcp2_crypto *fr, *nfr;
1784   uint64_t offset, end_offset;
1785   size_t idx, end_idx;
1786   uint64_t base_offset, end_base_offset;
1787   ngtcp2_range gap;
1788   ngtcp2_rtb *rtb = &pktns->rtb;
1789   ngtcp2_vec *v;
1790   int rv;
1791   ngtcp2_ksl_it it;
1792 
1793   *pfrc = NULL;
1794 
1795   for (it = ngtcp2_ksl_begin(&pktns->crypto.tx.frq); !ngtcp2_ksl_it_end(&it);) {
1796     frc = ngtcp2_ksl_it_get(&it);
1797     fr = &frc->fr.crypto;
1798 
1799     ngtcp2_ksl_remove_hint(&pktns->crypto.tx.frq, &it, &it, &fr->offset);
1800 
1801     idx = 0;
1802     offset = fr->offset;
1803     base_offset = 0;
1804 
1805     gap = ngtcp2_strm_get_unacked_range_after(rtb->crypto, offset);
1806     if (gap.begin < offset) {
1807       gap.begin = offset;
1808     }
1809 
1810     for (; idx < fr->datacnt && offset < gap.begin; ++idx) {
1811       v = &fr->data[idx];
1812       if (offset + v->len > gap.begin) {
1813         base_offset = gap.begin - offset;
1814         break;
1815       }
1816 
1817       offset += v->len;
1818     }
1819 
1820     if (idx == fr->datacnt) {
1821       ngtcp2_frame_chain_del(frc, conn->mem);
1822       continue;
1823     }
1824 
1825     assert(gap.begin == offset + base_offset);
1826 
1827     end_idx = idx;
1828     end_offset = offset;
1829     end_base_offset = 0;
1830 
1831     for (; end_idx < fr->datacnt; ++end_idx) {
1832       v = &fr->data[end_idx];
1833       if (end_offset + v->len > gap.end) {
1834         end_base_offset = gap.end - end_offset;
1835         break;
1836       }
1837 
1838       end_offset += v->len;
1839     }
1840 
1841     if (fr->offset == offset && base_offset == 0 && fr->datacnt == end_idx) {
1842       *pfrc = frc;
1843       return 0;
1844     }
1845 
1846     if (fr->datacnt == end_idx) {
1847       memmove(fr->data, fr->data + idx, sizeof(fr->data[0]) * (end_idx - idx));
1848 
1849       assert(fr->data[0].len > base_offset);
1850 
1851       fr->offset = offset + base_offset;
1852       fr->datacnt = end_idx - idx;
1853       fr->data[0].base += base_offset;
1854       fr->data[0].len -= (size_t)base_offset;
1855 
1856       *pfrc = frc;
1857       return 0;
1858     }
1859 
1860     rv = ngtcp2_frame_chain_crypto_datacnt_new(&nfrc, fr->datacnt - end_idx,
1861                                                conn->mem);
1862     if (rv != 0) {
1863       ngtcp2_frame_chain_del(frc, conn->mem);
1864       return rv;
1865     }
1866 
1867     nfr = &nfrc->fr.crypto;
1868     nfr->type = NGTCP2_FRAME_CRYPTO;
1869     memcpy(nfr->data, fr->data + end_idx,
1870            sizeof(nfr->data[0]) * (fr->datacnt - end_idx));
1871 
1872     assert(nfr->data[0].len > end_base_offset);
1873 
1874     nfr->offset = end_offset + end_base_offset;
1875     nfr->datacnt = fr->datacnt - end_idx;
1876     nfr->data[0].base += end_base_offset;
1877     nfr->data[0].len -= (size_t)end_base_offset;
1878 
1879     rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL, &nfr->offset, nfrc);
1880     if (rv != 0) {
1881       assert(ngtcp2_err_is_fatal(rv));
1882       ngtcp2_frame_chain_del(nfrc, conn->mem);
1883       ngtcp2_frame_chain_del(frc, conn->mem);
1884       return rv;
1885     }
1886 
1887     if (end_base_offset) {
1888       ++end_idx;
1889     }
1890 
1891     memmove(fr->data, fr->data + idx, sizeof(fr->data[0]) * (end_idx - idx));
1892 
1893     assert(fr->data[0].len > base_offset);
1894 
1895     fr->offset = offset + base_offset;
1896     fr->datacnt = end_idx - idx;
1897     if (end_base_offset) {
1898       assert(fr->data[fr->datacnt - 1].len > end_base_offset);
1899       fr->data[fr->datacnt - 1].len = (size_t)end_base_offset;
1900     }
1901     fr->data[0].base += base_offset;
1902     fr->data[0].len -= (size_t)base_offset;
1903 
1904     *pfrc = frc;
1905     return 0;
1906   }
1907 
1908   return 0;
1909 }
conn_cryptofrq_pop(ngtcp2_conn * conn,ngtcp2_frame_chain ** pfrc,ngtcp2_pktns * pktns,size_t left)1910 static int conn_cryptofrq_pop(ngtcp2_conn *conn, ngtcp2_frame_chain **pfrc,
1911                               ngtcp2_pktns *pktns, size_t left) {
1912   ngtcp2_crypto *fr, *nfr;
1913   ngtcp2_frame_chain *frc, *nfrc;
1914   int rv;
1915   size_t nmerged;
1916   uint64_t datalen;
1917   ngtcp2_vec a[NGTCP2_MAX_CRYPTO_DATACNT];
1918   ngtcp2_vec b[NGTCP2_MAX_CRYPTO_DATACNT];
1919   size_t acnt, bcnt;
1920   ngtcp2_ksl_it it;
1921 
1922   rv = conn_cryptofrq_unacked_pop(conn, pktns, &frc);
1923   if (rv != 0) {
1924     return rv;
1925   }
1926   if (frc == NULL) {
1927     *pfrc = NULL;
1928     return 0;
1929   }
1930 
1931   fr = &frc->fr.crypto;
1932   datalen = ngtcp2_vec_len(fr->data, fr->datacnt);
1933 
1934   if (datalen > left) {
1935     ngtcp2_vec_copy(a, fr->data, fr->datacnt);
1936     acnt = fr->datacnt;
1937 
1938     bcnt = 0;
1939     ngtcp2_vec_split(a, &acnt, b, &bcnt, left, NGTCP2_MAX_CRYPTO_DATACNT);
1940 
1941     assert(acnt > 0);
1942     assert(bcnt > 0);
1943 
1944     rv = ngtcp2_frame_chain_crypto_datacnt_new(&nfrc, bcnt, conn->mem);
1945     if (rv != 0) {
1946       assert(ngtcp2_err_is_fatal(rv));
1947       ngtcp2_frame_chain_del(frc, conn->mem);
1948       return rv;
1949     }
1950 
1951     nfr = &nfrc->fr.crypto;
1952     nfr->type = NGTCP2_FRAME_CRYPTO;
1953     nfr->offset = fr->offset + left;
1954     nfr->datacnt = bcnt;
1955     ngtcp2_vec_copy(nfr->data, b, bcnt);
1956 
1957     rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL, &nfr->offset, nfrc);
1958     if (rv != 0) {
1959       assert(ngtcp2_err_is_fatal(rv));
1960       ngtcp2_frame_chain_del(nfrc, conn->mem);
1961       ngtcp2_frame_chain_del(frc, conn->mem);
1962       return rv;
1963     }
1964 
1965     rv = ngtcp2_frame_chain_crypto_datacnt_new(&nfrc, acnt, conn->mem);
1966     if (rv != 0) {
1967       assert(ngtcp2_err_is_fatal(rv));
1968       ngtcp2_frame_chain_del(frc, conn->mem);
1969       return rv;
1970     }
1971 
1972     nfr = &nfrc->fr.crypto;
1973     *nfr = *fr;
1974     nfr->datacnt = acnt;
1975     ngtcp2_vec_copy(nfr->data, a, acnt);
1976 
1977     ngtcp2_frame_chain_del(frc, conn->mem);
1978 
1979     *pfrc = nfrc;
1980 
1981     return 0;
1982   }
1983 
1984   left -= (size_t)datalen;
1985 
1986   ngtcp2_vec_copy(a, fr->data, fr->datacnt);
1987   acnt = fr->datacnt;
1988 
1989   for (; left && ngtcp2_ksl_len(&pktns->crypto.tx.frq);) {
1990     it = ngtcp2_ksl_begin(&pktns->crypto.tx.frq);
1991     nfrc = ngtcp2_ksl_it_get(&it);
1992     nfr = &nfrc->fr.crypto;
1993 
1994     if (nfr->offset != fr->offset + datalen) {
1995       assert(fr->offset + datalen < nfr->offset);
1996       break;
1997     }
1998 
1999     rv = conn_cryptofrq_unacked_pop(conn, pktns, &nfrc);
2000     if (rv != 0) {
2001       assert(ngtcp2_err_is_fatal(rv));
2002       ngtcp2_frame_chain_del(frc, conn->mem);
2003       return rv;
2004     }
2005     if (nfrc == NULL) {
2006       break;
2007     }
2008 
2009     nfr = &nfrc->fr.crypto;
2010 
2011     nmerged = ngtcp2_vec_merge(a, &acnt, nfr->data, &nfr->datacnt, left,
2012                                NGTCP2_MAX_CRYPTO_DATACNT);
2013     if (nmerged == 0) {
2014       rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL, &nfr->offset, nfrc);
2015       if (rv != 0) {
2016         assert(ngtcp2_err_is_fatal(rv));
2017         ngtcp2_frame_chain_del(nfrc, conn->mem);
2018         ngtcp2_frame_chain_del(frc, conn->mem);
2019         return rv;
2020       }
2021       break;
2022     }
2023 
2024     datalen += nmerged;
2025     left -= nmerged;
2026 
2027     if (nfr->datacnt == 0) {
2028       ngtcp2_frame_chain_del(nfrc, conn->mem);
2029       continue;
2030     }
2031 
2032     nfr->offset += nmerged;
2033 
2034     rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL, &nfr->offset, nfrc);
2035     if (rv != 0) {
2036       ngtcp2_frame_chain_del(nfrc, conn->mem);
2037       ngtcp2_frame_chain_del(frc, conn->mem);
2038       return rv;
2039     }
2040 
2041     break;
2042   }
2043 
2044   if (acnt == fr->datacnt) {
2045     assert(acnt > 0);
2046     fr->data[acnt - 1] = a[acnt - 1];
2047 
2048     *pfrc = frc;
2049     return 0;
2050   }
2051 
2052   assert(acnt > fr->datacnt);
2053 
2054   rv = ngtcp2_frame_chain_crypto_datacnt_new(&nfrc, acnt, conn->mem);
2055   if (rv != 0) {
2056     ngtcp2_frame_chain_del(frc, conn->mem);
2057     return rv;
2058   }
2059 
2060   nfr = &nfrc->fr.crypto;
2061   *nfr = *fr;
2062   nfr->datacnt = acnt;
2063   ngtcp2_vec_copy(nfr->data, a, acnt);
2064 
2065   ngtcp2_frame_chain_del(frc, conn->mem);
2066 
2067   *pfrc = nfrc;
2068 
2069   return 0;
2070 }
2071 
2072 /*
2073  * conn_verify_dcid verifies that destination connection ID in |hd| is
2074  * valid for the connection.  If it is successfully verified and the
2075  * remote endpoint uses new DCID in the packet, nonzero value is
2076  * assigned to |*pnew_cid_used| if it is not NULL.  Otherwise 0 is
2077  * assigned to it.
2078  *
2079  * This function returns 0 if it succeeds, or one of the following
2080  * negative error codes:
2081  *
2082  * NGTCP2_ERR_NOMEM
2083  *     Out of memory.
2084  * NGTCP2_ERR_INVALID_ARGUMENT
2085  *     |dcid| is not known to the local endpoint.
2086  */
conn_verify_dcid(ngtcp2_conn * conn,int * pnew_cid_used,const ngtcp2_pkt_hd * hd)2087 static int conn_verify_dcid(ngtcp2_conn *conn, int *pnew_cid_used,
2088                             const ngtcp2_pkt_hd *hd) {
2089   ngtcp2_ksl_it it;
2090   ngtcp2_scid *scid;
2091   int rv;
2092 
2093   it = ngtcp2_ksl_lower_bound(&conn->scid.set, &hd->dcid);
2094   if (ngtcp2_ksl_it_end(&it)) {
2095     return NGTCP2_ERR_INVALID_ARGUMENT;
2096   }
2097 
2098   scid = ngtcp2_ksl_it_get(&it);
2099   if (!ngtcp2_cid_eq(&scid->cid, &hd->dcid)) {
2100     return NGTCP2_ERR_INVALID_ARGUMENT;
2101   }
2102 
2103   if (!(scid->flags & NGTCP2_SCID_FLAG_USED)) {
2104     scid->flags |= NGTCP2_SCID_FLAG_USED;
2105 
2106     if (scid->pe.index == NGTCP2_PQ_BAD_INDEX) {
2107       rv = ngtcp2_pq_push(&conn->scid.used, &scid->pe);
2108       if (rv != 0) {
2109         return rv;
2110       }
2111     }
2112 
2113     if (pnew_cid_used) {
2114       *pnew_cid_used = 1;
2115     }
2116   } else if (pnew_cid_used) {
2117     *pnew_cid_used = 0;
2118   }
2119 
2120   return 0;
2121 }
2122 
2123 /*
2124  * conn_should_pad_pkt returns nonzero if the packet should be padded.
2125  * |type| is the type of packet.  |left| is the space left in packet
2126  * buffer.  |write_datalen| is the number of bytes which will be sent
2127  * in the next, coalesced 0-RTT or Short packet.
2128  */
conn_should_pad_pkt(ngtcp2_conn * conn,uint8_t type,size_t left,uint64_t write_datalen,int ack_eliciting,int require_padding)2129 static int conn_should_pad_pkt(ngtcp2_conn *conn, uint8_t type, size_t left,
2130                                uint64_t write_datalen, int ack_eliciting,
2131                                int require_padding) {
2132   uint64_t min_payloadlen;
2133 
2134   if (type == NGTCP2_PKT_INITIAL) {
2135     if (conn->server) {
2136       if (!ack_eliciting) {
2137         return 0;
2138       }
2139 
2140       if (conn->hs_pktns->crypto.tx.ckm &&
2141           (conn->hs_pktns->rtb.probe_pkt_left ||
2142            ngtcp2_ksl_len(&conn->hs_pktns->crypto.tx.frq) ||
2143            !ngtcp2_acktr_empty(&conn->hs_pktns->acktr))) {
2144         /* If we have something to send in Handshake packet, then add
2145            PADDING in Handshake packet. */
2146         min_payloadlen = NGTCP2_MIN_COALESCED_PAYLOADLEN;
2147       } else {
2148         return 1;
2149       }
2150     } else {
2151       if (conn->hs_pktns->crypto.tx.ckm &&
2152           (conn->hs_pktns->rtb.probe_pkt_left ||
2153            ngtcp2_ksl_len(&conn->hs_pktns->crypto.tx.frq) ||
2154            !ngtcp2_acktr_empty(&conn->hs_pktns->acktr))) {
2155         /* If we have something to send in Handshake packet, then add
2156            PADDING in Handshake packet. */
2157         min_payloadlen = NGTCP2_MIN_COALESCED_PAYLOADLEN;
2158       } else if ((!conn->early.ckm && !conn->pktns.crypto.tx.ckm) ||
2159                  write_datalen == 0) {
2160         return 1;
2161       } else {
2162         /* If we have something to send in 0RTT or Short packet, then
2163            add PADDING in that packet.  Take maximum in case that
2164            write_datalen includes DATAGRAM which cannot be split. */
2165         min_payloadlen =
2166             ngtcp2_max(write_datalen, NGTCP2_MIN_COALESCED_PAYLOADLEN);
2167       }
2168     }
2169   } else {
2170     assert(type == NGTCP2_PKT_HANDSHAKE);
2171 
2172     if (!require_padding) {
2173       return 0;
2174     }
2175 
2176     if (!conn->pktns.crypto.tx.ckm || write_datalen == 0) {
2177       return 1;
2178     }
2179 
2180     min_payloadlen = ngtcp2_max(write_datalen, NGTCP2_MIN_COALESCED_PAYLOADLEN);
2181   }
2182 
2183   /* TODO the next packet type should be taken into account */
2184   return left <
2185          /* TODO Assuming that pkt_num is encoded in 1 byte. */
2186          NGTCP2_MIN_LONG_HEADERLEN + conn->dcid.current.cid.datalen +
2187              conn->oscid.datalen + 1 /* payloadlen bytes - 1 */ +
2188              min_payloadlen + NGTCP2_MAX_AEAD_OVERHEAD;
2189 }
2190 
conn_restart_timer_on_write(ngtcp2_conn * conn,ngtcp2_tstamp ts)2191 static void conn_restart_timer_on_write(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2192   conn->idle_ts = ts;
2193   conn->flags &= (uint16_t)~NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE;
2194 }
2195 
conn_restart_timer_on_read(ngtcp2_conn * conn,ngtcp2_tstamp ts)2196 static void conn_restart_timer_on_read(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2197   conn->idle_ts = ts;
2198   conn->flags |= NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE;
2199 }
2200 
2201 /*
2202  * conn_keep_alive_enabled returns nonzero if keep-alive is enabled.
2203  */
conn_keep_alive_enabled(ngtcp2_conn * conn)2204 static int conn_keep_alive_enabled(ngtcp2_conn *conn) {
2205   return conn->keep_alive.last_ts != UINT64_MAX && conn->keep_alive.timeout;
2206 }
2207 
2208 /*
2209  * conn_keep_alive_expired returns nonzero if keep-alive timer has
2210  * expired.
2211  */
conn_keep_alive_expired(ngtcp2_conn * conn,ngtcp2_tstamp ts)2212 static int conn_keep_alive_expired(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2213   return conn_keep_alive_enabled(conn) &&
2214          conn->keep_alive.last_ts + conn->keep_alive.timeout <= ts;
2215 }
2216 
2217 /*
2218  * conn_keep_alive_expiry returns the expiry time of keep-alive timer.
2219  */
conn_keep_alive_expiry(ngtcp2_conn * conn)2220 static ngtcp2_tstamp conn_keep_alive_expiry(ngtcp2_conn *conn) {
2221   if ((conn->flags & NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED) ||
2222       !conn_keep_alive_enabled(conn)) {
2223     return UINT64_MAX;
2224   }
2225 
2226   return conn->keep_alive.last_ts + conn->keep_alive.timeout;
2227 }
2228 
2229 /*
2230  * conn_cancel_expired_keep_alive_timer cancels the expired keep-alive
2231  * timer.
2232  */
conn_cancel_expired_keep_alive_timer(ngtcp2_conn * conn,ngtcp2_tstamp ts)2233 static void conn_cancel_expired_keep_alive_timer(ngtcp2_conn *conn,
2234                                                  ngtcp2_tstamp ts) {
2235   if (!(conn->flags & NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED) &&
2236       conn_keep_alive_expired(conn, ts)) {
2237     conn->flags |= NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED;
2238   }
2239 }
2240 
2241 /*
2242  * conn_update_keep_alive_last_ts updates the base time point of
2243  * keep-alive timer.
2244  */
conn_update_keep_alive_last_ts(ngtcp2_conn * conn,ngtcp2_tstamp ts)2245 static void conn_update_keep_alive_last_ts(ngtcp2_conn *conn,
2246                                            ngtcp2_tstamp ts) {
2247   conn->keep_alive.last_ts = ts;
2248   conn->flags &= (uint16_t)~NGTCP2_CONN_FLAG_KEEP_ALIVE_CANCELLED;
2249 }
2250 
ngtcp2_conn_set_keep_alive_timeout(ngtcp2_conn * conn,ngtcp2_duration timeout)2251 void ngtcp2_conn_set_keep_alive_timeout(ngtcp2_conn *conn,
2252                                         ngtcp2_duration timeout) {
2253   conn->keep_alive.timeout = timeout;
2254 }
2255 
2256 /*
2257  * NGTCP2_PKT_PACING_OVERHEAD defines overhead of userspace event
2258  * loop.  Packet pacing might require sub milliseconds packet spacing,
2259  * but userspace event loop might not offer such precision.
2260  * Typically, if delay is 0.5 microseconds, the actual delay after
2261  * which we can send packet is well over 1 millisecond when event loop
2262  * is involved (which includes other stuff, like reading packets etc
2263  * in a typical single threaded use case).
2264  */
2265 #define NGTCP2_PKT_PACING_OVERHEAD (500 * NGTCP2_MICROSECONDS)
2266 
conn_cancel_expired_pkt_tx_timer(ngtcp2_conn * conn,ngtcp2_tstamp ts)2267 static void conn_cancel_expired_pkt_tx_timer(ngtcp2_conn *conn,
2268                                              ngtcp2_tstamp ts) {
2269   if (conn->tx.pacing.next_ts == UINT64_MAX) {
2270     return;
2271   }
2272 
2273   if (conn->tx.pacing.next_ts > ts + NGTCP2_PKT_PACING_OVERHEAD) {
2274     return;
2275   }
2276 
2277   conn->tx.pacing.next_ts = UINT64_MAX;
2278 }
2279 
conn_pacing_pkt_tx_allowed(ngtcp2_conn * conn,ngtcp2_tstamp ts)2280 static int conn_pacing_pkt_tx_allowed(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2281   return conn->tx.pacing.next_ts == UINT64_MAX ||
2282          conn->tx.pacing.next_ts <= ts + NGTCP2_PKT_PACING_OVERHEAD;
2283 }
2284 
conn_pkt_flags(ngtcp2_conn * conn)2285 static uint8_t conn_pkt_flags(ngtcp2_conn *conn) {
2286   if (conn->remote.transport_params.grease_quic_bit &&
2287       (conn->flags & NGTCP2_CONN_FLAG_CLEAR_FIXED_BIT)) {
2288     return NGTCP2_PKT_FLAG_FIXED_BIT_CLEAR;
2289   }
2290 
2291   return NGTCP2_PKT_FLAG_NONE;
2292 }
2293 
conn_pkt_flags_long(ngtcp2_conn * conn)2294 static uint8_t conn_pkt_flags_long(ngtcp2_conn *conn) {
2295   return NGTCP2_PKT_FLAG_LONG_FORM | conn_pkt_flags(conn);
2296 }
2297 
conn_pkt_flags_short(ngtcp2_conn * conn)2298 static uint8_t conn_pkt_flags_short(ngtcp2_conn *conn) {
2299   return (uint8_t)(conn_pkt_flags(conn) | ((conn->pktns.crypto.tx.ckm->flags &
2300                                             NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE)
2301                                                ? NGTCP2_PKT_FLAG_KEY_PHASE
2302                                                : NGTCP2_PKT_FLAG_NONE));
2303 }
2304 
2305 /* NGTCP2_WRITE_PKT_FLAG_NONE indicates that no flag is set. */
2306 #define NGTCP2_WRITE_PKT_FLAG_NONE 0x00
2307 /* NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING indicates that packet other
2308    than Initial packet should be padded.  Initial packet might be
2309    padded based on QUIC requirement regardless of this flag. */
2310 #define NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING 0x01
2311 /* NGTCP2_WRITE_PKT_FLAG_MORE indicates that more frames might come
2312    and it should be encoded into the current packet. */
2313 #define NGTCP2_WRITE_PKT_FLAG_MORE 0x02
2314 
2315 /*
2316  * conn_write_handshake_pkt writes handshake packet in the buffer
2317  * pointed by |dest| whose length is |destlen|.  |type| specifies long
2318  * packet type.  It should be either NGTCP2_PKT_INITIAL or
2319  * NGTCP2_PKT_HANDSHAKE_PKT.
2320  *
2321  * |write_datalen| is the minimum length of application data ready to
2322  * send in subsequent 0RTT or Short packet.
2323  *
2324  * This function returns the number of bytes written in |dest| if it
2325  * succeeds, or one of the following negative error codes:
2326  *
2327  * NGTCP2_ERR_NOMEM
2328  *     Out of memory.
2329  * NGTCP2_ERR_CALLBACK_FAILURE
2330  *     User-defined callback function failed.
2331  */
2332 static ngtcp2_ssize
conn_write_handshake_pkt(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint8_t type,uint8_t flags,uint64_t write_datalen,ngtcp2_tstamp ts)2333 conn_write_handshake_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi, uint8_t *dest,
2334                          size_t destlen, uint8_t type, uint8_t flags,
2335                          uint64_t write_datalen, ngtcp2_tstamp ts) {
2336   int rv;
2337   ngtcp2_ppe ppe;
2338   ngtcp2_pkt_hd hd;
2339   ngtcp2_frame_chain *frq = NULL, **pfrc = &frq;
2340   ngtcp2_frame_chain *nfrc;
2341   ngtcp2_frame *ackfr = NULL, lfr;
2342   ngtcp2_ssize spktlen;
2343   ngtcp2_crypto_cc cc;
2344   ngtcp2_rtb_entry *rtbent;
2345   ngtcp2_pktns *pktns;
2346   size_t left;
2347   uint8_t rtb_entry_flags = NGTCP2_RTB_ENTRY_FLAG_NONE;
2348   int require_padding = (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING) != 0;
2349   int pkt_empty = 1;
2350   int padded = 0;
2351   int hd_logged = 0;
2352   uint64_t crypto_offset;
2353   ngtcp2_ssize num_reclaimed;
2354 
2355   switch (type) {
2356   case NGTCP2_PKT_INITIAL:
2357     if (!conn->in_pktns) {
2358       return 0;
2359     }
2360     assert(conn->in_pktns->crypto.tx.ckm);
2361     pktns = conn->in_pktns;
2362     break;
2363   case NGTCP2_PKT_HANDSHAKE:
2364     if (!conn->hs_pktns || !conn->hs_pktns->crypto.tx.ckm) {
2365       return 0;
2366     }
2367     pktns = conn->hs_pktns;
2368     break;
2369   default:
2370     assert(0);
2371     abort();
2372   }
2373 
2374   cc.aead = pktns->crypto.ctx.aead;
2375   cc.hp = pktns->crypto.ctx.hp;
2376   cc.ckm = pktns->crypto.tx.ckm;
2377   cc.hp_ctx = pktns->crypto.tx.hp_ctx;
2378   cc.encrypt = conn->callbacks.encrypt;
2379   cc.hp_mask = conn->callbacks.hp_mask;
2380 
2381   ngtcp2_pkt_hd_init(&hd, conn_pkt_flags_long(conn), type,
2382                      &conn->dcid.current.cid, &conn->oscid,
2383                      pktns->tx.last_pkt_num + 1, pktns_select_pkt_numlen(pktns),
2384                      conn->version, 0);
2385 
2386   if (!conn->server && type == NGTCP2_PKT_INITIAL &&
2387       conn->local.settings.token.len) {
2388     hd.token = conn->local.settings.token;
2389   }
2390 
2391   ngtcp2_ppe_init(&ppe, dest, destlen, &cc);
2392 
2393   rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
2394   if (rv != 0) {
2395     assert(NGTCP2_ERR_NOBUF == rv);
2396     return 0;
2397   }
2398 
2399   if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
2400     return 0;
2401   }
2402 
2403   rv = conn_create_ack_frame(conn, &ackfr, pktns, type, ts,
2404                              /* ack_delay = */ 0,
2405                              NGTCP2_DEFAULT_ACK_DELAY_EXPONENT);
2406   if (rv != 0) {
2407     ngtcp2_frame_chain_list_del(frq, conn->mem);
2408     return rv;
2409   }
2410 
2411   if (ackfr) {
2412     rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, ackfr);
2413     if (rv != 0) {
2414       assert(NGTCP2_ERR_NOBUF == rv);
2415     } else {
2416       ngtcp2_acktr_commit_ack(&pktns->acktr);
2417       ngtcp2_acktr_add_ack(&pktns->acktr, hd.pkt_num, ackfr->ack.largest_ack);
2418       pkt_empty = 0;
2419     }
2420   }
2421 
2422   /* Server requires at least NGTCP2_MAX_UDP_PAYLOAD_SIZE bytes in
2423      order to send ack-eliciting Initial packet. */
2424   if (!conn->server || type != NGTCP2_PKT_INITIAL ||
2425       destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
2426   build_pkt:
2427     for (; ngtcp2_ksl_len(&pktns->crypto.tx.frq);) {
2428       left = ngtcp2_ppe_left(&ppe);
2429 
2430       crypto_offset = conn_cryptofrq_unacked_offset(conn, pktns);
2431       if (crypto_offset == (size_t)-1) {
2432         conn_cryptofrq_clear(conn, pktns);
2433         break;
2434       }
2435 
2436       left = ngtcp2_pkt_crypto_max_datalen(crypto_offset, left, left);
2437       if (left == (size_t)-1) {
2438         break;
2439       }
2440 
2441       rv = conn_cryptofrq_pop(conn, &nfrc, pktns, left);
2442       if (rv != 0) {
2443         assert(ngtcp2_err_is_fatal(rv));
2444         ngtcp2_frame_chain_list_del(frq, conn->mem);
2445         return rv;
2446       }
2447 
2448       if (nfrc == NULL) {
2449         break;
2450       }
2451 
2452       rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &nfrc->fr);
2453       if (rv != 0) {
2454         assert(0);
2455       }
2456 
2457       *pfrc = nfrc;
2458       pfrc = &(*pfrc)->next;
2459 
2460       pkt_empty = 0;
2461       rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
2462                          NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
2463     }
2464 
2465     if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2466         pktns->rtb.num_retransmittable && pktns->rtb.probe_pkt_left) {
2467       num_reclaimed = ngtcp2_rtb_reclaim_on_pto(&pktns->rtb, conn, pktns,
2468                                                 pktns->rtb.probe_pkt_left + 1);
2469       if (num_reclaimed < 0) {
2470         ngtcp2_frame_chain_list_del(frq, conn->mem);
2471         return rv;
2472       }
2473       if (num_reclaimed) {
2474         goto build_pkt;
2475       }
2476       /* We had pktns->rtb.num_retransmittable > 0 but the contents of
2477          those packets have been acknowledged (i.e., retransmission in
2478          another packet).  For server, in this case, we don't have to
2479          send any probe packet.  Client needs to send probe packets
2480          until it knows that server has completed address validation or
2481          handshake has been confirmed. */
2482       if (pktns->rtb.num_retransmittable == 0 &&
2483           (conn->server ||
2484            (conn->flags & (NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED |
2485                            NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
2486         pktns->rtb.probe_pkt_left = 0;
2487         ngtcp2_conn_set_loss_detection_timer(conn, ts);
2488       }
2489     }
2490 
2491     /* Don't send any PING frame if client Initial has not been
2492        acknowledged yet. */
2493     if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2494         pktns->rtb.probe_pkt_left &&
2495         (type != NGTCP2_PKT_INITIAL ||
2496          ngtcp2_strm_is_all_tx_data_acked(&pktns->crypto.strm))) {
2497       lfr.type = NGTCP2_FRAME_PING;
2498 
2499       rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2500       if (rv != 0) {
2501         assert(rv == NGTCP2_ERR_NOBUF);
2502       } else {
2503         rtb_entry_flags |=
2504             NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING | NGTCP2_RTB_ENTRY_FLAG_PROBE;
2505         pkt_empty = 0;
2506       }
2507     }
2508 
2509     if (!pkt_empty) {
2510       if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
2511         /* The intention of smaller limit is get more chance to measure
2512            RTT samples in early phase. */
2513         if (pktns->rtb.probe_pkt_left || pktns->tx.num_non_ack_pkt >= 1) {
2514           lfr.type = NGTCP2_FRAME_PING;
2515 
2516           rv = conn_ppe_write_frame_hd_log(conn, &ppe, &hd_logged, &hd, &lfr);
2517           if (rv != 0) {
2518             assert(rv == NGTCP2_ERR_NOBUF);
2519           } else {
2520             rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
2521             pktns->tx.num_non_ack_pkt = 0;
2522           }
2523         } else {
2524           ++pktns->tx.num_non_ack_pkt;
2525         }
2526       } else {
2527         pktns->tx.num_non_ack_pkt = 0;
2528       }
2529     }
2530   }
2531 
2532   if (pkt_empty) {
2533     return 0;
2534   }
2535 
2536   /* If we cannot write another packet, then we need to add padding to
2537      Initial here. */
2538   if (conn_should_pad_pkt(
2539           conn, type, ngtcp2_ppe_left(&ppe), write_datalen,
2540           (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) != 0,
2541           require_padding)) {
2542     lfr.type = NGTCP2_FRAME_PADDING;
2543     lfr.padding.len = ngtcp2_ppe_padding(&ppe);
2544   } else {
2545     lfr.type = NGTCP2_FRAME_PADDING;
2546     lfr.padding.len = ngtcp2_ppe_padding_hp_sample(&ppe);
2547   }
2548 
2549   if (lfr.padding.len) {
2550     padded = 1;
2551     ngtcp2_log_tx_fr(&conn->log, &hd, &lfr);
2552     ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
2553   }
2554 
2555   spktlen = ngtcp2_ppe_final(&ppe, NULL);
2556   if (spktlen < 0) {
2557     assert(ngtcp2_err_is_fatal((int)spktlen));
2558     ngtcp2_frame_chain_list_del(frq, conn->mem);
2559     return spktlen;
2560   }
2561 
2562   ngtcp2_qlog_pkt_sent_end(&conn->qlog, &hd, (size_t)spktlen);
2563 
2564   if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) {
2565     if (pi) {
2566       conn_handle_tx_ecn(conn, pi, &rtb_entry_flags, pktns, &hd, ts);
2567     }
2568 
2569     rv = ngtcp2_rtb_entry_new(&rtbent, &hd, frq, ts, (size_t)spktlen,
2570                               rtb_entry_flags, conn->mem);
2571     if (rv != 0) {
2572       assert(ngtcp2_err_is_fatal(rv));
2573       ngtcp2_frame_chain_list_del(frq, conn->mem);
2574       return rv;
2575     }
2576 
2577     rv = conn_on_pkt_sent(conn, &pktns->rtb, rtbent);
2578     if (rv != 0) {
2579       ngtcp2_rtb_entry_del(rtbent, conn->mem);
2580       return rv;
2581     }
2582 
2583     if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
2584         (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE)) {
2585       conn_restart_timer_on_write(conn, ts);
2586     }
2587   } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
2588     conn_handle_tx_ecn(conn, pi, NULL, pktns, &hd, ts);
2589   }
2590 
2591   if (pktns->rtb.probe_pkt_left &&
2592       (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
2593     --pktns->rtb.probe_pkt_left;
2594   }
2595 
2596   conn_update_keep_alive_last_ts(conn, ts);
2597 
2598   conn->dcid.current.bytes_sent += (uint64_t)spktlen;
2599 
2600   conn->tx.pacing.pktlen += (size_t)spktlen;
2601 
2602   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
2603 
2604   ++pktns->tx.last_pkt_num;
2605 
2606   return spktlen;
2607 }
2608 
2609 /*
2610  * conn_write_ack_pkt writes QUIC packet for type |type| which only
2611  * includes ACK frame in the buffer pointed by |dest| whose length is
2612  * |destlen|.
2613  *
2614  * This function returns the number of bytes written in |dest| if it
2615  * succeeds, or one of the following negative error codes:
2616  *
2617  * NGTCP2_ERR_CALLBACK_FAILURE
2618  *     User-defined callback function failed.
2619  * NGTCP2_ERR_NOMEM
2620  *     Out of memory.
2621  */
conn_write_ack_pkt(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint8_t type,ngtcp2_tstamp ts)2622 static ngtcp2_ssize conn_write_ack_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
2623                                        uint8_t *dest, size_t destlen,
2624                                        uint8_t type, ngtcp2_tstamp ts) {
2625   int rv;
2626   ngtcp2_frame *ackfr;
2627   ngtcp2_pktns *pktns;
2628   ngtcp2_duration ack_delay;
2629   uint64_t ack_delay_exponent;
2630   ngtcp2_ssize spktlen;
2631 
2632   assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
2633 
2634   switch (type) {
2635   case NGTCP2_PKT_INITIAL:
2636     assert(conn->server);
2637     pktns = conn->in_pktns;
2638     ack_delay = 0;
2639     ack_delay_exponent = NGTCP2_DEFAULT_ACK_DELAY_EXPONENT;
2640     break;
2641   case NGTCP2_PKT_HANDSHAKE:
2642     pktns = conn->hs_pktns;
2643     ack_delay = 0;
2644     ack_delay_exponent = NGTCP2_DEFAULT_ACK_DELAY_EXPONENT;
2645     break;
2646   case NGTCP2_PKT_SHORT:
2647     pktns = &conn->pktns;
2648     ack_delay = conn_compute_ack_delay(conn);
2649     ack_delay_exponent = conn->local.transport_params.ack_delay_exponent;
2650     break;
2651   default:
2652     assert(0);
2653     abort();
2654   }
2655 
2656   if (!pktns->crypto.tx.ckm) {
2657     return 0;
2658   }
2659 
2660   ackfr = NULL;
2661   rv = conn_create_ack_frame(conn, &ackfr, pktns, type, ts, ack_delay,
2662                              ack_delay_exponent);
2663   if (rv != 0) {
2664     return rv;
2665   }
2666 
2667   if (!ackfr) {
2668     return 0;
2669   }
2670 
2671   spktlen = ngtcp2_conn_write_single_frame_pkt(
2672       conn, pi, dest, destlen, type, &conn->dcid.current.cid, ackfr,
2673       NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
2674 
2675   if (spktlen <= 0) {
2676     return spktlen;
2677   }
2678 
2679   conn->dcid.current.bytes_sent += (uint64_t)spktlen;
2680 
2681   return spktlen;
2682 }
2683 
conn_discard_pktns(ngtcp2_conn * conn,ngtcp2_pktns ** ppktns,ngtcp2_tstamp ts)2684 static void conn_discard_pktns(ngtcp2_conn *conn, ngtcp2_pktns **ppktns,
2685                                ngtcp2_tstamp ts) {
2686   ngtcp2_pktns *pktns = *ppktns;
2687   uint64_t bytes_in_flight;
2688 
2689   bytes_in_flight = pktns->rtb.cc_bytes_in_flight;
2690 
2691   assert(conn->cstat.bytes_in_flight >= bytes_in_flight);
2692 
2693   conn->cstat.bytes_in_flight -= bytes_in_flight;
2694   conn->cstat.pto_count = 0;
2695   conn->cstat.last_tx_pkt_ts[pktns->rtb.pktns_id] = UINT64_MAX;
2696   conn->cstat.loss_time[pktns->rtb.pktns_id] = UINT64_MAX;
2697 
2698   conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.rx.ckm->aead_ctx);
2699   conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.rx.hp_ctx);
2700   conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
2701   conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.tx.hp_ctx);
2702 
2703   pktns_del(pktns, conn->mem);
2704   *ppktns = NULL;
2705 
2706   ngtcp2_conn_set_loss_detection_timer(conn, ts);
2707 }
2708 
2709 /*
2710  * conn_discard_initial_state discards state for Initial packet number
2711  * space.
2712  */
conn_discard_initial_state(ngtcp2_conn * conn,ngtcp2_tstamp ts)2713 static void conn_discard_initial_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2714   if (!conn->in_pktns) {
2715     return;
2716   }
2717 
2718   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
2719                   "discarding Initial packet number space");
2720 
2721   conn_discard_pktns(conn, &conn->in_pktns, ts);
2722 }
2723 
2724 /*
2725  * conn_discard_handshake_state discards state for Handshake packet
2726  * number space.
2727  */
conn_discard_handshake_state(ngtcp2_conn * conn,ngtcp2_tstamp ts)2728 static void conn_discard_handshake_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
2729   if (!conn->hs_pktns) {
2730     return;
2731   }
2732 
2733   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
2734                   "discarding Handshake packet number space");
2735 
2736   conn_discard_pktns(conn, &conn->hs_pktns, ts);
2737 }
2738 
2739 /*
2740  * conn_discard_early_key discards early key.
2741  */
conn_discard_early_key(ngtcp2_conn * conn)2742 static void conn_discard_early_key(ngtcp2_conn *conn) {
2743   assert(conn->early.ckm);
2744 
2745   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "discarding early key");
2746 
2747   conn_call_delete_crypto_aead_ctx(conn, &conn->early.ckm->aead_ctx);
2748   conn_call_delete_crypto_cipher_ctx(conn, &conn->early.hp_ctx);
2749   memset(&conn->early.hp_ctx, 0, sizeof(conn->early.hp_ctx));
2750 
2751   ngtcp2_crypto_km_del(conn->early.ckm, conn->mem);
2752   conn->early.ckm = NULL;
2753 }
2754 
2755 /*
2756  * conn_write_handshake_ack_pkts writes packets which contain ACK
2757  * frame only.  This function writes at most 2 packets for each
2758  * Initial and Handshake packet.
2759  */
conn_write_handshake_ack_pkts(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_tstamp ts)2760 static ngtcp2_ssize conn_write_handshake_ack_pkts(ngtcp2_conn *conn,
2761                                                   ngtcp2_pkt_info *pi,
2762                                                   uint8_t *dest, size_t destlen,
2763                                                   ngtcp2_tstamp ts) {
2764   ngtcp2_ssize res = 0, nwrite = 0;
2765 
2766   /* In the most cases, client sends ACK in conn_write_handshake_pkt.
2767      This function is only called when it is CWND limited.  It is not
2768      required for client to send ACK for server Initial.  This is
2769      because once it gets server Initial, it gets Handshake tx key and
2770      discards Initial key.  The only good reason to send ACK is give
2771      server RTT measurement early. */
2772   if (conn->server && conn->in_pktns) {
2773     nwrite =
2774         conn_write_ack_pkt(conn, pi, dest, destlen, NGTCP2_PKT_INITIAL, ts);
2775     if (nwrite < 0) {
2776       assert(nwrite != NGTCP2_ERR_NOBUF);
2777       return nwrite;
2778     }
2779 
2780     res += nwrite;
2781     dest += nwrite;
2782     destlen -= (size_t)nwrite;
2783   }
2784 
2785   if (conn->hs_pktns->crypto.tx.ckm) {
2786     nwrite =
2787         conn_write_ack_pkt(conn, pi, dest, destlen, NGTCP2_PKT_HANDSHAKE, ts);
2788     if (nwrite < 0) {
2789       assert(nwrite != NGTCP2_ERR_NOBUF);
2790       return nwrite;
2791     }
2792 
2793     res += nwrite;
2794 
2795     if (!conn->server && nwrite) {
2796       conn_discard_initial_state(conn, ts);
2797     }
2798   }
2799 
2800   return res;
2801 }
2802 
2803 /*
2804  * conn_write_client_initial writes Initial packet in the buffer
2805  * pointed by |dest| whose length is |destlen|.
2806  *
2807  * This function returns the number of bytes written in |dest| if it
2808  * succeeds, or one of the following negative error codes:
2809  *
2810  * NGTCP2_ERR_NOMEM
2811  *     Out of memory.
2812  * NGTCP2_ERR_CALLBACK_FAILURE
2813  *     User-defined callback function failed.
2814  */
conn_write_client_initial(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint64_t early_datalen,ngtcp2_tstamp ts)2815 static ngtcp2_ssize conn_write_client_initial(ngtcp2_conn *conn,
2816                                               ngtcp2_pkt_info *pi,
2817                                               uint8_t *dest, size_t destlen,
2818                                               uint64_t early_datalen,
2819                                               ngtcp2_tstamp ts) {
2820   int rv;
2821 
2822   rv = conn_call_client_initial(conn);
2823   if (rv != 0) {
2824     return rv;
2825   }
2826 
2827   return conn_write_handshake_pkt(conn, pi, dest, destlen, NGTCP2_PKT_INITIAL,
2828                                   NGTCP2_WRITE_PKT_FLAG_NONE, early_datalen,
2829                                   ts);
2830 }
2831 
2832 /*
2833  * dcid_tx_left returns the maximum number of bytes that server is
2834  * allowed to send to an unvalidated path associated to |dcid|.
2835  */
dcid_tx_left(ngtcp2_dcid * dcid)2836 static uint64_t dcid_tx_left(ngtcp2_dcid *dcid) {
2837   if (dcid->flags & NGTCP2_DCID_FLAG_PATH_VALIDATED) {
2838     return SIZE_MAX;
2839   }
2840   /* From QUIC spec: Prior to validating the client address, servers
2841      MUST NOT send more than three times as many bytes as the number
2842      of bytes they have received. */
2843   assert(dcid->bytes_recv * 3 >= dcid->bytes_sent);
2844 
2845   return dcid->bytes_recv * 3 - dcid->bytes_sent;
2846 }
2847 
2848 /*
2849  * conn_server_tx_left returns the maximum number of bytes that server
2850  * is allowed to send to an unvalidated path.
2851  */
conn_server_tx_left(ngtcp2_conn * conn,ngtcp2_dcid * dcid)2852 static uint64_t conn_server_tx_left(ngtcp2_conn *conn, ngtcp2_dcid *dcid) {
2853   assert(conn->server);
2854 
2855   /* If pv->dcid has the current path, use conn->dcid.current.  This
2856      is because conn->dcid.current gets update for bytes_recv and
2857      bytes_sent. */
2858   if (ngtcp2_path_eq(&dcid->ps.path, &conn->dcid.current.ps.path)) {
2859     return dcid_tx_left(&conn->dcid.current);
2860   }
2861 
2862   return dcid_tx_left(dcid);
2863 }
2864 
2865 /*
2866  * conn_write_handshake_pkts writes Initial and Handshake packets in
2867  * the buffer pointed by |dest| whose length is |destlen|.
2868  *
2869  * This function returns the number of bytes written in |dest| if it
2870  * succeeds, or one of the following negative error codes:
2871  *
2872  * NGTCP2_ERR_NOMEM
2873  *     Out of memory.
2874  * NGTCP2_ERR_CALLBACK_FAILURE
2875  *     User-defined callback function failed.
2876  */
conn_write_handshake_pkts(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint64_t write_datalen,ngtcp2_tstamp ts)2877 static ngtcp2_ssize conn_write_handshake_pkts(ngtcp2_conn *conn,
2878                                               ngtcp2_pkt_info *pi,
2879                                               uint8_t *dest, size_t destlen,
2880                                               uint64_t write_datalen,
2881                                               ngtcp2_tstamp ts) {
2882   ngtcp2_ssize nwrite;
2883   ngtcp2_ssize res = 0;
2884   ngtcp2_rtb_entry *rtbent;
2885   uint8_t wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
2886   ngtcp2_conn_stat *cstat = &conn->cstat;
2887   ngtcp2_ksl_it it;
2888 
2889   /* As a client, we would like to discard Initial packet number space
2890      when sending the first Handshake packet.  When sending Handshake
2891      packet, it should be one of 1) sending ACK, 2) sending PTO probe
2892      packet, or 3) sending CRYPTO.  If we have pending acknowledgement
2893      for Initial, then do not discard Initial packet number space.
2894      Otherwise, if either 1) or 2) is satisfied, discard Initial
2895      packet number space.  When sending Handshake CRYPTO, it indicates
2896      that client has received Handshake CRYPTO from server.  Initial
2897      packet number space is discarded because 1) is met.  If there is
2898      pending Initial ACK, Initial packet number space is discarded
2899      after writing the first Handshake packet.
2900    */
2901   if (!conn->server && conn->hs_pktns->crypto.tx.ckm && conn->in_pktns &&
2902       !ngtcp2_acktr_require_active_ack(&conn->in_pktns->acktr,
2903                                        /* max_ack_delay = */ 0, ts) &&
2904       (ngtcp2_acktr_require_active_ack(&conn->hs_pktns->acktr,
2905                                        /* max_ack_delay = */ 0, ts) ||
2906        conn->hs_pktns->rtb.probe_pkt_left)) {
2907     /* Discard Initial state here so that Handshake packet is not
2908        padded. */
2909     conn_discard_initial_state(conn, ts);
2910   } else if (conn->in_pktns) {
2911     nwrite =
2912         conn_write_handshake_pkt(conn, pi, dest, destlen, NGTCP2_PKT_INITIAL,
2913                                  NGTCP2_WRITE_PKT_FLAG_NONE, write_datalen, ts);
2914     if (nwrite < 0) {
2915       assert(nwrite != NGTCP2_ERR_NOBUF);
2916       return nwrite;
2917     }
2918 
2919     if (nwrite == 0) {
2920       if (conn->server && (conn->in_pktns->rtb.probe_pkt_left ||
2921                            ngtcp2_ksl_len(&conn->in_pktns->crypto.tx.frq))) {
2922         if (cstat->loss_detection_timer != UINT64_MAX &&
2923             conn_server_tx_left(conn, &conn->dcid.current) <
2924                 NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
2925           ngtcp2_log_info(
2926               &conn->log, NGTCP2_LOG_EVENT_RCV,
2927               "loss detection timer canceled due to amplification limit");
2928           cstat->loss_detection_timer = UINT64_MAX;
2929         }
2930 
2931         return 0;
2932       }
2933     } else {
2934       res += nwrite;
2935       dest += nwrite;
2936       destlen -= (size_t)nwrite;
2937 
2938       if (destlen) {
2939         /* We might have already added padding to Initial, but in that
2940            case, we should have destlen == 0 and no Handshake packet
2941            will be written. */
2942         if (conn->server) {
2943           it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
2944           if (!ngtcp2_ksl_it_end(&it)) {
2945             rtbent = ngtcp2_ksl_it_get(&it);
2946             if (rtbent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
2947               wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
2948             }
2949           }
2950         } else {
2951           wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
2952         }
2953       }
2954     }
2955   }
2956 
2957   nwrite = conn_write_handshake_pkt(
2958       conn, pi, dest, destlen, NGTCP2_PKT_HANDSHAKE, wflags, write_datalen, ts);
2959   if (nwrite < 0) {
2960     assert(nwrite != NGTCP2_ERR_NOBUF);
2961     return nwrite;
2962   }
2963 
2964   res += nwrite;
2965 
2966   if (!conn->server && conn->hs_pktns->crypto.tx.ckm && nwrite) {
2967     /* We don't need to send further Initial packet if we have
2968        Handshake key and sent something with it.  So discard initial
2969        state here. */
2970     conn_discard_initial_state(conn, ts);
2971   }
2972 
2973   return res;
2974 }
2975 
2976 /*
2977  * conn_initial_stream_rx_offset returns the initial maximum offset of
2978  * data for a stream denoted by |stream_id|.
2979  */
conn_initial_stream_rx_offset(ngtcp2_conn * conn,int64_t stream_id)2980 static uint64_t conn_initial_stream_rx_offset(ngtcp2_conn *conn,
2981                                               int64_t stream_id) {
2982   int local_stream = conn_local_stream(conn, stream_id);
2983 
2984   if (bidi_stream(stream_id)) {
2985     if (local_stream) {
2986       return conn->local.transport_params.initial_max_stream_data_bidi_local;
2987     }
2988     return conn->local.transport_params.initial_max_stream_data_bidi_remote;
2989   }
2990 
2991   if (local_stream) {
2992     return 0;
2993   }
2994   return conn->local.transport_params.initial_max_stream_data_uni;
2995 }
2996 
2997 /*
2998  * conn_should_send_max_stream_data returns nonzero if MAX_STREAM_DATA
2999  * frame should be send for |strm|.
3000  */
conn_should_send_max_stream_data(ngtcp2_conn * conn,ngtcp2_strm * strm)3001 static int conn_should_send_max_stream_data(ngtcp2_conn *conn,
3002                                             ngtcp2_strm *strm) {
3003   uint64_t inc = strm->rx.unsent_max_offset - strm->rx.max_offset;
3004   (void)conn;
3005 
3006   return strm->rx.window < 2 * inc;
3007 }
3008 
3009 /*
3010  * conn_should_send_max_data returns nonzero if MAX_DATA frame should
3011  * be sent.
3012  */
conn_should_send_max_data(ngtcp2_conn * conn)3013 static int conn_should_send_max_data(ngtcp2_conn *conn) {
3014   uint64_t inc = conn->rx.unsent_max_offset - conn->rx.max_offset;
3015 
3016   return conn->rx.window < 2 * inc;
3017 }
3018 
3019 /*
3020  * conn_required_num_new_connection_id returns the number of
3021  * additional connection ID the local endpoint has to provide to the
3022  * remote endpoint.
3023  */
conn_required_num_new_connection_id(ngtcp2_conn * conn)3024 static size_t conn_required_num_new_connection_id(ngtcp2_conn *conn) {
3025   uint64_t n;
3026   size_t len = ngtcp2_ksl_len(&conn->scid.set);
3027 
3028   if (len >= NGTCP2_MAX_SCID_POOL_SIZE) {
3029     return 0;
3030   }
3031 
3032   assert(conn->remote.transport_params.active_connection_id_limit);
3033 
3034   /* len includes retired CID.  We don't provide extra CID if doing so
3035      exceeds NGTCP2_MAX_SCID_POOL_SIZE. */
3036 
3037   n = conn->remote.transport_params.active_connection_id_limit +
3038       conn->scid.num_retired;
3039 
3040   return (size_t)ngtcp2_min(NGTCP2_MAX_SCID_POOL_SIZE, n) - len;
3041 }
3042 
3043 /*
3044  * conn_enqueue_new_connection_id generates additional connection IDs
3045  * and prepares to send them to the remote endpoint.
3046  *
3047  * This function returns 0 if it succeeds, or one of the following
3048  * negative error codes:
3049  *
3050  * NGTCP2_ERR_NOMEM
3051  *     Out of memory.
3052  * NGTCP2_ERR_CALLBACK_FAILURE
3053  *     User-defined callback function failed.
3054  */
conn_enqueue_new_connection_id(ngtcp2_conn * conn)3055 static int conn_enqueue_new_connection_id(ngtcp2_conn *conn) {
3056   size_t i, need = conn_required_num_new_connection_id(conn);
3057   size_t cidlen = conn->oscid.datalen;
3058   ngtcp2_cid cid;
3059   uint64_t seq;
3060   int rv;
3061   uint8_t token[NGTCP2_STATELESS_RESET_TOKENLEN];
3062   ngtcp2_frame_chain *nfrc;
3063   ngtcp2_pktns *pktns = &conn->pktns;
3064   ngtcp2_scid *scid;
3065   ngtcp2_ksl_it it;
3066 
3067   for (i = 0; i < need; ++i) {
3068     rv = conn_call_get_new_connection_id(conn, &cid, token, cidlen);
3069     if (rv != 0) {
3070       return rv;
3071     }
3072 
3073     if (cid.datalen != cidlen) {
3074       return NGTCP2_ERR_CALLBACK_FAILURE;
3075     }
3076 
3077     /* Assert uniqueness */
3078     it = ngtcp2_ksl_lower_bound(&conn->scid.set, &cid);
3079     if (!ngtcp2_ksl_it_end(&it) &&
3080         ngtcp2_cid_eq(ngtcp2_ksl_it_key(&it), &cid)) {
3081       return NGTCP2_ERR_CALLBACK_FAILURE;
3082     }
3083 
3084     seq = ++conn->scid.last_seq;
3085 
3086     scid = ngtcp2_mem_malloc(conn->mem, sizeof(*scid));
3087     if (scid == NULL) {
3088       return NGTCP2_ERR_NOMEM;
3089     }
3090 
3091     ngtcp2_scid_init(scid, seq, &cid);
3092 
3093     rv = ngtcp2_ksl_insert(&conn->scid.set, NULL, &scid->cid, scid);
3094     if (rv != 0) {
3095       ngtcp2_mem_free(conn->mem, scid);
3096       return rv;
3097     }
3098 
3099     rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3100     if (rv != 0) {
3101       return rv;
3102     }
3103 
3104     nfrc->fr.type = NGTCP2_FRAME_NEW_CONNECTION_ID;
3105     nfrc->fr.new_connection_id.seq = seq;
3106     nfrc->fr.new_connection_id.retire_prior_to = 0;
3107     nfrc->fr.new_connection_id.cid = cid;
3108     memcpy(nfrc->fr.new_connection_id.stateless_reset_token, token,
3109            sizeof(token));
3110     nfrc->next = pktns->tx.frq;
3111     pktns->tx.frq = nfrc;
3112   }
3113 
3114   return 0;
3115 }
3116 
3117 /*
3118  * conn_remove_retired_connection_id removes the already retired
3119  * connection ID.  It waits PTO before actually removing a connection
3120  * ID after it receives RETIRE_CONNECTION_ID from peer to catch
3121  * reordered packets.
3122  *
3123  * This function returns 0 if it succeeds, or one of the following
3124  * negative error codes:
3125  *
3126  * NGTCP2_ERR_NOMEM
3127  *     Out of memory.
3128  * NGTCP2_ERR_CALLBACK_FAILURE
3129  *     User-defined callback function failed.
3130  */
conn_remove_retired_connection_id(ngtcp2_conn * conn,ngtcp2_duration pto,ngtcp2_tstamp ts)3131 static int conn_remove_retired_connection_id(ngtcp2_conn *conn,
3132                                              ngtcp2_duration pto,
3133                                              ngtcp2_tstamp ts) {
3134   ngtcp2_duration timeout = pto;
3135   ngtcp2_scid *scid;
3136   ngtcp2_dcid *dcid;
3137   int rv;
3138 
3139   for (; !ngtcp2_pq_empty(&conn->scid.used);) {
3140     scid = ngtcp2_struct_of(ngtcp2_pq_top(&conn->scid.used), ngtcp2_scid, pe);
3141 
3142     if (scid->retired_ts == UINT64_MAX || scid->retired_ts + timeout >= ts) {
3143       break;
3144     }
3145 
3146     assert(scid->flags & NGTCP2_SCID_FLAG_RETIRED);
3147 
3148     rv = conn_call_remove_connection_id(conn, &scid->cid);
3149     if (rv != 0) {
3150       return rv;
3151     }
3152 
3153     ngtcp2_ksl_remove(&conn->scid.set, NULL, &scid->cid);
3154     ngtcp2_pq_pop(&conn->scid.used);
3155     ngtcp2_mem_free(conn->mem, scid);
3156 
3157     assert(conn->scid.num_retired);
3158     --conn->scid.num_retired;
3159   }
3160 
3161   for (; ngtcp2_ringbuf_len(&conn->dcid.retired);) {
3162     dcid = ngtcp2_ringbuf_get(&conn->dcid.retired, 0);
3163     if (dcid->retired_ts + timeout >= ts) {
3164       break;
3165     }
3166 
3167     rv = conn_call_deactivate_dcid(conn, dcid);
3168     if (rv != 0) {
3169       return rv;
3170     }
3171 
3172     ngtcp2_ringbuf_pop_front(&conn->dcid.retired);
3173   }
3174 
3175   return 0;
3176 }
3177 
3178 /*
3179  * conn_min_short_pktlen returns the minimum length of Short packet
3180  * this endpoint sends.
3181  */
conn_min_short_pktlen(ngtcp2_conn * conn)3182 static size_t conn_min_short_pktlen(ngtcp2_conn *conn) {
3183   return conn->dcid.current.cid.datalen + NGTCP2_MIN_PKT_EXPANDLEN;
3184 }
3185 
3186 /*
3187  * conn_write_pkt writes a protected packet in the buffer pointed by
3188  * |dest| whose length if |destlen|.  |type| specifies the type of
3189  * packet.  It can be NGTCP2_PKT_SHORT or NGTCP2_PKT_0RTT.
3190  *
3191  * This function can send new stream data.  In order to send stream
3192  * data, specify the underlying stream and parameters to
3193  * |vmsg|->stream.  If |vmsg|->stream.fin is set to nonzero, it
3194  * signals that the given data is the final portion of the stream.
3195  * |vmsg|->stream.data vector of length |vmsg|->stream.datacnt
3196  * specifies stream data to send.  The number of bytes sent to the
3197  * stream is assigned to *|vmsg|->stream.pdatalen.  If 0 length STREAM
3198  * data is sent, 0 is assigned to it.  The caller should initialize
3199  * *|vmsg|->stream.pdatalen to -1.
3200  *
3201  * If |require_padding| is nonzero, padding bytes are added to occupy
3202  * the remaining packet payload.
3203  *
3204  * This function returns the number of bytes written in |dest| if it
3205  * succeeds, or one of the following negative error codes:
3206  *
3207  * NGTCP2_ERR_NOMEM
3208  *     Out of memory.
3209  * NGTCP2_ERR_CALLBACK_FAILURE
3210  *     User-defined callback function failed.
3211  * NGTCP2_ERR_STREAM_DATA_BLOCKED
3212  *     Stream data could not be written because of flow control.
3213  */
conn_write_pkt(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_vmsg * vmsg,uint8_t type,uint8_t flags,ngtcp2_tstamp ts)3214 static ngtcp2_ssize conn_write_pkt(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
3215                                    uint8_t *dest, size_t destlen,
3216                                    ngtcp2_vmsg *vmsg, uint8_t type,
3217                                    uint8_t flags, ngtcp2_tstamp ts) {
3218   int rv = 0;
3219   ngtcp2_crypto_cc *cc = &conn->pkt.cc;
3220   ngtcp2_ppe *ppe = &conn->pkt.ppe;
3221   ngtcp2_pkt_hd *hd = &conn->pkt.hd;
3222   ngtcp2_frame *ackfr = NULL, lfr;
3223   ngtcp2_ssize nwrite;
3224   ngtcp2_frame_chain **pfrc, *nfrc, *frc;
3225   ngtcp2_rtb_entry *ent;
3226   ngtcp2_strm *strm;
3227   int pkt_empty = 1;
3228   uint64_t ndatalen = 0;
3229   int send_stream = 0;
3230   int stream_blocked = 0;
3231   int send_datagram = 0;
3232   ngtcp2_pktns *pktns = &conn->pktns;
3233   size_t left;
3234   uint64_t datalen = 0;
3235   ngtcp2_vec data[NGTCP2_MAX_STREAM_DATACNT];
3236   size_t datacnt;
3237   uint8_t rtb_entry_flags = NGTCP2_RTB_ENTRY_FLAG_NONE;
3238   int hd_logged = 0;
3239   ngtcp2_path_challenge_entry *pcent;
3240   uint8_t hd_flags;
3241   int require_padding = (flags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING) != 0;
3242   int write_more = (flags & NGTCP2_WRITE_PKT_FLAG_MORE) != 0;
3243   int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
3244   size_t min_pktlen = conn_min_short_pktlen(conn);
3245   int padded = 0;
3246   ngtcp2_cc_pkt cc_pkt;
3247   uint64_t crypto_offset;
3248   uint64_t stream_offset;
3249   ngtcp2_ssize num_reclaimed;
3250   int fin;
3251   uint64_t target_max_data;
3252   ngtcp2_conn_stat *cstat = &conn->cstat;
3253   uint64_t delta;
3254   const ngtcp2_cid *scid;
3255   int keep_alive_expired = 0;
3256 
3257   /* Return 0 if destlen is less than minimum packet length which can
3258      trigger Stateless Reset */
3259   if (destlen < min_pktlen) {
3260     return 0;
3261   }
3262 
3263   if (vmsg) {
3264     switch (vmsg->type) {
3265     case NGTCP2_VMSG_TYPE_STREAM:
3266       datalen = ngtcp2_vec_len(vmsg->stream.data, vmsg->stream.datacnt);
3267       ndatalen = conn_enforce_flow_control(conn, vmsg->stream.strm, datalen);
3268       /* 0 length STREAM frame is allowed */
3269       if (ndatalen || datalen == 0) {
3270         send_stream = 1;
3271       } else {
3272         stream_blocked = 1;
3273       }
3274       break;
3275     case NGTCP2_VMSG_TYPE_DATAGRAM:
3276       datalen = ngtcp2_vec_len(vmsg->datagram.data, vmsg->datagram.datacnt);
3277       send_datagram = 1;
3278       break;
3279     default:
3280       break;
3281     }
3282   }
3283 
3284   if (!ppe_pending) {
3285     switch (type) {
3286     case NGTCP2_PKT_SHORT:
3287       hd_flags = conn_pkt_flags_short(conn);
3288       scid = NULL;
3289       cc->aead = pktns->crypto.ctx.aead;
3290       cc->hp = pktns->crypto.ctx.hp;
3291       cc->ckm = pktns->crypto.tx.ckm;
3292       cc->hp_ctx = pktns->crypto.tx.hp_ctx;
3293 
3294       /* transport parameter is only valid after handshake completion
3295          which means we don't know how many connection ID that remote
3296          peer can accept before handshake completion. */
3297       if (conn->oscid.datalen &&
3298           (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
3299         rv = conn_enqueue_new_connection_id(conn);
3300         if (rv != 0) {
3301           return rv;
3302         }
3303       }
3304 
3305       break;
3306     case NGTCP2_PKT_0RTT:
3307       assert(!conn->server);
3308       if (!conn->early.ckm) {
3309         return 0;
3310       }
3311       hd_flags = conn_pkt_flags_long(conn);
3312       scid = &conn->oscid;
3313       cc->aead = conn->early.ctx.aead;
3314       cc->hp = conn->early.ctx.hp;
3315       cc->ckm = conn->early.ckm;
3316       cc->hp_ctx = conn->early.hp_ctx;
3317       break;
3318     default:
3319       /* Unreachable */
3320       assert(0);
3321     }
3322 
3323     cc->encrypt = conn->callbacks.encrypt;
3324     cc->hp_mask = conn->callbacks.hp_mask;
3325 
3326     if (conn_should_send_max_data(conn)) {
3327       rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3328       if (rv != 0) {
3329         return rv;
3330       }
3331 
3332       if (conn->local.settings.max_window &&
3333           conn->tx.last_max_data_ts != UINT64_MAX &&
3334           ts - conn->tx.last_max_data_ts <
3335               NGTCP2_FLOW_WINDOW_RTT_FACTOR * cstat->smoothed_rtt &&
3336           conn->local.settings.max_window > conn->rx.window) {
3337         target_max_data = NGTCP2_FLOW_WINDOW_SCALING_FACTOR * conn->rx.window;
3338         if (target_max_data > conn->local.settings.max_window) {
3339           target_max_data = conn->local.settings.max_window;
3340         }
3341 
3342         delta = target_max_data - conn->rx.window;
3343         if (conn->rx.unsent_max_offset + delta > NGTCP2_MAX_VARINT) {
3344           delta = NGTCP2_MAX_VARINT - conn->rx.unsent_max_offset;
3345         }
3346 
3347         conn->rx.window = target_max_data;
3348       } else {
3349         delta = 0;
3350       }
3351 
3352       conn->tx.last_max_data_ts = ts;
3353 
3354       nfrc->fr.type = NGTCP2_FRAME_MAX_DATA;
3355       nfrc->fr.max_data.max_data = conn->rx.unsent_max_offset + delta;
3356       nfrc->next = pktns->tx.frq;
3357       pktns->tx.frq = nfrc;
3358 
3359       conn->rx.max_offset = conn->rx.unsent_max_offset =
3360           nfrc->fr.max_data.max_data;
3361     }
3362 
3363     ngtcp2_pkt_hd_init(hd, hd_flags, type, &conn->dcid.current.cid, scid,
3364                        pktns->tx.last_pkt_num + 1,
3365                        pktns_select_pkt_numlen(pktns), conn->version, 0);
3366 
3367     ngtcp2_ppe_init(ppe, dest, destlen, cc);
3368 
3369     rv = ngtcp2_ppe_encode_hd(ppe, hd);
3370     if (rv != 0) {
3371       assert(NGTCP2_ERR_NOBUF == rv);
3372       return 0;
3373     }
3374 
3375     if (!ngtcp2_ppe_ensure_hp_sample(ppe)) {
3376       return 0;
3377     }
3378 
3379     if (ngtcp2_ringbuf_len(&conn->rx.path_challenge)) {
3380       pcent = ngtcp2_ringbuf_get(&conn->rx.path_challenge, 0);
3381 
3382       /* PATH_RESPONSE is bound to the path that the corresponding
3383          PATH_CHALLENGE is received. */
3384       if (ngtcp2_path_eq(&conn->dcid.current.ps.path, &pcent->ps.path)) {
3385         lfr.type = NGTCP2_FRAME_PATH_RESPONSE;
3386         memcpy(lfr.path_response.data, pcent->data,
3387                sizeof(lfr.path_response.data));
3388 
3389         rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3390         if (rv != 0) {
3391           assert(NGTCP2_ERR_NOBUF == rv);
3392         } else {
3393           ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge);
3394 
3395           pkt_empty = 0;
3396           rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
3397           require_padding =
3398               !conn->server || destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE;
3399           /* We don't retransmit PATH_RESPONSE. */
3400         }
3401       }
3402     }
3403 
3404     rv = conn_create_ack_frame(conn, &ackfr, pktns, type, ts,
3405                                conn_compute_ack_delay(conn),
3406                                conn->local.transport_params.ack_delay_exponent);
3407     if (rv != 0) {
3408       assert(ngtcp2_err_is_fatal(rv));
3409       return rv;
3410     }
3411 
3412     if (ackfr) {
3413       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, ackfr);
3414       if (rv != 0) {
3415         assert(NGTCP2_ERR_NOBUF == rv);
3416       } else {
3417         ngtcp2_acktr_commit_ack(&pktns->acktr);
3418         ngtcp2_acktr_add_ack(&pktns->acktr, hd->pkt_num,
3419                              ackfr->ack.largest_ack);
3420         pkt_empty = 0;
3421       }
3422     }
3423 
3424   build_pkt:
3425     for (pfrc = &pktns->tx.frq; *pfrc;) {
3426       if ((*pfrc)->binder &&
3427           ((*pfrc)->binder->flags & NGTCP2_FRAME_CHAIN_BINDER_FLAG_ACK)) {
3428         frc = *pfrc;
3429         *pfrc = (*pfrc)->next;
3430         ngtcp2_frame_chain_del(frc, conn->mem);
3431         continue;
3432       }
3433 
3434       switch ((*pfrc)->fr.type) {
3435       case NGTCP2_FRAME_STOP_SENDING:
3436         strm =
3437             ngtcp2_conn_find_stream(conn, (*pfrc)->fr.stop_sending.stream_id);
3438         if (strm == NULL || (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD)) {
3439           frc = *pfrc;
3440           *pfrc = (*pfrc)->next;
3441           ngtcp2_frame_chain_del(frc, conn->mem);
3442           continue;
3443         }
3444 
3445         rv = conn_call_stream_stop_sending(
3446             conn, (*pfrc)->fr.stop_sending.stream_id,
3447             (*pfrc)->fr.stop_sending.app_error_code, strm->stream_user_data);
3448         if (rv != 0) {
3449           assert(ngtcp2_err_is_fatal(rv));
3450           return rv;
3451         }
3452 
3453         break;
3454       case NGTCP2_FRAME_STREAM:
3455         assert(0);
3456         break;
3457       case NGTCP2_FRAME_MAX_STREAMS_BIDI:
3458         if ((*pfrc)->fr.max_streams.max_streams <
3459             conn->remote.bidi.max_streams) {
3460           frc = *pfrc;
3461           *pfrc = (*pfrc)->next;
3462           ngtcp2_frame_chain_del(frc, conn->mem);
3463           continue;
3464         }
3465         break;
3466       case NGTCP2_FRAME_MAX_STREAMS_UNI:
3467         if ((*pfrc)->fr.max_streams.max_streams <
3468             conn->remote.uni.max_streams) {
3469           frc = *pfrc;
3470           *pfrc = (*pfrc)->next;
3471           ngtcp2_frame_chain_del(frc, conn->mem);
3472           continue;
3473         }
3474         break;
3475       case NGTCP2_FRAME_MAX_STREAM_DATA:
3476         strm = ngtcp2_conn_find_stream(conn,
3477                                        (*pfrc)->fr.max_stream_data.stream_id);
3478         if (strm == NULL || (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) ||
3479             (*pfrc)->fr.max_stream_data.max_stream_data < strm->rx.max_offset) {
3480           frc = *pfrc;
3481           *pfrc = (*pfrc)->next;
3482           ngtcp2_frame_chain_del(frc, conn->mem);
3483           continue;
3484         }
3485         break;
3486       case NGTCP2_FRAME_MAX_DATA:
3487         if ((*pfrc)->fr.max_data.max_data < conn->rx.max_offset) {
3488           frc = *pfrc;
3489           *pfrc = (*pfrc)->next;
3490           ngtcp2_frame_chain_del(frc, conn->mem);
3491           continue;
3492         }
3493         break;
3494       case NGTCP2_FRAME_RETIRE_CONNECTION_ID:
3495         ++conn->dcid.num_retire_queued;
3496         break;
3497       case NGTCP2_FRAME_CRYPTO:
3498         assert(0);
3499         break;
3500       }
3501 
3502       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &(*pfrc)->fr);
3503       if (rv != 0) {
3504         assert(NGTCP2_ERR_NOBUF == rv);
3505         break;
3506       }
3507 
3508       pkt_empty = 0;
3509       rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3510                          NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3511       pfrc = &(*pfrc)->next;
3512     }
3513 
3514     if (rv != NGTCP2_ERR_NOBUF) {
3515       for (; ngtcp2_ksl_len(&pktns->crypto.tx.frq);) {
3516         left = ngtcp2_ppe_left(ppe);
3517 
3518         crypto_offset = conn_cryptofrq_unacked_offset(conn, pktns);
3519         if (crypto_offset == (size_t)-1) {
3520           conn_cryptofrq_clear(conn, pktns);
3521           break;
3522         }
3523 
3524         left = ngtcp2_pkt_crypto_max_datalen(crypto_offset, left, left);
3525 
3526         if (left == (size_t)-1) {
3527           break;
3528         }
3529 
3530         rv = conn_cryptofrq_pop(conn, &nfrc, pktns, left);
3531         if (rv != 0) {
3532           assert(ngtcp2_err_is_fatal(rv));
3533           return rv;
3534         }
3535 
3536         if (nfrc == NULL) {
3537           break;
3538         }
3539 
3540         rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3541         if (rv != 0) {
3542           assert(0);
3543         }
3544 
3545         *pfrc = nfrc;
3546         pfrc = &(*pfrc)->next;
3547 
3548         pkt_empty = 0;
3549         rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3550                            NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3551       }
3552     }
3553 
3554     /* Write MAX_STREAM_ID after RESET_STREAM so that we can extend stream
3555        ID space in one packet. */
3556     if (rv != NGTCP2_ERR_NOBUF && *pfrc == NULL &&
3557         conn->remote.bidi.unsent_max_streams > conn->remote.bidi.max_streams) {
3558       rv = conn_call_extend_max_remote_streams_bidi(
3559           conn, conn->remote.bidi.unsent_max_streams);
3560       if (rv != 0) {
3561         assert(ngtcp2_err_is_fatal(rv));
3562         return rv;
3563       }
3564 
3565       rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3566       if (rv != 0) {
3567         assert(ngtcp2_err_is_fatal(rv));
3568         return rv;
3569       }
3570       nfrc->fr.type = NGTCP2_FRAME_MAX_STREAMS_BIDI;
3571       nfrc->fr.max_streams.max_streams = conn->remote.bidi.unsent_max_streams;
3572       *pfrc = nfrc;
3573 
3574       conn->remote.bidi.max_streams = conn->remote.bidi.unsent_max_streams;
3575 
3576       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &(*pfrc)->fr);
3577       if (rv != 0) {
3578         assert(NGTCP2_ERR_NOBUF == rv);
3579       } else {
3580         pkt_empty = 0;
3581         rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3582                            NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3583         pfrc = &(*pfrc)->next;
3584       }
3585     }
3586 
3587     if (rv != NGTCP2_ERR_NOBUF && *pfrc == NULL) {
3588       if (conn->remote.uni.unsent_max_streams > conn->remote.uni.max_streams) {
3589         rv = conn_call_extend_max_remote_streams_uni(
3590             conn, conn->remote.uni.unsent_max_streams);
3591         if (rv != 0) {
3592           assert(ngtcp2_err_is_fatal(rv));
3593           return rv;
3594         }
3595 
3596         rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3597         if (rv != 0) {
3598           assert(ngtcp2_err_is_fatal(rv));
3599           return rv;
3600         }
3601         nfrc->fr.type = NGTCP2_FRAME_MAX_STREAMS_UNI;
3602         nfrc->fr.max_streams.max_streams = conn->remote.uni.unsent_max_streams;
3603         *pfrc = nfrc;
3604 
3605         conn->remote.uni.max_streams = conn->remote.uni.unsent_max_streams;
3606 
3607         rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd,
3608                                          &(*pfrc)->fr);
3609         if (rv != 0) {
3610           assert(NGTCP2_ERR_NOBUF == rv);
3611         } else {
3612           pkt_empty = 0;
3613           rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3614                              NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3615           pfrc = &(*pfrc)->next;
3616         }
3617       }
3618     }
3619 
3620     if (rv != NGTCP2_ERR_NOBUF) {
3621       for (; !ngtcp2_pq_empty(&conn->tx.strmq);) {
3622         strm = ngtcp2_conn_tx_strmq_top(conn);
3623 
3624         if (!(strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
3625             conn_should_send_max_stream_data(conn, strm)) {
3626           rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3627           if (rv != 0) {
3628             assert(ngtcp2_err_is_fatal(rv));
3629             return rv;
3630           }
3631 
3632           if (conn->local.settings.max_stream_window &&
3633               strm->tx.last_max_stream_data_ts != UINT64_MAX &&
3634               ts - strm->tx.last_max_stream_data_ts <
3635                   NGTCP2_FLOW_WINDOW_RTT_FACTOR * cstat->smoothed_rtt &&
3636               conn->local.settings.max_stream_window > strm->rx.window) {
3637             target_max_data =
3638                 NGTCP2_FLOW_WINDOW_SCALING_FACTOR * strm->rx.window;
3639             if (target_max_data > conn->local.settings.max_stream_window) {
3640               target_max_data = conn->local.settings.max_stream_window;
3641             }
3642 
3643             delta = target_max_data - strm->rx.window;
3644             if (strm->rx.unsent_max_offset + delta > NGTCP2_MAX_VARINT) {
3645               delta = NGTCP2_MAX_VARINT - strm->rx.unsent_max_offset;
3646             }
3647 
3648             strm->rx.window = target_max_data;
3649           } else {
3650             delta = 0;
3651           }
3652 
3653           strm->tx.last_max_stream_data_ts = ts;
3654 
3655           nfrc->fr.type = NGTCP2_FRAME_MAX_STREAM_DATA;
3656           nfrc->fr.max_stream_data.stream_id = strm->stream_id;
3657           nfrc->fr.max_stream_data.max_stream_data =
3658               strm->rx.unsent_max_offset + delta;
3659           ngtcp2_list_insert(nfrc, pfrc);
3660 
3661           rv =
3662               conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3663           if (rv != 0) {
3664             assert(NGTCP2_ERR_NOBUF == rv);
3665             break;
3666           }
3667 
3668           pkt_empty = 0;
3669           rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3670                              NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3671           pfrc = &(*pfrc)->next;
3672           strm->rx.max_offset = strm->rx.unsent_max_offset =
3673               nfrc->fr.max_stream_data.max_stream_data;
3674         }
3675 
3676         if (ngtcp2_strm_streamfrq_empty(strm)) {
3677           ngtcp2_conn_tx_strmq_pop(conn);
3678           continue;
3679         }
3680 
3681         stream_offset = ngtcp2_strm_streamfrq_unacked_offset(strm);
3682         if (stream_offset == (uint64_t)-1) {
3683           ngtcp2_strm_streamfrq_clear(strm);
3684           ngtcp2_conn_tx_strmq_pop(conn);
3685           continue;
3686         }
3687 
3688         left = ngtcp2_ppe_left(ppe);
3689 
3690         left = ngtcp2_pkt_stream_max_datalen(strm->stream_id, stream_offset,
3691                                              left, left);
3692 
3693         if (left == (size_t)-1) {
3694           break;
3695         }
3696 
3697         rv = ngtcp2_strm_streamfrq_pop(strm, &nfrc, left);
3698         if (rv != 0) {
3699           assert(ngtcp2_err_is_fatal(rv));
3700           return rv;
3701         }
3702 
3703         if (nfrc == NULL) {
3704           /* TODO Why? */
3705           break;
3706         }
3707 
3708         rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3709         if (rv != 0) {
3710           assert(0);
3711         }
3712 
3713         *pfrc = nfrc;
3714         pfrc = &(*pfrc)->next;
3715 
3716         pkt_empty = 0;
3717         rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3718                            NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3719 
3720         if (ngtcp2_strm_streamfrq_empty(strm)) {
3721           ngtcp2_conn_tx_strmq_pop(conn);
3722           continue;
3723         }
3724 
3725         ngtcp2_conn_tx_strmq_pop(conn);
3726         ++strm->cycle;
3727         rv = ngtcp2_conn_tx_strmq_push(conn, strm);
3728         if (rv != 0) {
3729           assert(ngtcp2_err_is_fatal(rv));
3730           return rv;
3731         }
3732       }
3733     }
3734 
3735     if (rv != NGTCP2_ERR_NOBUF && !send_stream && !send_datagram &&
3736         !(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
3737         pktns->rtb.num_retransmittable && pktns->tx.frq == NULL &&
3738         pktns->rtb.probe_pkt_left) {
3739       num_reclaimed = ngtcp2_rtb_reclaim_on_pto(&pktns->rtb, conn, pktns,
3740                                                 pktns->rtb.probe_pkt_left + 1);
3741       if (num_reclaimed < 0) {
3742         return rv;
3743       }
3744       if (num_reclaimed) {
3745         goto build_pkt;
3746       }
3747 
3748       /* We had pktns->rtb.num_retransmittable > 0 but the contents of
3749          those packets have been acknowledged (i.e., retransmission in
3750          another packet).  In this case, we don't have to send any
3751          probe packet. */
3752       if (pktns->rtb.num_retransmittable == 0) {
3753         pktns->rtb.probe_pkt_left = 0;
3754         ngtcp2_conn_set_loss_detection_timer(conn, ts);
3755       }
3756     }
3757   } else {
3758     pfrc = conn->pkt.pfrc;
3759     rtb_entry_flags |= conn->pkt.rtb_entry_flags;
3760     pkt_empty = conn->pkt.pkt_empty;
3761     hd_logged = conn->pkt.hd_logged;
3762   }
3763 
3764   left = ngtcp2_ppe_left(ppe);
3765 
3766   if (rv != NGTCP2_ERR_NOBUF && send_stream && *pfrc == NULL &&
3767       (ndatalen = ngtcp2_pkt_stream_max_datalen(
3768            vmsg->stream.strm->stream_id, vmsg->stream.strm->tx.offset, ndatalen,
3769            left)) != (size_t)-1 &&
3770       (ndatalen || datalen == 0)) {
3771     datacnt = ngtcp2_vec_copy_at_most(data, NGTCP2_MAX_STREAM_DATACNT,
3772                                       vmsg->stream.data, vmsg->stream.datacnt,
3773                                       (size_t)ndatalen);
3774     ndatalen = ngtcp2_vec_len(data, datacnt);
3775 
3776     assert((datacnt == 0 && datalen == 0) || (datacnt && datalen));
3777 
3778     rv = ngtcp2_frame_chain_stream_datacnt_new(&nfrc, datacnt, conn->mem);
3779     if (rv != 0) {
3780       assert(ngtcp2_err_is_fatal(rv));
3781       return rv;
3782     }
3783 
3784     nfrc->fr.stream.type = NGTCP2_FRAME_STREAM;
3785     nfrc->fr.stream.flags = 0;
3786     nfrc->fr.stream.stream_id = vmsg->stream.strm->stream_id;
3787     nfrc->fr.stream.offset = vmsg->stream.strm->tx.offset;
3788     nfrc->fr.stream.datacnt = datacnt;
3789     ngtcp2_vec_copy(nfrc->fr.stream.data, data, datacnt);
3790 
3791     fin = (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_FIN) &&
3792           ndatalen == datalen;
3793     nfrc->fr.stream.fin = (uint8_t)fin;
3794 
3795     rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3796     if (rv != 0) {
3797       assert(0);
3798     }
3799 
3800     *pfrc = nfrc;
3801     pfrc = &(*pfrc)->next;
3802 
3803     pkt_empty = 0;
3804     rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING |
3805                        NGTCP2_RTB_ENTRY_FLAG_RETRANSMITTABLE;
3806 
3807     vmsg->stream.strm->tx.offset += ndatalen;
3808     conn->tx.offset += ndatalen;
3809 
3810     if (fin) {
3811       ngtcp2_strm_shutdown(vmsg->stream.strm, NGTCP2_STRM_FLAG_SHUT_WR);
3812     }
3813 
3814     if (vmsg->stream.pdatalen) {
3815       *vmsg->stream.pdatalen = (ngtcp2_ssize)ndatalen;
3816     }
3817   } else {
3818     send_stream = 0;
3819   }
3820 
3821   if (rv != NGTCP2_ERR_NOBUF && send_datagram &&
3822       left >= ngtcp2_pkt_datagram_framelen((size_t)datalen)) {
3823     if (conn->callbacks.ack_datagram || conn->callbacks.lost_datagram) {
3824       rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
3825       if (rv != 0) {
3826         assert(ngtcp2_err_is_fatal(rv));
3827         return rv;
3828       }
3829 
3830       nfrc->fr.datagram.type = NGTCP2_FRAME_DATAGRAM_LEN;
3831       nfrc->fr.datagram.dgram_id = vmsg->datagram.dgram_id;
3832       nfrc->fr.datagram.datacnt = vmsg->datagram.datacnt;
3833       nfrc->fr.datagram.data = (ngtcp2_vec *)vmsg->datagram.data;
3834 
3835       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &nfrc->fr);
3836       assert(rv == 0);
3837 
3838       /* Because DATAGRAM will not be retransmitted, we do not use
3839          data anymore.  Just nullify it.  The only reason to keep
3840          track a frame is keep dgram_id to pass it to
3841          ngtcp2_ack_datagram or ngtcp2_lost_datagram callbacks. */
3842       nfrc->fr.datagram.datacnt = 0;
3843       nfrc->fr.datagram.data = NULL;
3844 
3845       *pfrc = nfrc;
3846       pfrc = &(*pfrc)->next;
3847     } else {
3848       lfr.datagram.type = NGTCP2_FRAME_DATAGRAM_LEN;
3849       lfr.datagram.datacnt = vmsg->datagram.datacnt;
3850       lfr.datagram.data = (ngtcp2_vec *)vmsg->datagram.data;
3851 
3852       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3853       assert(rv == 0);
3854     }
3855 
3856     pkt_empty = 0;
3857     rtb_entry_flags |=
3858         NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING | NGTCP2_RTB_ENTRY_FLAG_DATAGRAM;
3859 
3860     if (vmsg->datagram.paccepted) {
3861       *vmsg->datagram.paccepted = 1;
3862     }
3863   } else {
3864     send_datagram = 0;
3865   }
3866 
3867   if (pkt_empty) {
3868     assert(rv == 0 || NGTCP2_ERR_NOBUF == rv);
3869     if (rv == 0 && stream_blocked && ngtcp2_conn_get_max_data_left(conn)) {
3870       return NGTCP2_ERR_STREAM_DATA_BLOCKED;
3871     }
3872 
3873     keep_alive_expired = conn_keep_alive_expired(conn, ts);
3874 
3875     if (conn->pktns.rtb.probe_pkt_left == 0 && !keep_alive_expired) {
3876       return 0;
3877     }
3878   } else if (write_more) {
3879     conn->pkt.pfrc = pfrc;
3880     conn->pkt.pkt_empty = pkt_empty;
3881     conn->pkt.rtb_entry_flags = rtb_entry_flags;
3882     conn->pkt.hd_logged = hd_logged;
3883     conn->flags |= NGTCP2_CONN_FLAG_PPE_PENDING;
3884 
3885     assert(vmsg);
3886 
3887     switch (vmsg->type) {
3888     case NGTCP2_VMSG_TYPE_STREAM:
3889       if (send_stream) {
3890         if (ngtcp2_ppe_left(ppe)) {
3891           return NGTCP2_ERR_WRITE_MORE;
3892         }
3893       } else if (ngtcp2_conn_get_max_data_left(conn) && stream_blocked) {
3894         return NGTCP2_ERR_STREAM_DATA_BLOCKED;
3895       }
3896       break;
3897     case NGTCP2_VMSG_TYPE_DATAGRAM:
3898       if (send_datagram && ngtcp2_ppe_left(ppe)) {
3899         return NGTCP2_ERR_WRITE_MORE;
3900       }
3901       /* If DATAGRAM cannot be written due to insufficient space,
3902          continue to create a packet with the hope that application
3903          calls ngtcp2_conn_writev_datagram again. */
3904       break;
3905     default:
3906       assert(0);
3907     }
3908   }
3909 
3910   if (!(rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
3911     if (pktns->tx.num_non_ack_pkt >= NGTCP2_MAX_NON_ACK_TX_PKT ||
3912         keep_alive_expired) {
3913       lfr.type = NGTCP2_FRAME_PING;
3914 
3915       rv = conn_ppe_write_frame_hd_log(conn, ppe, &hd_logged, hd, &lfr);
3916       if (rv != 0) {
3917         assert(rv == NGTCP2_ERR_NOBUF);
3918         /* TODO If buffer is too small, PING cannot be written if
3919            packet is still empty. */
3920       } else {
3921         rtb_entry_flags |= NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING;
3922         pktns->tx.num_non_ack_pkt = 0;
3923       }
3924     } else {
3925       ++pktns->tx.num_non_ack_pkt;
3926     }
3927   } else {
3928     pktns->tx.num_non_ack_pkt = 0;
3929   }
3930 
3931   /* TODO Push STREAM frame back to ngtcp2_strm if there is an error
3932      before ngtcp2_rtb_entry is safely created and added. */
3933   if (require_padding ||
3934       /* Making full sized packet will help GSO a bit */
3935       ngtcp2_ppe_left(ppe) < 10) {
3936     lfr.padding.len = ngtcp2_ppe_padding(ppe);
3937   } else {
3938     lfr.padding.len = ngtcp2_ppe_padding_size(ppe, min_pktlen);
3939   }
3940 
3941   if (lfr.padding.len) {
3942     lfr.type = NGTCP2_FRAME_PADDING;
3943     padded = 1;
3944     ngtcp2_log_tx_fr(&conn->log, hd, &lfr);
3945     ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
3946   }
3947 
3948   nwrite = ngtcp2_ppe_final(ppe, NULL);
3949   if (nwrite < 0) {
3950     assert(ngtcp2_err_is_fatal((int)nwrite));
3951     return nwrite;
3952   }
3953 
3954   ++cc->ckm->use_count;
3955 
3956   ngtcp2_qlog_pkt_sent_end(&conn->qlog, hd, (size_t)nwrite);
3957 
3958   /* TODO ack-eliciting vs needs-tracking */
3959   /* probe packet needs tracking but it does not need ACK, could be lost. */
3960   if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) {
3961     if (pi) {
3962       conn_handle_tx_ecn(conn, pi, &rtb_entry_flags, pktns, hd, ts);
3963     }
3964 
3965     rv = ngtcp2_rtb_entry_new(&ent, hd, NULL, ts, (size_t)nwrite,
3966                               rtb_entry_flags, conn->mem);
3967     if (rv != 0) {
3968       assert(ngtcp2_err_is_fatal((int)nwrite));
3969       return rv;
3970     }
3971 
3972     if (*pfrc != pktns->tx.frq) {
3973       ent->frc = pktns->tx.frq;
3974       pktns->tx.frq = *pfrc;
3975       *pfrc = NULL;
3976     }
3977 
3978     if ((rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) &&
3979         pktns->rtb.num_ack_eliciting == 0 && conn->cc.event) {
3980       conn->cc.event(&conn->cc, &conn->cstat, NGTCP2_CC_EVENT_TYPE_TX_START,
3981                      ts);
3982     }
3983 
3984     rv = conn_on_pkt_sent(conn, &pktns->rtb, ent);
3985     if (rv != 0) {
3986       assert(ngtcp2_err_is_fatal(rv));
3987       ngtcp2_rtb_entry_del(ent, conn->mem);
3988       return rv;
3989     }
3990 
3991     if (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
3992       if (conn->cc.on_pkt_sent) {
3993         conn->cc.on_pkt_sent(
3994             &conn->cc, &conn->cstat,
3995             ngtcp2_cc_pkt_init(&cc_pkt, hd->pkt_num, (size_t)nwrite,
3996                                NGTCP2_PKTNS_ID_APPLICATION, ts));
3997       }
3998 
3999       if (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE) {
4000         conn_restart_timer_on_write(conn, ts);
4001       }
4002     }
4003   } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
4004     conn_handle_tx_ecn(conn, pi, NULL, pktns, hd, ts);
4005   }
4006 
4007   conn->flags &= (uint16_t)~NGTCP2_CONN_FLAG_PPE_PENDING;
4008 
4009   if (pktns->rtb.probe_pkt_left &&
4010       (rtb_entry_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
4011     --pktns->rtb.probe_pkt_left;
4012 
4013     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "probe pkt size=%td",
4014                     nwrite);
4015   }
4016 
4017   conn_update_keep_alive_last_ts(conn, ts);
4018 
4019   conn->dcid.current.bytes_sent += (uint64_t)nwrite;
4020 
4021   conn->tx.pacing.pktlen += (size_t)nwrite;
4022 
4023   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
4024 
4025   ++pktns->tx.last_pkt_num;
4026 
4027   return nwrite;
4028 }
4029 
ngtcp2_conn_write_single_frame_pkt(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint8_t type,const ngtcp2_cid * dcid,ngtcp2_frame * fr,uint8_t rtb_flags,const ngtcp2_path * path,ngtcp2_tstamp ts)4030 ngtcp2_ssize ngtcp2_conn_write_single_frame_pkt(
4031     ngtcp2_conn *conn, ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen,
4032     uint8_t type, const ngtcp2_cid *dcid, ngtcp2_frame *fr, uint8_t rtb_flags,
4033     const ngtcp2_path *path, ngtcp2_tstamp ts) {
4034   int rv;
4035   ngtcp2_ppe ppe;
4036   ngtcp2_pkt_hd hd;
4037   ngtcp2_frame lfr;
4038   ngtcp2_ssize nwrite;
4039   ngtcp2_crypto_cc cc;
4040   ngtcp2_pktns *pktns;
4041   uint8_t flags;
4042   ngtcp2_rtb_entry *rtbent;
4043   int padded = 0;
4044   const ngtcp2_cid *scid;
4045 
4046   switch (type) {
4047   case NGTCP2_PKT_INITIAL:
4048     pktns = conn->in_pktns;
4049     flags = conn_pkt_flags_long(conn);
4050     scid = &conn->oscid;
4051     break;
4052   case NGTCP2_PKT_HANDSHAKE:
4053     pktns = conn->hs_pktns;
4054     flags = conn_pkt_flags_long(conn);
4055     scid = &conn->oscid;
4056     break;
4057   case NGTCP2_PKT_SHORT:
4058     /* 0 means Short packet. */
4059     pktns = &conn->pktns;
4060     flags = conn_pkt_flags_short(conn);
4061     scid = NULL;
4062     break;
4063   default:
4064     /* We don't support 0-RTT packet in this function. */
4065     assert(0);
4066     abort();
4067   }
4068 
4069   cc.aead = pktns->crypto.ctx.aead;
4070   cc.hp = pktns->crypto.ctx.hp;
4071   cc.ckm = pktns->crypto.tx.ckm;
4072   cc.hp_ctx = pktns->crypto.tx.hp_ctx;
4073   cc.encrypt = conn->callbacks.encrypt;
4074   cc.hp_mask = conn->callbacks.hp_mask;
4075 
4076   ngtcp2_pkt_hd_init(&hd, flags, type, dcid, scid, pktns->tx.last_pkt_num + 1,
4077                      pktns_select_pkt_numlen(pktns), conn->version, 0);
4078 
4079   ngtcp2_ppe_init(&ppe, dest, destlen, &cc);
4080 
4081   rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
4082   if (rv != 0) {
4083     assert(NGTCP2_ERR_NOBUF == rv);
4084     return 0;
4085   }
4086 
4087   if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
4088     return 0;
4089   }
4090 
4091   ngtcp2_log_tx_pkt_hd(&conn->log, &hd);
4092   ngtcp2_qlog_pkt_sent_start(&conn->qlog);
4093 
4094   rv = conn_ppe_write_frame(conn, &ppe, &hd, fr);
4095   if (rv != 0) {
4096     assert(NGTCP2_ERR_NOBUF == rv);
4097     return 0;
4098   }
4099 
4100   lfr.type = NGTCP2_FRAME_PADDING;
4101   switch (fr->type) {
4102   case NGTCP2_FRAME_PATH_CHALLENGE:
4103   case NGTCP2_FRAME_PATH_RESPONSE:
4104     if (!conn->server || destlen >= NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
4105       lfr.padding.len = ngtcp2_ppe_padding(&ppe);
4106     } else {
4107       lfr.padding.len = 0;
4108     }
4109     break;
4110   default:
4111     if (type == NGTCP2_PKT_SHORT) {
4112       lfr.padding.len =
4113           ngtcp2_ppe_padding_size(&ppe, conn_min_short_pktlen(conn));
4114     } else {
4115       lfr.padding.len = ngtcp2_ppe_padding_hp_sample(&ppe);
4116     }
4117   }
4118   if (lfr.padding.len) {
4119     padded = 1;
4120     ngtcp2_log_tx_fr(&conn->log, &hd, &lfr);
4121     ngtcp2_qlog_write_frame(&conn->qlog, &lfr);
4122   }
4123 
4124   nwrite = ngtcp2_ppe_final(&ppe, NULL);
4125   if (nwrite < 0) {
4126     return nwrite;
4127   }
4128 
4129   if (type == NGTCP2_PKT_SHORT) {
4130     ++cc.ckm->use_count;
4131   }
4132 
4133   ngtcp2_qlog_pkt_sent_end(&conn->qlog, &hd, (size_t)nwrite);
4134 
4135   /* Do this when we are sure that there is no error. */
4136   switch (fr->type) {
4137   case NGTCP2_FRAME_ACK:
4138   case NGTCP2_FRAME_ACK_ECN:
4139     ngtcp2_acktr_commit_ack(&pktns->acktr);
4140     ngtcp2_acktr_add_ack(&pktns->acktr, hd.pkt_num, fr->ack.largest_ack);
4141     break;
4142   }
4143 
4144   if (((rtb_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) || padded) &&
4145       (!path || ngtcp2_path_eq(&conn->dcid.current.ps.path, path))) {
4146     if (pi) {
4147       conn_handle_tx_ecn(conn, pi, &rtb_flags, pktns, &hd, ts);
4148     }
4149 
4150     rv = ngtcp2_rtb_entry_new(&rtbent, &hd, NULL, ts, (size_t)nwrite, rtb_flags,
4151                               conn->mem);
4152     if (rv != 0) {
4153       return rv;
4154     }
4155 
4156     rv = conn_on_pkt_sent(conn, &pktns->rtb, rtbent);
4157     if (rv != 0) {
4158       ngtcp2_rtb_entry_del(rtbent, conn->mem);
4159       return rv;
4160     }
4161 
4162     if (rtb_flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING) {
4163       if (conn->flags & NGTCP2_CONN_FLAG_RESTART_IDLE_TIMER_ON_WRITE) {
4164         conn_restart_timer_on_write(conn, ts);
4165       }
4166 
4167       if (pktns->rtb.probe_pkt_left && path &&
4168           ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
4169         --pktns->rtb.probe_pkt_left;
4170 
4171         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "probe pkt size=%td",
4172                         nwrite);
4173       }
4174     }
4175   } else if (pi && conn->tx.ecn.state == NGTCP2_ECN_STATE_CAPABLE) {
4176     conn_handle_tx_ecn(conn, pi, NULL, pktns, &hd, ts);
4177   }
4178 
4179   if (path && ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
4180     conn_update_keep_alive_last_ts(conn, ts);
4181   }
4182 
4183   conn->tx.pacing.pktlen += (size_t)nwrite;
4184 
4185   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
4186 
4187   ++pktns->tx.last_pkt_num;
4188 
4189   return nwrite;
4190 }
4191 
4192 /*
4193  * conn_process_early_rtb makes any pending 0RTT packet Short packet.
4194  */
conn_process_early_rtb(ngtcp2_conn * conn)4195 static void conn_process_early_rtb(ngtcp2_conn *conn) {
4196   ngtcp2_rtb_entry *ent;
4197   ngtcp2_rtb *rtb = &conn->pktns.rtb;
4198   ngtcp2_ksl_it it;
4199 
4200   for (it = ngtcp2_rtb_head(rtb); !ngtcp2_ksl_it_end(&it);
4201        ngtcp2_ksl_it_next(&it)) {
4202     ent = ngtcp2_ksl_it_get(&it);
4203 
4204     if ((ent->hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) == 0 ||
4205         ent->hd.type != NGTCP2_PKT_0RTT) {
4206       continue;
4207     }
4208 
4209     /*  0-RTT packet is retransmitted as a Short packet. */
4210     ent->hd.flags &= (uint8_t)~NGTCP2_PKT_FLAG_LONG_FORM;
4211     ent->hd.type = NGTCP2_PKT_SHORT;
4212   }
4213 }
4214 
4215 /*
4216  * conn_handshake_remnants_left returns nonzero if there may be
4217  * handshake packets the local endpoint has to send, including new
4218  * packets and lost ones.
4219  */
conn_handshake_remnants_left(ngtcp2_conn * conn)4220 static int conn_handshake_remnants_left(ngtcp2_conn *conn) {
4221   ngtcp2_pktns *in_pktns = conn->in_pktns;
4222   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
4223 
4224   return !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) ||
4225          (in_pktns && (in_pktns->rtb.num_retransmittable ||
4226                        ngtcp2_ksl_len(&in_pktns->crypto.tx.frq))) ||
4227          (hs_pktns && (hs_pktns->rtb.num_retransmittable ||
4228                        ngtcp2_ksl_len(&hs_pktns->crypto.tx.frq)));
4229 }
4230 
4231 /*
4232  * conn_retire_dcid_seq retires destination connection ID denoted by
4233  * |seq|.
4234  *
4235  * This function returns 0 if it succeeds, or one of the following
4236  * negative error codes:
4237  *
4238  * NGTCP2_ERR_NOMEM
4239  *     Out of memory.
4240  */
conn_retire_dcid_seq(ngtcp2_conn * conn,uint64_t seq)4241 static int conn_retire_dcid_seq(ngtcp2_conn *conn, uint64_t seq) {
4242   ngtcp2_pktns *pktns = &conn->pktns;
4243   ngtcp2_frame_chain *nfrc;
4244   int rv;
4245 
4246   rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
4247   if (rv != 0) {
4248     return rv;
4249   }
4250 
4251   nfrc->fr.type = NGTCP2_FRAME_RETIRE_CONNECTION_ID;
4252   nfrc->fr.retire_connection_id.seq = seq;
4253   nfrc->next = pktns->tx.frq;
4254   pktns->tx.frq = nfrc;
4255 
4256   return 0;
4257 }
4258 
4259 /*
4260  * conn_retire_dcid retires |dcid|.
4261  *
4262  * This function returns 0 if it succeeds, or one of the following
4263  * negative error codes:
4264  *
4265  * NGTCP2_ERR_NOMEM
4266  *     Out of memory
4267  */
conn_retire_dcid(ngtcp2_conn * conn,const ngtcp2_dcid * dcid,ngtcp2_tstamp ts)4268 static int conn_retire_dcid(ngtcp2_conn *conn, const ngtcp2_dcid *dcid,
4269                             ngtcp2_tstamp ts) {
4270   ngtcp2_ringbuf *rb = &conn->dcid.retired;
4271   ngtcp2_dcid *dest, *stale_dcid;
4272   int rv;
4273 
4274   assert(dcid->cid.datalen);
4275 
4276   if (ngtcp2_ringbuf_full(rb)) {
4277     stale_dcid = ngtcp2_ringbuf_get(rb, 0);
4278     rv = conn_call_deactivate_dcid(conn, stale_dcid);
4279     if (rv != 0) {
4280       return rv;
4281     }
4282 
4283     ngtcp2_ringbuf_pop_front(rb);
4284   }
4285 
4286   dest = ngtcp2_ringbuf_push_back(rb);
4287   ngtcp2_dcid_copy(dest, dcid);
4288   dest->retired_ts = ts;
4289 
4290   return conn_retire_dcid_seq(conn, dcid->seq);
4291 }
4292 
4293 /*
4294  * conn_bind_dcid stores the DCID to |*pdcid| bound to |path|.  If
4295  * such DCID is not found, bind the new DCID to |path| and stores it
4296  * to |*pdcid|.  If a remote endpoint uses zero-length connection ID,
4297  * the pointer to conn->dcid.current is assigned to |*pdcid|.
4298  *
4299  * This function returns 0 if it succeeds, or one of the following
4300  * negative error codes:
4301  *
4302  * NGTCP2_ERR_CONN_ID_BLOCKED
4303  *     No unused DCID is available
4304  * NGTCP2_ERR_NOMEM
4305  *     Out of memory
4306  */
conn_bind_dcid(ngtcp2_conn * conn,ngtcp2_dcid ** pdcid,const ngtcp2_path * path,ngtcp2_tstamp ts)4307 static int conn_bind_dcid(ngtcp2_conn *conn, ngtcp2_dcid **pdcid,
4308                           const ngtcp2_path *path, ngtcp2_tstamp ts) {
4309   ngtcp2_dcid *dcid, *ndcid;
4310   ngtcp2_cid cid;
4311   size_t i, len;
4312   int rv;
4313 
4314   assert(!ngtcp2_path_eq(&conn->dcid.current.ps.path, path));
4315   assert(!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path));
4316   assert(!conn->pv || !(conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) ||
4317          !ngtcp2_path_eq(&conn->pv->fallback_dcid.ps.path, path));
4318 
4319   len = ngtcp2_ringbuf_len(&conn->dcid.bound);
4320   for (i = 0; i < len; ++i) {
4321     dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
4322 
4323     if (ngtcp2_path_eq(&dcid->ps.path, path)) {
4324       *pdcid = dcid;
4325       return 0;
4326     }
4327   }
4328 
4329   if (conn->dcid.current.cid.datalen == 0) {
4330     ndcid = ngtcp2_ringbuf_push_back(&conn->dcid.bound);
4331     ngtcp2_cid_zero(&cid);
4332     ngtcp2_dcid_init(ndcid, ++conn->dcid.zerolen_seq, &cid, NULL);
4333     ngtcp2_dcid_set_path(ndcid, path);
4334 
4335     *pdcid = ndcid;
4336 
4337     return 0;
4338   }
4339 
4340   if (ngtcp2_ringbuf_len(&conn->dcid.unused) == 0) {
4341     return NGTCP2_ERR_CONN_ID_BLOCKED;
4342   }
4343 
4344   if (ngtcp2_ringbuf_full(&conn->dcid.bound)) {
4345     dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, 0);
4346     rv = conn_retire_dcid(conn, dcid, ts);
4347     if (rv != 0) {
4348       return rv;
4349     }
4350   }
4351 
4352   dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
4353   ndcid = ngtcp2_ringbuf_push_back(&conn->dcid.bound);
4354 
4355   ngtcp2_dcid_copy(ndcid, dcid);
4356   ndcid->bound_ts = ts;
4357   ngtcp2_dcid_set_path(ndcid, path);
4358 
4359   ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
4360 
4361   *pdcid = ndcid;
4362 
4363   return 0;
4364 }
4365 
4366 /*
4367  * conn_stop_pv stops the path validation which is currently running.
4368  * This function does nothing if no path validation is currently being
4369  * performed.
4370  *
4371  * This function returns 0 if it succeeds, or one of the following
4372  * negative error codes:
4373  *
4374  * NGTCP2_ERR_NOMEM
4375  *     Out of memory
4376  */
conn_stop_pv(ngtcp2_conn * conn,ngtcp2_tstamp ts)4377 static int conn_stop_pv(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
4378   int rv = 0;
4379   ngtcp2_pv *pv = conn->pv;
4380 
4381   if (pv == NULL) {
4382     return 0;
4383   }
4384 
4385   if (pv->dcid.cid.datalen && pv->dcid.seq != conn->dcid.current.seq) {
4386     rv = conn_retire_dcid(conn, &pv->dcid, ts);
4387     if (rv != 0) {
4388       goto fin;
4389     }
4390   }
4391 
4392   if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
4393       pv->fallback_dcid.cid.datalen &&
4394       pv->fallback_dcid.seq != conn->dcid.current.seq &&
4395       pv->fallback_dcid.seq != pv->dcid.seq) {
4396     rv = conn_retire_dcid(conn, &pv->fallback_dcid, ts);
4397     if (rv != 0) {
4398       goto fin;
4399     }
4400   }
4401 
4402 fin:
4403   ngtcp2_pv_del(pv);
4404   conn->pv = NULL;
4405 
4406   return rv;
4407 }
4408 
4409 /*
4410  * conn_abort_pv aborts the current path validation and frees
4411  * resources allocated for it.  This function assumes that conn->pv is
4412  * not NULL.
4413  *
4414  * This function returns 0 if it succeeds, or one of the following
4415  * negative error codes:
4416  *
4417  * NGTCP2_ERR_NOMEM
4418  *     Out of memory
4419  * NGTCP2_ERR_CALLBACK_FAILURE
4420  *     User-defined callback function failed.
4421  */
conn_abort_pv(ngtcp2_conn * conn,ngtcp2_tstamp ts)4422 static int conn_abort_pv(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
4423   ngtcp2_pv *pv = conn->pv;
4424   int rv;
4425 
4426   assert(pv);
4427 
4428   if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
4429     rv = conn_call_path_validation(conn, pv,
4430                                    NGTCP2_PATH_VALIDATION_RESULT_ABORTED);
4431     if (rv != 0) {
4432       return rv;
4433     }
4434   }
4435 
4436   return conn_stop_pv(conn, ts);
4437 }
4438 
conn_update_dcid_max_udp_payload_size(ngtcp2_conn * conn,ngtcp2_dcid * dcid,size_t payloadlen)4439 static void conn_update_dcid_max_udp_payload_size(ngtcp2_conn *conn,
4440                                                   ngtcp2_dcid *dcid,
4441                                                   size_t payloadlen) {
4442   if (!conn->local.settings.assume_symmetric_path) {
4443     return;
4444   }
4445 
4446   dcid->max_udp_payload_size =
4447       ngtcp2_max(dcid->max_udp_payload_size, payloadlen);
4448 }
4449 
conn_shape_udp_payload(ngtcp2_conn * conn,const ngtcp2_dcid * dcid,size_t payloadlen)4450 static size_t conn_shape_udp_payload(ngtcp2_conn *conn, const ngtcp2_dcid *dcid,
4451                                      size_t payloadlen) {
4452   if (conn->local.settings.no_udp_payload_size_shaping) {
4453     return ngtcp2_min(payloadlen, conn->local.settings.max_udp_payload_size);
4454   }
4455 
4456   payloadlen =
4457       ngtcp2_min(payloadlen, conn->local.settings.max_udp_payload_size);
4458 
4459   return ngtcp2_min(payloadlen, dcid->max_udp_payload_size);
4460 }
4461 
4462 static void conn_reset_congestion_state(ngtcp2_conn *conn, ngtcp2_tstamp ts);
4463 
4464 /*
4465  * conn_on_path_validation_failed is called when path validation
4466  * fails.  This function may delete |pv|.
4467  *
4468  * This function returns 0 if it succeeds, or one of the following
4469  * negative error codes:
4470  *
4471  * NGTCP2_ERR_NOMEM
4472  *     Out of memory
4473  * NGTCP2_ERR_CALLBACK_FAILURE
4474  *     User-defined callback function failed.
4475  */
conn_on_path_validation_failed(ngtcp2_conn * conn,ngtcp2_pv * pv,ngtcp2_tstamp ts)4476 static int conn_on_path_validation_failed(ngtcp2_conn *conn, ngtcp2_pv *pv,
4477                                           ngtcp2_tstamp ts) {
4478   int rv;
4479 
4480   if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
4481     rv = conn_call_path_validation(conn, pv,
4482                                    NGTCP2_PATH_VALIDATION_RESULT_FAILURE);
4483     if (rv != 0) {
4484       return rv;
4485     }
4486   }
4487 
4488   if (pv->flags & NGTCP2_PV_FLAG_MTU_PROBE) {
4489     return NGTCP2_ERR_NO_VIABLE_PATH;
4490   }
4491 
4492   if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) {
4493     ngtcp2_dcid_copy(&conn->dcid.current, &pv->fallback_dcid);
4494     conn_reset_congestion_state(conn, ts);
4495   }
4496 
4497   return conn_stop_pv(conn, ts);
4498 }
4499 
4500 /*
4501  * conn_write_path_challenge writes a packet which includes
4502  * PATH_CHALLENGE frame into |dest| of length |destlen|.
4503  *
4504  * This function returns the number of bytes written to |dest|, or one
4505  * of the following negative error codes:
4506  *
4507  * NGTCP2_ERR_NOMEM
4508  *     Out of memory
4509  * NGTCP2_ERR_CALLBACK_FAILURE
4510  *     User-defined callback function failed.
4511  */
conn_write_path_challenge(ngtcp2_conn * conn,ngtcp2_path * path,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_tstamp ts)4512 static ngtcp2_ssize conn_write_path_challenge(ngtcp2_conn *conn,
4513                                               ngtcp2_path *path,
4514                                               ngtcp2_pkt_info *pi,
4515                                               uint8_t *dest, size_t destlen,
4516                                               ngtcp2_tstamp ts) {
4517   ngtcp2_ssize nwrite;
4518   ngtcp2_tstamp expiry;
4519   ngtcp2_pv *pv = conn->pv;
4520   ngtcp2_frame lfr;
4521   ngtcp2_duration timeout;
4522   uint8_t flags;
4523   uint64_t tx_left;
4524   int rv;
4525 
4526   if (ngtcp2_pv_validation_timed_out(pv, ts)) {
4527     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
4528                     "path validation was timed out");
4529     rv = conn_on_path_validation_failed(conn, pv, ts);
4530     if (rv != 0) {
4531       return rv;
4532     }
4533 
4534     /* We might set path to the one which we just failed validate.
4535        Set it to the current path here. */
4536     if (path) {
4537       ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
4538     }
4539 
4540     return 0;
4541   }
4542 
4543   ngtcp2_pv_handle_entry_expiry(pv, ts);
4544 
4545   if (!ngtcp2_pv_should_send_probe(pv)) {
4546     return 0;
4547   }
4548 
4549   rv = conn_call_get_path_challenge_data(conn, lfr.path_challenge.data);
4550   if (rv != 0) {
4551     return rv;
4552   }
4553 
4554   lfr.type = NGTCP2_FRAME_PATH_CHALLENGE;
4555 
4556   timeout = conn_compute_pto(conn, &conn->pktns);
4557   timeout = ngtcp2_max(timeout, 3 * conn->cstat.initial_rtt);
4558   expiry = ts + timeout * (1ULL << pv->round);
4559 
4560   destlen = conn_shape_udp_payload(conn, &pv->dcid, destlen);
4561 
4562   if (conn->server) {
4563     if (!(pv->dcid.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
4564       tx_left = conn_server_tx_left(conn, &pv->dcid);
4565       destlen = (size_t)ngtcp2_min((uint64_t)destlen, tx_left);
4566       if (destlen == 0) {
4567         return 0;
4568       }
4569     }
4570 
4571     if (destlen < NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
4572       flags = NGTCP2_PV_ENTRY_FLAG_UNDERSIZED;
4573     } else {
4574       flags = NGTCP2_PV_ENTRY_FLAG_NONE;
4575     }
4576   } else {
4577     flags = NGTCP2_PV_ENTRY_FLAG_NONE;
4578   }
4579 
4580   ngtcp2_pv_add_entry(pv, lfr.path_challenge.data, expiry, flags, ts);
4581 
4582   nwrite = ngtcp2_conn_write_single_frame_pkt(
4583       conn, pi, dest, destlen, NGTCP2_PKT_SHORT, &pv->dcid.cid, &lfr,
4584       NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING, &pv->dcid.ps.path, ts);
4585   if (nwrite <= 0) {
4586     return nwrite;
4587   }
4588 
4589   if (path) {
4590     ngtcp2_path_copy(path, &pv->dcid.ps.path);
4591   }
4592 
4593   if (ngtcp2_path_eq(&pv->dcid.ps.path, &conn->dcid.current.ps.path)) {
4594     conn->dcid.current.bytes_sent += (uint64_t)nwrite;
4595   } else {
4596     pv->dcid.bytes_sent += (uint64_t)nwrite;
4597   }
4598 
4599   return nwrite;
4600 }
4601 
4602 /*
4603  * conn_write_path_response writes a packet which includes
4604  * PATH_RESPONSE frame into |dest| of length |destlen|.
4605  *
4606  * This function returns the number of bytes written to |dest|, or one
4607  * of the following negative error codes:
4608  *
4609  * NGTCP2_ERR_NOMEM
4610  *     Out of memory
4611  * NGTCP2_ERR_CALLBACK_FAILURE
4612  *     User-defined callback function failed.
4613  */
conn_write_path_response(ngtcp2_conn * conn,ngtcp2_path * path,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_tstamp ts)4614 static ngtcp2_ssize conn_write_path_response(ngtcp2_conn *conn,
4615                                              ngtcp2_path *path,
4616                                              ngtcp2_pkt_info *pi, uint8_t *dest,
4617                                              size_t destlen, ngtcp2_tstamp ts) {
4618   ngtcp2_pv *pv = conn->pv;
4619   ngtcp2_path_challenge_entry *pcent = NULL;
4620   ngtcp2_dcid *dcid = NULL;
4621   ngtcp2_frame lfr;
4622   ngtcp2_ssize nwrite;
4623   int rv;
4624   uint64_t tx_left;
4625 
4626   for (; ngtcp2_ringbuf_len(&conn->rx.path_challenge);) {
4627     pcent = ngtcp2_ringbuf_get(&conn->rx.path_challenge, 0);
4628 
4629     if (ngtcp2_path_eq(&conn->dcid.current.ps.path, &pcent->ps.path)) {
4630       /* Send PATH_RESPONSE from conn_write_pkt. */
4631       return 0;
4632     }
4633 
4634     if (pv) {
4635       if (ngtcp2_path_eq(&pv->dcid.ps.path, &pcent->ps.path)) {
4636         dcid = &pv->dcid;
4637         break;
4638       }
4639       if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
4640           ngtcp2_path_eq(&pv->fallback_dcid.ps.path, &pcent->ps.path)) {
4641         dcid = &pv->fallback_dcid;
4642         break;
4643       }
4644     }
4645 
4646     if (conn->server) {
4647       break;
4648     }
4649 
4650     /* Client does not expect to respond to path validation against
4651        unknown path */
4652     ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge);
4653     pcent = NULL;
4654   }
4655 
4656   if (pcent == NULL) {
4657     return 0;
4658   }
4659 
4660   if (dcid == NULL) {
4661     /* client is expected to have |path| in conn->dcid.current or
4662        conn->pv. */
4663     assert(conn->server);
4664 
4665     rv = conn_bind_dcid(conn, &dcid, &pcent->ps.path, ts);
4666     if (rv != 0) {
4667       if (ngtcp2_err_is_fatal(rv)) {
4668         return rv;
4669       }
4670       return 0;
4671     }
4672   }
4673 
4674   destlen = conn_shape_udp_payload(conn, dcid, destlen);
4675 
4676   if (conn->server && !(dcid->flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
4677     tx_left = conn_server_tx_left(conn, dcid);
4678     destlen = (size_t)ngtcp2_min((uint64_t)destlen, tx_left);
4679     if (destlen == 0) {
4680       return 0;
4681     }
4682   }
4683 
4684   lfr.type = NGTCP2_FRAME_PATH_RESPONSE;
4685   memcpy(lfr.path_response.data, pcent->data, sizeof(lfr.path_response.data));
4686 
4687   nwrite = ngtcp2_conn_write_single_frame_pkt(
4688       conn, pi, dest, destlen, NGTCP2_PKT_SHORT, &dcid->cid, &lfr,
4689       NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING, &pcent->ps.path, ts);
4690   if (nwrite <= 0) {
4691     return nwrite;
4692   }
4693 
4694   if (path) {
4695     ngtcp2_path_copy(path, &pcent->ps.path);
4696   }
4697 
4698   ngtcp2_ringbuf_pop_front(&conn->rx.path_challenge);
4699 
4700   dcid->bytes_sent += (uint64_t)nwrite;
4701 
4702   return nwrite;
4703 }
4704 
ngtcp2_conn_write_pkt_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_tstamp ts)4705 ngtcp2_ssize ngtcp2_conn_write_pkt_versioned(ngtcp2_conn *conn,
4706                                              ngtcp2_path *path,
4707                                              int pkt_info_version,
4708                                              ngtcp2_pkt_info *pi, uint8_t *dest,
4709                                              size_t destlen, ngtcp2_tstamp ts) {
4710   return ngtcp2_conn_writev_stream_versioned(
4711       conn, path, pkt_info_version, pi, dest, destlen,
4712       /* pdatalen = */ NULL, NGTCP2_WRITE_STREAM_FLAG_NONE,
4713       /* stream_id = */ -1,
4714       /* datav = */ NULL, /* datavcnt = */ 0, ts);
4715 }
4716 
4717 /*
4718  * conn_on_version_negotiation is called when Version Negotiation
4719  * packet is received.  The function decodes the data in the buffer
4720  * pointed by |payload| whose length is |payloadlen| as Version
4721  * Negotiation packet payload.  The packet header is given in |hd|.
4722  *
4723  * This function returns 0 if it succeeds, or one of the following
4724  * negative error codes:
4725  *
4726  * NGTCP2_ERR_NOMEM
4727  *     Out of memory.
4728  * NGTCP2_ERR_CALLBACK_FAILURE
4729  *     User-defined callback function failed.
4730  * NGTCP2_ERR_INVALID_ARGUMENT
4731  *     Packet payload is badly formatted.
4732  */
conn_on_version_negotiation(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd,const uint8_t * payload,size_t payloadlen)4733 static int conn_on_version_negotiation(ngtcp2_conn *conn,
4734                                        const ngtcp2_pkt_hd *hd,
4735                                        const uint8_t *payload,
4736                                        size_t payloadlen) {
4737   uint32_t sv[16];
4738   uint32_t *p;
4739   int rv = 0;
4740   size_t nsv;
4741   size_t i;
4742 
4743   if (payloadlen % sizeof(uint32_t)) {
4744     return NGTCP2_ERR_INVALID_ARGUMENT;
4745   }
4746 
4747   if (payloadlen > sizeof(sv)) {
4748     p = ngtcp2_mem_malloc(conn->mem, payloadlen);
4749     if (p == NULL) {
4750       return NGTCP2_ERR_NOMEM;
4751     }
4752   } else {
4753     p = sv;
4754   }
4755 
4756   nsv = ngtcp2_pkt_decode_version_negotiation(p, payload, payloadlen);
4757 
4758   ngtcp2_log_rx_vn(&conn->log, hd, p, nsv);
4759 
4760   for (i = 0; i < nsv; ++i) {
4761     if (p[i] == conn->version) {
4762       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
4763                       "ignore Version Negotiation because it contains version "
4764                       "selected by client");
4765 
4766       rv = NGTCP2_ERR_INVALID_ARGUMENT;
4767       goto fin;
4768     }
4769   }
4770 
4771   rv = conn_call_recv_version_negotiation(conn, hd, p, nsv);
4772   if (rv != 0) {
4773     goto fin;
4774   }
4775 
4776   /* TODO Just move to the terminal state for now in order not to
4777      send CONNECTION_CLOSE frame. */
4778   conn->state = NGTCP2_CS_DRAINING;
4779 
4780 fin:
4781   if (p != sv) {
4782     ngtcp2_mem_free(conn->mem, p);
4783   }
4784 
4785   return rv;
4786 }
4787 
conn_tx_strmq_first_cycle(ngtcp2_conn * conn)4788 static uint64_t conn_tx_strmq_first_cycle(ngtcp2_conn *conn) {
4789   ngtcp2_strm *strm;
4790 
4791   if (ngtcp2_pq_empty(&conn->tx.strmq)) {
4792     return 0;
4793   }
4794 
4795   strm = ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
4796   return strm->cycle;
4797 }
4798 
ngtcp2_conn_tx_strmq_first_cycle(ngtcp2_conn * conn)4799 uint64_t ngtcp2_conn_tx_strmq_first_cycle(ngtcp2_conn *conn) {
4800   ngtcp2_strm *strm;
4801 
4802   if (ngtcp2_pq_empty(&conn->tx.strmq)) {
4803     return 0;
4804   }
4805 
4806   strm = ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
4807   return strm->cycle;
4808 }
4809 
ngtcp2_conn_resched_frames(ngtcp2_conn * conn,ngtcp2_pktns * pktns,ngtcp2_frame_chain ** pfrc)4810 int ngtcp2_conn_resched_frames(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
4811                                ngtcp2_frame_chain **pfrc) {
4812   ngtcp2_frame_chain **first = pfrc;
4813   ngtcp2_frame_chain *frc;
4814   ngtcp2_stream *sfr;
4815   ngtcp2_strm *strm;
4816   int rv;
4817 
4818   if (*pfrc == NULL) {
4819     return 0;
4820   }
4821 
4822   for (; *pfrc;) {
4823     switch ((*pfrc)->fr.type) {
4824     case NGTCP2_FRAME_STREAM:
4825       frc = *pfrc;
4826 
4827       *pfrc = frc->next;
4828       frc->next = NULL;
4829       sfr = &frc->fr.stream;
4830 
4831       strm = ngtcp2_conn_find_stream(conn, sfr->stream_id);
4832       if (!strm) {
4833         ngtcp2_frame_chain_del(frc, conn->mem);
4834         break;
4835       }
4836       rv = ngtcp2_strm_streamfrq_push(strm, frc);
4837       if (rv != 0) {
4838         ngtcp2_frame_chain_del(frc, conn->mem);
4839         return rv;
4840       }
4841       if (!ngtcp2_strm_is_tx_queued(strm)) {
4842         strm->cycle = conn_tx_strmq_first_cycle(conn);
4843         rv = ngtcp2_conn_tx_strmq_push(conn, strm);
4844         if (rv != 0) {
4845           return rv;
4846         }
4847       }
4848       break;
4849     case NGTCP2_FRAME_CRYPTO:
4850       frc = *pfrc;
4851 
4852       *pfrc = frc->next;
4853       frc->next = NULL;
4854 
4855       rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL,
4856                              &frc->fr.crypto.offset, frc);
4857       if (rv != 0) {
4858         assert(ngtcp2_err_is_fatal(rv));
4859         ngtcp2_frame_chain_del(frc, conn->mem);
4860         return rv;
4861       }
4862       break;
4863     default:
4864       pfrc = &(*pfrc)->next;
4865     }
4866   }
4867 
4868   *pfrc = pktns->tx.frq;
4869   pktns->tx.frq = *first;
4870 
4871   return 0;
4872 }
4873 
4874 /*
4875  * conn_on_retry is called when Retry packet is received.  The
4876  * function decodes the data in the buffer pointed by |pkt| whose
4877  * length is |pktlen| as Retry packet.  The length of long packet
4878  * header is given in |hdpktlen|.  |pkt| includes packet header.
4879  *
4880  * This function returns 0 if it succeeds, or one of the following
4881  * negative error codes:
4882  *
4883  * NGTCP2_ERR_NOMEM
4884  *     Out of memory.
4885  * NGTCP2_ERR_CALLBACK_FAILURE
4886  *     User-defined callback function failed.
4887  * NGTCP2_ERR_INVALID_ARGUMENT
4888  *     Packet payload is badly formatted.
4889  * NGTCP2_ERR_PROTO
4890  *     ODCID does not match; or Token is empty.
4891  */
conn_on_retry(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd,size_t hdpktlen,const uint8_t * pkt,size_t pktlen,ngtcp2_tstamp ts)4892 static int conn_on_retry(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd,
4893                          size_t hdpktlen, const uint8_t *pkt, size_t pktlen,
4894                          ngtcp2_tstamp ts) {
4895   int rv;
4896   ngtcp2_pkt_retry retry;
4897   ngtcp2_pktns *in_pktns = conn->in_pktns;
4898   ngtcp2_rtb *rtb = &conn->pktns.rtb;
4899   ngtcp2_rtb *in_rtb;
4900   uint8_t cidbuf[sizeof(retry.odcid.data) * 2 + 1];
4901   ngtcp2_vec *token;
4902 
4903   if (!in_pktns || conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) {
4904     return 0;
4905   }
4906 
4907   in_rtb = &in_pktns->rtb;
4908 
4909   rv = ngtcp2_pkt_decode_retry(&retry, pkt + hdpktlen, pktlen - hdpktlen);
4910   if (rv != 0) {
4911     return rv;
4912   }
4913 
4914   retry.odcid = conn->dcid.current.cid;
4915 
4916   rv = ngtcp2_pkt_verify_retry_tag(
4917       conn->version, &retry, pkt, pktlen, conn->callbacks.encrypt,
4918       &conn->crypto.retry_aead, &conn->crypto.retry_aead_ctx);
4919   if (rv != 0) {
4920     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
4921                     "unable to verify Retry packet integrity");
4922     return rv;
4923   }
4924 
4925   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT, "odcid=0x%s",
4926                   (const char *)ngtcp2_encode_hex(cidbuf, retry.odcid.data,
4927                                                   retry.odcid.datalen));
4928 
4929   if (retry.token.len == 0) {
4930     return NGTCP2_ERR_PROTO;
4931   }
4932 
4933   if (ngtcp2_cid_eq(&conn->dcid.current.cid, &hd->scid)) {
4934     return 0;
4935   }
4936 
4937   ngtcp2_qlog_retry_pkt_received(&conn->qlog, hd);
4938 
4939   /* DCID must be updated before invoking callback because client
4940      generates new initial keys there. */
4941   conn->dcid.current.cid = hd->scid;
4942   conn->retry_scid = hd->scid;
4943 
4944   conn->flags |= NGTCP2_CONN_FLAG_RECV_RETRY;
4945 
4946   rv = conn_call_recv_retry(conn, hd);
4947   if (rv != 0) {
4948     return rv;
4949   }
4950 
4951   conn->state = NGTCP2_CS_CLIENT_INITIAL;
4952 
4953   /* Just freeing memory is dangerous because we might free twice. */
4954 
4955   rv = ngtcp2_rtb_remove_all(rtb, conn, &conn->pktns, &conn->cstat);
4956   if (rv != 0) {
4957     return rv;
4958   }
4959 
4960   rv = ngtcp2_rtb_remove_all(in_rtb, conn, in_pktns, &conn->cstat);
4961   if (rv != 0) {
4962     return rv;
4963   }
4964 
4965   token = &conn->local.settings.token;
4966 
4967   ngtcp2_mem_free(conn->mem, token->base);
4968   token->base = NULL;
4969   token->len = 0;
4970 
4971   token->base = ngtcp2_mem_malloc(conn->mem, retry.token.len);
4972   if (token->base == NULL) {
4973     return NGTCP2_ERR_NOMEM;
4974   }
4975   token->len = retry.token.len;
4976 
4977   ngtcp2_cpymem(token->base, retry.token.base, retry.token.len);
4978 
4979   reset_conn_stat_recovery(&conn->cstat);
4980   conn_reset_congestion_state(conn, ts);
4981   conn_reset_ecn_validation_state(conn);
4982 
4983   return 0;
4984 }
4985 
ngtcp2_conn_detect_lost_pkt(ngtcp2_conn * conn,ngtcp2_pktns * pktns,ngtcp2_conn_stat * cstat,ngtcp2_tstamp ts)4986 int ngtcp2_conn_detect_lost_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
4987                                 ngtcp2_conn_stat *cstat, ngtcp2_tstamp ts) {
4988   return ngtcp2_rtb_detect_lost_pkt(&pktns->rtb, conn, pktns, cstat, ts);
4989 }
4990 
4991 /*
4992  * conn_recv_ack processes received ACK frame |fr|.  |pkt_ts| is the
4993  * timestamp when packet is received.  |ts| should be the current
4994  * time.  Usually they are the same, but for buffered packets,
4995  * |pkt_ts| would be earlier than |ts|.
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  * NGTCP2_ERR_ACK_FRAME
5003  *     ACK frame is malformed.
5004  * NGTCP2_ERR_PROTO
5005  *     |fr| acknowledges a packet this endpoint has not sent.
5006  * NGTCP2_ERR_CALLBACK_FAILURE
5007  *     User callback failed.
5008  */
conn_recv_ack(ngtcp2_conn * conn,ngtcp2_pktns * pktns,ngtcp2_ack * fr,ngtcp2_tstamp pkt_ts,ngtcp2_tstamp ts)5009 static int conn_recv_ack(ngtcp2_conn *conn, ngtcp2_pktns *pktns, ngtcp2_ack *fr,
5010                          ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
5011   int rv;
5012   ngtcp2_frame_chain *frc = NULL;
5013   ngtcp2_ssize num_acked;
5014   ngtcp2_conn_stat *cstat = &conn->cstat;
5015 
5016   if (pktns->tx.last_pkt_num < fr->largest_ack) {
5017     return NGTCP2_ERR_PROTO;
5018   }
5019 
5020   rv = ngtcp2_pkt_validate_ack(fr);
5021   if (rv != 0) {
5022     return rv;
5023   }
5024 
5025   ngtcp2_acktr_recv_ack(&pktns->acktr, fr);
5026 
5027   num_acked = ngtcp2_rtb_recv_ack(&pktns->rtb, fr, &conn->cstat, conn, pktns,
5028                                   pkt_ts, ts);
5029   if (num_acked < 0) {
5030     /* TODO assert this */
5031     assert(ngtcp2_err_is_fatal((int)num_acked));
5032     ngtcp2_frame_chain_list_del(frc, conn->mem);
5033     return (int)num_acked;
5034   }
5035 
5036   if (num_acked == 0) {
5037     return 0;
5038   }
5039 
5040   pktns->rtb.probe_pkt_left = 0;
5041 
5042   if (cstat->pto_count &&
5043       (conn->server || (conn->flags & NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED))) {
5044     /* Reset PTO count but no less than 2 to avoid frequent probe
5045        packet transmission. */
5046     cstat->pto_count = ngtcp2_min(cstat->pto_count, 2);
5047   }
5048 
5049   ngtcp2_conn_set_loss_detection_timer(conn, ts);
5050 
5051   return 0;
5052 }
5053 
5054 /*
5055  * conn_assign_recved_ack_delay_unscaled assigns
5056  * fr->ack_delay_unscaled.
5057  */
assign_recved_ack_delay_unscaled(ngtcp2_ack * fr,uint64_t ack_delay_exponent)5058 static void assign_recved_ack_delay_unscaled(ngtcp2_ack *fr,
5059                                              uint64_t ack_delay_exponent) {
5060   fr->ack_delay_unscaled =
5061       fr->ack_delay * (1ULL << ack_delay_exponent) * NGTCP2_MICROSECONDS;
5062 }
5063 
5064 /*
5065  * conn_recv_max_stream_data processes received MAX_STREAM_DATA frame
5066  * |fr|.
5067  *
5068  * This function returns 0 if it succeeds, or one of the following
5069  * negative error codes:
5070  *
5071  * NGTCP2_ERR_STREAM_STATE
5072  *     Stream ID indicates that it is a local stream, and the local
5073  *     endpoint has not initiated it; or stream is peer initiated
5074  *     unidirectional stream.
5075  * NGTCP2_ERR_STREAM_LIMIT
5076  *     Stream ID exceeds allowed limit.
5077  * NGTCP2_ERR_NOMEM
5078  *     Out of memory.
5079  */
conn_recv_max_stream_data(ngtcp2_conn * conn,const ngtcp2_max_stream_data * fr)5080 static int conn_recv_max_stream_data(ngtcp2_conn *conn,
5081                                      const ngtcp2_max_stream_data *fr) {
5082   ngtcp2_strm *strm;
5083   ngtcp2_idtr *idtr;
5084   int local_stream = conn_local_stream(conn, fr->stream_id);
5085   int bidi = bidi_stream(fr->stream_id);
5086   int rv;
5087 
5088   if (bidi) {
5089     if (local_stream) {
5090       if (conn->local.bidi.next_stream_id <= fr->stream_id) {
5091         return NGTCP2_ERR_STREAM_STATE;
5092       }
5093     } else if (conn->remote.bidi.max_streams <
5094                ngtcp2_ord_stream_id(fr->stream_id)) {
5095       return NGTCP2_ERR_STREAM_LIMIT;
5096     }
5097 
5098     idtr = &conn->remote.bidi.idtr;
5099   } else {
5100     if (!local_stream || conn->local.uni.next_stream_id <= fr->stream_id) {
5101       return NGTCP2_ERR_STREAM_STATE;
5102     }
5103 
5104     idtr = &conn->remote.uni.idtr;
5105   }
5106 
5107   strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
5108   if (strm == NULL) {
5109     if (local_stream) {
5110       /* Stream has been closed. */
5111       return 0;
5112     }
5113 
5114     rv = ngtcp2_idtr_open(idtr, fr->stream_id);
5115     if (rv != 0) {
5116       if (ngtcp2_err_is_fatal(rv)) {
5117         return rv;
5118       }
5119       assert(rv == NGTCP2_ERR_STREAM_IN_USE);
5120       /* Stream has been closed. */
5121       return 0;
5122     }
5123 
5124     strm = ngtcp2_mem_malloc(conn->mem, sizeof(ngtcp2_strm));
5125     if (strm == NULL) {
5126       return NGTCP2_ERR_NOMEM;
5127     }
5128     rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
5129     if (rv != 0) {
5130       ngtcp2_mem_free(conn->mem, strm);
5131       return rv;
5132     }
5133 
5134     rv = conn_call_stream_open(conn, strm);
5135     if (rv != 0) {
5136       return rv;
5137     }
5138   }
5139 
5140   if (strm->tx.max_offset < fr->max_stream_data) {
5141     strm->tx.max_offset = fr->max_stream_data;
5142 
5143     /* Don't call callback if stream is half-closed local */
5144     if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
5145       return 0;
5146     }
5147 
5148     rv = conn_call_extend_max_stream_data(conn, strm, fr->stream_id,
5149                                           fr->max_stream_data);
5150     if (rv != 0) {
5151       return rv;
5152     }
5153   }
5154 
5155   return 0;
5156 }
5157 
5158 /*
5159  * conn_recv_max_data processes received MAX_DATA frame |fr|.
5160  */
conn_recv_max_data(ngtcp2_conn * conn,const ngtcp2_max_data * fr)5161 static void conn_recv_max_data(ngtcp2_conn *conn, const ngtcp2_max_data *fr) {
5162   conn->tx.max_offset = ngtcp2_max(conn->tx.max_offset, fr->max_data);
5163 }
5164 
5165 /*
5166  * conn_buffer_pkt buffers |pkt| of length |pktlen|, chaining it from
5167  * |*ppc|.
5168  *
5169  * This function returns 0 if it succeeds, or one of the following
5170  * negative error codes:
5171  *
5172  * NGTCP2_ERR_NOMEM
5173  *     Out of memory.
5174  */
conn_buffer_pkt(ngtcp2_conn * conn,ngtcp2_pktns * pktns,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,size_t dgramlen,ngtcp2_tstamp ts)5175 static int conn_buffer_pkt(ngtcp2_conn *conn, ngtcp2_pktns *pktns,
5176                            const ngtcp2_path *path, const ngtcp2_pkt_info *pi,
5177                            const uint8_t *pkt, size_t pktlen, size_t dgramlen,
5178                            ngtcp2_tstamp ts) {
5179   int rv;
5180   ngtcp2_pkt_chain **ppc = &pktns->rx.buffed_pkts, *pc;
5181   size_t i;
5182   for (i = 0; *ppc && i < NGTCP2_MAX_NUM_BUFFED_RX_PKTS;
5183        ppc = &(*ppc)->next, ++i)
5184     ;
5185 
5186   if (i == NGTCP2_MAX_NUM_BUFFED_RX_PKTS) {
5187     return 0;
5188   }
5189 
5190   rv =
5191       ngtcp2_pkt_chain_new(&pc, path, pi, pkt, pktlen, dgramlen, ts, conn->mem);
5192   if (rv != 0) {
5193     return rv;
5194   }
5195 
5196   *ppc = pc;
5197 
5198   return 0;
5199 }
5200 
ensure_decrypt_buffer(ngtcp2_vec * vec,size_t n,size_t initial,const ngtcp2_mem * mem)5201 static int ensure_decrypt_buffer(ngtcp2_vec *vec, size_t n, size_t initial,
5202                                  const ngtcp2_mem *mem) {
5203   uint8_t *nbuf;
5204   size_t len;
5205 
5206   if (vec->len >= n) {
5207     return 0;
5208   }
5209 
5210   len = vec->len == 0 ? initial : vec->len * 2;
5211   for (; len < n; len *= 2)
5212     ;
5213   nbuf = ngtcp2_mem_realloc(mem, vec->base, len);
5214   if (nbuf == NULL) {
5215     return NGTCP2_ERR_NOMEM;
5216   }
5217   vec->base = nbuf;
5218   vec->len = len;
5219 
5220   return 0;
5221 }
5222 
5223 /*
5224  * conn_ensure_decrypt_hp_buffer ensures that
5225  * conn->crypto.decrypt_hp_buf has at least |n| bytes space.
5226  *
5227  * This function returns 0 if it succeeds, or one of the following
5228  * negative error codes:
5229  *
5230  * NGTCP2_ERR_NOMEM
5231  *     Out of memory.
5232  */
conn_ensure_decrypt_hp_buffer(ngtcp2_conn * conn,size_t n)5233 static int conn_ensure_decrypt_hp_buffer(ngtcp2_conn *conn, size_t n) {
5234   return ensure_decrypt_buffer(&conn->crypto.decrypt_hp_buf, n, 256, conn->mem);
5235 }
5236 
5237 /*
5238  * conn_ensure_decrypt_buffer ensures that conn->crypto.decrypt_buf
5239  * has at least |n| bytes space.
5240  *
5241  * This function returns 0 if it succeeds, or one of the following
5242  * negative error codes:
5243  *
5244  * NGTCP2_ERR_NOMEM
5245  *     Out of memory.
5246  */
conn_ensure_decrypt_buffer(ngtcp2_conn * conn,size_t n)5247 static int conn_ensure_decrypt_buffer(ngtcp2_conn *conn, size_t n) {
5248   return ensure_decrypt_buffer(&conn->crypto.decrypt_buf, n, 2048, conn->mem);
5249 }
5250 
5251 /*
5252  * decrypt_pkt decrypts the data pointed by |payload| whose length is
5253  * |payloadlen|, and writes plaintext data to the buffer pointed by
5254  * |dest|.  The buffer pointed by |aad| is the Additional
5255  * Authenticated Data, and its length is |aadlen|.  |pkt_num| is used
5256  * to create a nonce.  |ckm| is the cryptographic key, and iv to use.
5257  * |decrypt| is a callback function which actually decrypts a packet.
5258  *
5259  * This function returns the number of bytes written in |dest| if it
5260  * succeeds, or one of the following negative error codes:
5261  *
5262  * NGTCP2_ERR_CALLBACK_FAILURE
5263  *     User callback failed.
5264  * NGTCP2_ERR_DECRYPT
5265  *     Failed to decrypt a packet.
5266  */
decrypt_pkt(uint8_t * dest,const ngtcp2_crypto_aead * aead,const uint8_t * payload,size_t payloadlen,const uint8_t * aad,size_t aadlen,int64_t pkt_num,ngtcp2_crypto_km * ckm,ngtcp2_decrypt decrypt)5267 static ngtcp2_ssize decrypt_pkt(uint8_t *dest, const ngtcp2_crypto_aead *aead,
5268                                 const uint8_t *payload, size_t payloadlen,
5269                                 const uint8_t *aad, size_t aadlen,
5270                                 int64_t pkt_num, ngtcp2_crypto_km *ckm,
5271                                 ngtcp2_decrypt decrypt) {
5272   /* TODO nonce is limited to 64 bytes. */
5273   uint8_t nonce[64];
5274   int rv;
5275 
5276   assert(sizeof(nonce) >= ckm->iv.len);
5277 
5278   ngtcp2_crypto_create_nonce(nonce, ckm->iv.base, ckm->iv.len, pkt_num);
5279 
5280   rv = decrypt(dest, aead, &ckm->aead_ctx, payload, payloadlen, nonce,
5281                ckm->iv.len, aad, aadlen);
5282 
5283   if (rv != 0) {
5284     if (rv == NGTCP2_ERR_DECRYPT) {
5285       return rv;
5286     }
5287     return NGTCP2_ERR_CALLBACK_FAILURE;
5288   }
5289 
5290   assert(payloadlen >= aead->max_overhead);
5291 
5292   return (ngtcp2_ssize)(payloadlen - aead->max_overhead);
5293 }
5294 
5295 /*
5296  * decrypt_hp decryptes packet header.  The packet number starts at
5297  * |pkt| + |pkt_num_offset|.  The entire plaintext QUIC packet header
5298  * will be written to the buffer pointed by |dest| whose capacity is
5299  * |destlen|.
5300  *
5301  * This function returns the number of bytes written to |dest|, or one
5302  * of the following negative error codes:
5303  *
5304  * NGTCP2_ERR_PROTO
5305  *     Packet is badly formatted
5306  * NGTCP2_ERR_CALLBACK_FAILURE
5307  *     User-defined callback function failed; or it does not return
5308  *     expected result.
5309  */
decrypt_hp(ngtcp2_pkt_hd * hd,uint8_t * dest,const ngtcp2_crypto_cipher * hp,const uint8_t * pkt,size_t pktlen,size_t pkt_num_offset,ngtcp2_crypto_km * ckm,const ngtcp2_crypto_cipher_ctx * hp_ctx,ngtcp2_hp_mask hp_mask)5310 static ngtcp2_ssize decrypt_hp(ngtcp2_pkt_hd *hd, uint8_t *dest,
5311                                const ngtcp2_crypto_cipher *hp,
5312                                const uint8_t *pkt, size_t pktlen,
5313                                size_t pkt_num_offset, ngtcp2_crypto_km *ckm,
5314                                const ngtcp2_crypto_cipher_ctx *hp_ctx,
5315                                ngtcp2_hp_mask hp_mask) {
5316   size_t sample_offset;
5317   uint8_t *p = dest;
5318   uint8_t mask[NGTCP2_HP_SAMPLELEN];
5319   size_t i;
5320   int rv;
5321   (void)ckm;
5322 
5323   assert(hp_mask);
5324   assert(ckm);
5325 
5326   if (pkt_num_offset + 4 + NGTCP2_HP_SAMPLELEN > pktlen) {
5327     return NGTCP2_ERR_PROTO;
5328   }
5329 
5330   p = ngtcp2_cpymem(p, pkt, pkt_num_offset);
5331 
5332   sample_offset = pkt_num_offset + 4;
5333 
5334   rv = hp_mask(mask, hp, hp_ctx, pkt + sample_offset);
5335   if (rv != 0) {
5336     return NGTCP2_ERR_CALLBACK_FAILURE;
5337   }
5338 
5339   if (hd->flags & NGTCP2_PKT_FLAG_LONG_FORM) {
5340     dest[0] = (uint8_t)(dest[0] ^ (mask[0] & 0x0f));
5341   } else {
5342     dest[0] = (uint8_t)(dest[0] ^ (mask[0] & 0x1f));
5343     if (dest[0] & NGTCP2_SHORT_KEY_PHASE_BIT) {
5344       hd->flags |= NGTCP2_PKT_FLAG_KEY_PHASE;
5345     }
5346   }
5347 
5348   hd->pkt_numlen = (size_t)((dest[0] & NGTCP2_PKT_NUMLEN_MASK) + 1);
5349 
5350   for (i = 0; i < hd->pkt_numlen; ++i) {
5351     *p++ = *(pkt + pkt_num_offset + i) ^ mask[i + 1];
5352   }
5353 
5354   hd->pkt_num = ngtcp2_get_pkt_num(p - hd->pkt_numlen, hd->pkt_numlen);
5355 
5356   return p - dest;
5357 }
5358 
5359 /*
5360  * conn_emit_pending_crypto_data delivers pending stream data to the
5361  * application due to packet reordering.
5362  *
5363  * This function returns 0 if it succeeds, or one of the following
5364  * negative error codes:
5365  *
5366  * NGTCP2_ERR_CALLBACK_FAILURE
5367  *     User callback failed
5368  * NGTCP2_ERR_CRYPTO
5369  *     TLS backend reported error
5370  */
conn_emit_pending_crypto_data(ngtcp2_conn * conn,ngtcp2_crypto_level crypto_level,ngtcp2_strm * strm,uint64_t rx_offset)5371 static int conn_emit_pending_crypto_data(ngtcp2_conn *conn,
5372                                          ngtcp2_crypto_level crypto_level,
5373                                          ngtcp2_strm *strm,
5374                                          uint64_t rx_offset) {
5375   size_t datalen;
5376   const uint8_t *data;
5377   int rv;
5378   uint64_t offset;
5379 
5380   if (!strm->rx.rob) {
5381     return 0;
5382   }
5383 
5384   for (;;) {
5385     datalen = ngtcp2_rob_data_at(strm->rx.rob, &data, rx_offset);
5386     if (datalen == 0) {
5387       assert(rx_offset == ngtcp2_strm_rx_offset(strm));
5388       return 0;
5389     }
5390 
5391     offset = rx_offset;
5392     rx_offset += datalen;
5393 
5394     rv = conn_call_recv_crypto_data(conn, crypto_level, offset, data, datalen);
5395     if (rv != 0) {
5396       return rv;
5397     }
5398 
5399     ngtcp2_rob_pop(strm->rx.rob, rx_offset - datalen, datalen);
5400   }
5401 }
5402 
5403 /*
5404  * conn_recv_connection_close is called when CONNECTION_CLOSE or
5405  * APPLICATION_CLOSE frame is received.
5406  */
conn_recv_connection_close(ngtcp2_conn * conn,ngtcp2_connection_close * fr)5407 static void conn_recv_connection_close(ngtcp2_conn *conn,
5408                                        ngtcp2_connection_close *fr) {
5409   conn->state = NGTCP2_CS_DRAINING;
5410   if (fr->type == NGTCP2_FRAME_CONNECTION_CLOSE) {
5411     conn->rx.ccec.type = NGTCP2_CONNECTION_CLOSE_ERROR_CODE_TYPE_TRANSPORT;
5412   } else {
5413     conn->rx.ccec.type = NGTCP2_CONNECTION_CLOSE_ERROR_CODE_TYPE_APPLICATION;
5414   }
5415   conn->rx.ccec.error_code = fr->error_code;
5416 }
5417 
conn_recv_path_challenge(ngtcp2_conn * conn,const ngtcp2_path * path,ngtcp2_path_challenge * fr)5418 static void conn_recv_path_challenge(ngtcp2_conn *conn, const ngtcp2_path *path,
5419                                      ngtcp2_path_challenge *fr) {
5420   ngtcp2_path_challenge_entry *ent;
5421 
5422   /* client only responds to PATH_CHALLENGE from the current path or
5423      path which client is migrating to. */
5424   if (!conn->server && !ngtcp2_path_eq(&conn->dcid.current.ps.path, path) &&
5425       (!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path))) {
5426     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
5427                     "discard PATH_CHALLENGE from the path which is not current "
5428                     "or endpoint is migrating to");
5429     return;
5430   }
5431 
5432   ent = ngtcp2_ringbuf_push_front(&conn->rx.path_challenge);
5433   ngtcp2_path_challenge_entry_init(ent, path, fr->data);
5434 }
5435 
5436 /*
5437  * conn_reset_congestion_state resets congestion state.
5438  */
conn_reset_congestion_state(ngtcp2_conn * conn,ngtcp2_tstamp ts)5439 static void conn_reset_congestion_state(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
5440   conn_reset_conn_stat_cc(conn, &conn->cstat);
5441 
5442   conn->cc.reset(&conn->cc, &conn->cstat, ts);
5443 
5444   if (conn->hs_pktns) {
5445     ngtcp2_rtb_reset_cc_state(&conn->hs_pktns->rtb,
5446                               conn->hs_pktns->tx.last_pkt_num + 1);
5447   }
5448   ngtcp2_rtb_reset_cc_state(&conn->pktns.rtb, conn->pktns.tx.last_pkt_num + 1);
5449   ngtcp2_rst_init(&conn->rst);
5450 
5451   conn->tx.pacing.next_ts = UINT64_MAX;
5452 }
5453 
conn_recv_path_response(ngtcp2_conn * conn,ngtcp2_path_response * fr,ngtcp2_tstamp ts)5454 static int conn_recv_path_response(ngtcp2_conn *conn, ngtcp2_path_response *fr,
5455                                    ngtcp2_tstamp ts) {
5456   int rv;
5457   ngtcp2_duration pto, timeout;
5458   ngtcp2_pv *pv = conn->pv, *npv;
5459   uint8_t ent_flags;
5460 
5461   if (!pv) {
5462     return 0;
5463   }
5464 
5465   rv = ngtcp2_pv_validate(pv, &ent_flags, fr->data);
5466   if (rv != 0) {
5467     assert(!ngtcp2_err_is_fatal(rv));
5468 
5469     return 0;
5470   }
5471 
5472   if (!(pv->flags & NGTCP2_PV_FLAG_DONT_CARE)) {
5473     if (!(pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE)) {
5474       if (pv->dcid.seq != conn->dcid.current.seq) {
5475         assert(conn->dcid.current.cid.datalen);
5476 
5477         rv = conn_retire_dcid(conn, &conn->dcid.current, ts);
5478         if (rv != 0) {
5479           return rv;
5480         }
5481         ngtcp2_dcid_copy(&conn->dcid.current, &pv->dcid);
5482       }
5483       conn_reset_congestion_state(conn, ts);
5484       conn_reset_ecn_validation_state(conn);
5485     }
5486 
5487     if (ngtcp2_path_eq(&pv->dcid.ps.path, &conn->dcid.current.ps.path)) {
5488       conn->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
5489     }
5490 
5491     rv = conn_call_path_validation(conn, pv,
5492                                    NGTCP2_PATH_VALIDATION_RESULT_SUCCESS);
5493     if (rv != 0) {
5494       return rv;
5495     }
5496   }
5497 
5498   if (pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) {
5499     pto = conn_compute_pto(conn, &conn->pktns);
5500     timeout = 3 * ngtcp2_max(pto, pv->fallback_pto);
5501 
5502     if (ent_flags & NGTCP2_PV_ENTRY_FLAG_UNDERSIZED) {
5503       assert(conn->server);
5504 
5505       /* Validate path again */
5506       rv = ngtcp2_pv_new(&npv, &pv->dcid, timeout,
5507                          NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE |
5508                              NGTCP2_PV_FLAG_MTU_PROBE,
5509                          &conn->log, conn->mem);
5510       if (rv != 0) {
5511         return rv;
5512       }
5513 
5514       npv->dcid.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
5515       ngtcp2_dcid_copy(&npv->fallback_dcid, &pv->fallback_dcid);
5516       npv->fallback_pto = pv->fallback_pto;
5517     } else {
5518       rv = ngtcp2_pv_new(&npv, &pv->fallback_dcid, timeout,
5519                          NGTCP2_PV_FLAG_DONT_CARE, &conn->log, conn->mem);
5520       if (rv != 0) {
5521         return rv;
5522       }
5523     }
5524 
5525     /* Unset the flag bit so that conn_stop_pv does not retire
5526        DCID. */
5527     pv->flags &= (uint8_t)~NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE;
5528 
5529     rv = conn_stop_pv(conn, ts);
5530     if (rv != 0) {
5531       ngtcp2_pv_del(npv);
5532       return rv;
5533     }
5534 
5535     conn->pv = npv;
5536 
5537     return 0;
5538   }
5539 
5540   return conn_stop_pv(conn, ts);
5541 }
5542 
5543 /*
5544  * pkt_num_bits returns the number of bits available when packet
5545  * number is encoded in |pkt_numlen| bytes.
5546  */
pkt_num_bits(size_t pkt_numlen)5547 static size_t pkt_num_bits(size_t pkt_numlen) {
5548   switch (pkt_numlen) {
5549   case 1:
5550     return 8;
5551   case 2:
5552     return 16;
5553   case 3:
5554     return 24;
5555   case 4:
5556     return 32;
5557   default:
5558     assert(0);
5559     abort();
5560   }
5561 }
5562 
5563 /*
5564  * pktns_pkt_num_is_duplicate returns nonzero if |pkt_num| is
5565  * duplicated packet number.
5566  */
pktns_pkt_num_is_duplicate(ngtcp2_pktns * pktns,int64_t pkt_num)5567 static int pktns_pkt_num_is_duplicate(ngtcp2_pktns *pktns, int64_t pkt_num) {
5568   return ngtcp2_gaptr_is_pushed(&pktns->rx.pngap, (uint64_t)pkt_num, 1);
5569 }
5570 
5571 /*
5572  * pktns_commit_recv_pkt_num marks packet number |pkt_num| as
5573  * received.
5574  */
pktns_commit_recv_pkt_num(ngtcp2_pktns * pktns,int64_t pkt_num,int ack_eliciting,ngtcp2_tstamp ts)5575 static int pktns_commit_recv_pkt_num(ngtcp2_pktns *pktns, int64_t pkt_num,
5576                                      int ack_eliciting, ngtcp2_tstamp ts) {
5577   int rv;
5578 
5579   if (ack_eliciting && pktns->rx.max_ack_eliciting_pkt_num + 1 != pkt_num) {
5580     ngtcp2_acktr_immediate_ack(&pktns->acktr);
5581   }
5582   if (pktns->rx.max_pkt_num < pkt_num) {
5583     pktns->rx.max_pkt_num = pkt_num;
5584     pktns->rx.max_pkt_ts = ts;
5585   }
5586   if (ack_eliciting && pktns->rx.max_ack_eliciting_pkt_num < pkt_num) {
5587     pktns->rx.max_ack_eliciting_pkt_num = pkt_num;
5588   }
5589 
5590   rv = ngtcp2_gaptr_push(&pktns->rx.pngap, (uint64_t)pkt_num, 1);
5591   if (rv != 0) {
5592     return rv;
5593   }
5594 
5595   if (ngtcp2_ksl_len(&pktns->rx.pngap.gap) > 256) {
5596     ngtcp2_gaptr_drop_first_gap(&pktns->rx.pngap);
5597   }
5598 
5599   return 0;
5600 }
5601 
5602 /*
5603  * verify_token verifies |hd| contains |token| in its token field.  It
5604  * returns 0 if it succeeds, or NGTCP2_ERR_PROTO.
5605  */
verify_token(const ngtcp2_vec * token,const ngtcp2_pkt_hd * hd)5606 static int verify_token(const ngtcp2_vec *token, const ngtcp2_pkt_hd *hd) {
5607   if (token->len == hd->token.len &&
5608       ngtcp2_cmemeq(token->base, hd->token.base, token->len)) {
5609     return 0;
5610   }
5611   return NGTCP2_ERR_PROTO;
5612 }
5613 
pktns_increase_ecn_counts(ngtcp2_pktns * pktns,const ngtcp2_pkt_info * pi)5614 static void pktns_increase_ecn_counts(ngtcp2_pktns *pktns,
5615                                       const ngtcp2_pkt_info *pi) {
5616   switch (pi->ecn & NGTCP2_ECN_MASK) {
5617   case NGTCP2_ECN_ECT_0:
5618     ++pktns->rx.ecn.ect0;
5619     break;
5620   case NGTCP2_ECN_ECT_1:
5621     ++pktns->rx.ecn.ect1;
5622     break;
5623   case NGTCP2_ECN_CE:
5624     ++pktns->rx.ecn.ce;
5625     break;
5626   }
5627 }
5628 
5629 static int conn_recv_crypto(ngtcp2_conn *conn, ngtcp2_crypto_level crypto_level,
5630                             ngtcp2_strm *strm, const ngtcp2_crypto *fr);
5631 
5632 static ngtcp2_ssize conn_recv_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
5633                                   const ngtcp2_pkt_info *pi, const uint8_t *pkt,
5634                                   size_t pktlen, size_t dgramlen,
5635                                   ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts);
5636 
5637 static int conn_process_buffered_protected_pkt(ngtcp2_conn *conn,
5638                                                ngtcp2_pktns *pktns,
5639                                                ngtcp2_tstamp ts);
5640 
5641 /*
5642  * conn_recv_handshake_pkt processes received packet |pkt| whose
5643  * length is |pktlen| during handshake period.  The buffer pointed by
5644  * |pkt| might contain multiple packets.  This function only processes
5645  * one packet.  |pkt_ts| is the timestamp when packet is received.
5646  * |ts| should be the current time.  Usually they are the same, but
5647  * for buffered packets, |pkt_ts| would be earlier than |ts|.
5648  *
5649  * This function returns the number of bytes it reads if it succeeds,
5650  * or one of the following negative error codes:
5651  *
5652  * NGTCP2_ERR_RECV_VERSION_NEGOTIATION
5653  *     Version Negotiation packet is received.
5654  * NGTCP2_ERR_NOMEM
5655  *     Out of memory.
5656  * NGTCP2_ERR_CALLBACK_FAILURE
5657  *     User-defined callback function failed.
5658  * NGTCP2_ERR_DISCARD_PKT
5659  *     Packet was discarded because plain text header was malformed;
5660  *     or its payload could not be decrypted.
5661  * NGTCP2_ERR_FRAME_FORMAT
5662  *     Frame is badly formatted
5663  * NGTCP2_ERR_ACK_FRAME
5664  *     ACK frame is malformed.
5665  * NGTCP2_ERR_CRYPTO
5666  *     TLS stack reported error.
5667  * NGTCP2_ERR_PROTO
5668  *     Generic QUIC protocol error.
5669  *
5670  * In addition to the above error codes, error codes returned from
5671  * conn_recv_pkt are also returned.
5672  */
5673 static ngtcp2_ssize
conn_recv_handshake_pkt(ngtcp2_conn * conn,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,size_t dgramlen,ngtcp2_tstamp pkt_ts,ngtcp2_tstamp ts)5674 conn_recv_handshake_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
5675                         const ngtcp2_pkt_info *pi, const uint8_t *pkt,
5676                         size_t pktlen, size_t dgramlen, ngtcp2_tstamp pkt_ts,
5677                         ngtcp2_tstamp ts) {
5678   ngtcp2_ssize nread;
5679   ngtcp2_pkt_hd hd;
5680   ngtcp2_max_frame mfr;
5681   ngtcp2_frame *fr = &mfr.fr;
5682   int rv;
5683   int require_ack = 0;
5684   size_t hdpktlen;
5685   const uint8_t *payload;
5686   size_t payloadlen;
5687   ngtcp2_ssize nwrite;
5688   ngtcp2_crypto_aead *aead;
5689   ngtcp2_crypto_cipher *hp;
5690   ngtcp2_crypto_km *ckm;
5691   ngtcp2_crypto_cipher_ctx *hp_ctx;
5692   ngtcp2_hp_mask hp_mask;
5693   ngtcp2_decrypt decrypt;
5694   ngtcp2_pktns *pktns;
5695   ngtcp2_strm *crypto;
5696   ngtcp2_crypto_level crypto_level;
5697   int invalid_reserved_bits = 0;
5698 
5699   if (pktlen == 0) {
5700     return 0;
5701   }
5702 
5703   if (!(pkt[0] & NGTCP2_HEADER_FORM_BIT)) {
5704     if (conn->state == NGTCP2_CS_SERVER_INITIAL) {
5705       /* Ignore Short packet unless server's first Handshake packet
5706          has been transmitted. */
5707       return (ngtcp2_ssize)pktlen;
5708     }
5709 
5710     if (conn->pktns.crypto.rx.ckm) {
5711       return 0;
5712     }
5713 
5714     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
5715                     "buffering Short packet len=%zu", pktlen);
5716 
5717     rv = conn_buffer_pkt(conn, &conn->pktns, path, pi, pkt, pktlen, dgramlen,
5718                          ts);
5719     if (rv != 0) {
5720       assert(ngtcp2_err_is_fatal(rv));
5721       return rv;
5722     }
5723     return (ngtcp2_ssize)pktlen;
5724   }
5725 
5726   nread = ngtcp2_pkt_decode_hd_long(&hd, pkt, pktlen);
5727   if (nread < 0) {
5728     return NGTCP2_ERR_DISCARD_PKT;
5729   }
5730 
5731   switch (hd.type) {
5732   case NGTCP2_PKT_VERSION_NEGOTIATION:
5733     hdpktlen = (size_t)nread;
5734 
5735     ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
5736 
5737     if (conn->server) {
5738       return NGTCP2_ERR_DISCARD_PKT;
5739     }
5740 
5741     /* Receiving Version Negotiation packet after getting Handshake
5742        packet from server is invalid. */
5743     if (conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) {
5744       return NGTCP2_ERR_DISCARD_PKT;
5745     }
5746 
5747     if (!ngtcp2_cid_eq(&conn->oscid, &hd.dcid)) {
5748       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5749                       "packet was ignored because of mismatched DCID");
5750       return NGTCP2_ERR_DISCARD_PKT;
5751     }
5752 
5753     if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
5754       /* Just discard invalid Version Negotiation packet */
5755       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5756                       "packet was ignored because of mismatched SCID");
5757       return NGTCP2_ERR_DISCARD_PKT;
5758     }
5759     rv = conn_on_version_negotiation(conn, &hd, pkt + hdpktlen,
5760                                      pktlen - hdpktlen);
5761     if (rv != 0) {
5762       if (ngtcp2_err_is_fatal(rv)) {
5763         return rv;
5764       }
5765       return NGTCP2_ERR_DISCARD_PKT;
5766     }
5767     return NGTCP2_ERR_RECV_VERSION_NEGOTIATION;
5768   case NGTCP2_PKT_RETRY:
5769     hdpktlen = (size_t)nread;
5770 
5771     ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
5772 
5773     if (conn->server) {
5774       return NGTCP2_ERR_DISCARD_PKT;
5775     }
5776 
5777     /* Receiving Retry packet after getting Initial packet from server
5778        is invalid. */
5779     if (conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) {
5780       return NGTCP2_ERR_DISCARD_PKT;
5781     }
5782 
5783     rv = conn_on_retry(conn, &hd, hdpktlen, pkt, pktlen, ts);
5784     if (rv != 0) {
5785       if (ngtcp2_err_is_fatal(rv)) {
5786         return rv;
5787       }
5788       return NGTCP2_ERR_DISCARD_PKT;
5789     }
5790     return (ngtcp2_ssize)pktlen;
5791   }
5792 
5793   if (pktlen < (size_t)nread + hd.len) {
5794     return NGTCP2_ERR_DISCARD_PKT;
5795   }
5796 
5797   pktlen = (size_t)nread + hd.len;
5798 
5799   if (conn->version != hd.version) {
5800     return NGTCP2_ERR_DISCARD_PKT;
5801   }
5802 
5803   /* Quoted from spec: if subsequent packets of those types include a
5804      different Source Connection ID, they MUST be discarded. */
5805   if ((conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) &&
5806       !ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
5807     ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
5808     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5809                     "packet was ignored because of mismatched SCID");
5810     return NGTCP2_ERR_DISCARD_PKT;
5811   }
5812 
5813   switch (hd.type) {
5814   case NGTCP2_PKT_0RTT:
5815     if (!conn->server) {
5816       return NGTCP2_ERR_DISCARD_PKT;
5817     }
5818     if (conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) {
5819       if (conn->early.ckm) {
5820         ngtcp2_ssize nread2;
5821         /* TODO Avoid to parse header twice. */
5822         nread2 =
5823             conn_recv_pkt(conn, path, pi, pkt, pktlen, dgramlen, pkt_ts, ts);
5824         if (nread2 < 0) {
5825           return nread2;
5826         }
5827       }
5828 
5829       /* Discard 0-RTT packet if we don't have a key to decrypt it. */
5830       return (ngtcp2_ssize)pktlen;
5831     }
5832 
5833     /* Buffer re-ordered 0-RTT packet. */
5834     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
5835                     "buffering 0-RTT packet len=%zu", pktlen);
5836 
5837     rv = conn_buffer_pkt(conn, conn->in_pktns, path, pi, pkt, pktlen, dgramlen,
5838                          ts);
5839     if (rv != 0) {
5840       assert(ngtcp2_err_is_fatal(rv));
5841       return rv;
5842     }
5843 
5844     return (ngtcp2_ssize)pktlen;
5845   case NGTCP2_PKT_INITIAL:
5846     if (!conn->in_pktns) {
5847       ngtcp2_log_info(
5848           &conn->log, NGTCP2_LOG_EVENT_PKT,
5849           "Initial packet is discarded because keys have been discarded");
5850       return (ngtcp2_ssize)pktlen;
5851     }
5852 
5853     assert(conn->in_pktns);
5854 
5855     if (conn->server) {
5856       if (conn->local.settings.token.len) {
5857         rv = verify_token(&conn->local.settings.token, &hd);
5858         if (rv != 0) {
5859           ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5860                           "packet was ignored because token is invalid");
5861           return NGTCP2_ERR_DISCARD_PKT;
5862         }
5863       }
5864       if ((conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) == 0) {
5865         /* Set rcid here so that it is available to callback.  If this
5866            packet is discarded later in this function and no packet is
5867            processed in this connection attempt so far, connection
5868            will be dropped. */
5869         conn->rcid = hd.dcid;
5870 
5871         rv = conn_call_recv_client_initial(conn, &hd.dcid);
5872         if (rv != 0) {
5873           return rv;
5874         }
5875       }
5876     } else if (hd.token.len != 0) {
5877       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5878                       "packet was ignored because token is not empty");
5879       return NGTCP2_ERR_DISCARD_PKT;
5880     }
5881 
5882     pktns = conn->in_pktns;
5883     crypto = &pktns->crypto.strm;
5884     crypto_level = NGTCP2_CRYPTO_LEVEL_INITIAL;
5885 
5886     break;
5887   case NGTCP2_PKT_HANDSHAKE:
5888     if (!conn->hs_pktns->crypto.rx.ckm) {
5889       if (conn->server) {
5890         ngtcp2_log_info(
5891             &conn->log, NGTCP2_LOG_EVENT_PKT,
5892             "Handshake packet at this point is unexpected and discarded");
5893         return (ngtcp2_ssize)pktlen;
5894       }
5895       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
5896                       "buffering Handshake packet len=%zu", pktlen);
5897 
5898       rv = conn_buffer_pkt(conn, conn->hs_pktns, path, pi, pkt, pktlen,
5899                            dgramlen, ts);
5900       if (rv != 0) {
5901         assert(ngtcp2_err_is_fatal(rv));
5902         return rv;
5903       }
5904       return (ngtcp2_ssize)pktlen;
5905     }
5906 
5907     pktns = conn->hs_pktns;
5908     crypto = &pktns->crypto.strm;
5909     crypto_level = NGTCP2_CRYPTO_LEVEL_HANDSHAKE;
5910 
5911     break;
5912   default:
5913     /* unknown packet type */
5914     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5915                     "packet was ignored because of unknown packet type");
5916     return (ngtcp2_ssize)pktlen;
5917   }
5918 
5919   hp_mask = conn->callbacks.hp_mask;
5920   decrypt = conn->callbacks.decrypt;
5921   aead = &pktns->crypto.ctx.aead;
5922   hp = &pktns->crypto.ctx.hp;
5923   ckm = pktns->crypto.rx.ckm;
5924   hp_ctx = &pktns->crypto.rx.hp_ctx;
5925 
5926   assert(ckm);
5927   assert(hp_mask);
5928   assert(decrypt);
5929 
5930   rv = conn_ensure_decrypt_hp_buffer(conn, (size_t)nread + 4);
5931   if (rv != 0) {
5932     return rv;
5933   }
5934 
5935   nwrite = decrypt_hp(&hd, conn->crypto.decrypt_hp_buf.base, hp, pkt, pktlen,
5936                       (size_t)nread, ckm, hp_ctx, hp_mask);
5937   if (nwrite < 0) {
5938     if (ngtcp2_err_is_fatal((int)nwrite)) {
5939       return nwrite;
5940     }
5941     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5942                     "could not decrypt packet number");
5943     return NGTCP2_ERR_DISCARD_PKT;
5944   }
5945 
5946   hdpktlen = (size_t)nwrite;
5947   payload = pkt + hdpktlen;
5948   payloadlen = hd.len - hd.pkt_numlen;
5949 
5950   hd.pkt_num = ngtcp2_pkt_adjust_pkt_num(pktns->rx.max_pkt_num, hd.pkt_num,
5951                                          pkt_num_bits(hd.pkt_numlen));
5952   if (hd.pkt_num > NGTCP2_MAX_PKT_NUM) {
5953     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5954                     "pkn=%" PRId64 " is greater than maximum pkn", hd.pkt_num);
5955     return NGTCP2_ERR_DISCARD_PKT;
5956   }
5957 
5958   ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
5959 
5960   rv = ngtcp2_pkt_verify_reserved_bits(conn->crypto.decrypt_hp_buf.base[0]);
5961   if (rv != 0) {
5962     invalid_reserved_bits = 1;
5963 
5964     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5965                     "packet has incorrect reserved bits");
5966 
5967     /* Will return error after decrypting payload */
5968   }
5969 
5970   if (pktns_pkt_num_is_duplicate(pktns, hd.pkt_num)) {
5971     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5972                     "packet was discarded because of duplicated packet number");
5973     return NGTCP2_ERR_DISCARD_PKT;
5974   }
5975 
5976   rv = conn_ensure_decrypt_buffer(conn, payloadlen);
5977   if (rv != 0) {
5978     return rv;
5979   }
5980 
5981   nwrite = decrypt_pkt(conn->crypto.decrypt_buf.base, aead, payload, payloadlen,
5982                        conn->crypto.decrypt_hp_buf.base, hdpktlen, hd.pkt_num,
5983                        ckm, decrypt);
5984   if (nwrite < 0) {
5985     if (ngtcp2_err_is_fatal((int)nwrite)) {
5986       return nwrite;
5987     }
5988     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
5989                     "could not decrypt packet payload");
5990     return NGTCP2_ERR_DISCARD_PKT;
5991   }
5992 
5993   if (invalid_reserved_bits) {
5994     return NGTCP2_ERR_PROTO;
5995   }
5996 
5997   payload = conn->crypto.decrypt_buf.base;
5998   payloadlen = (size_t)nwrite;
5999 
6000   switch (hd.type) {
6001   case NGTCP2_PKT_INITIAL:
6002     if (!conn->server || ((conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED) &&
6003                           !ngtcp2_cid_eq(&conn->rcid, &hd.dcid))) {
6004       rv = conn_verify_dcid(conn, NULL, &hd);
6005       if (rv != 0) {
6006         if (ngtcp2_err_is_fatal(rv)) {
6007           return rv;
6008         }
6009         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6010                         "packet was ignored because of mismatched DCID");
6011         return NGTCP2_ERR_DISCARD_PKT;
6012       }
6013     }
6014     break;
6015   case NGTCP2_PKT_HANDSHAKE:
6016     rv = conn_verify_dcid(conn, NULL, &hd);
6017     if (rv != 0) {
6018       if (ngtcp2_err_is_fatal(rv)) {
6019         return rv;
6020       }
6021       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6022                       "packet was ignored because of mismatched DCID");
6023       return NGTCP2_ERR_DISCARD_PKT;
6024     }
6025     break;
6026   default:
6027     assert(0);
6028   }
6029 
6030   if (payloadlen == 0) {
6031     /* QUIC packet must contain at least one frame */
6032     if (hd.type == NGTCP2_PKT_INITIAL) {
6033       return NGTCP2_ERR_DISCARD_PKT;
6034     }
6035     return NGTCP2_ERR_PROTO;
6036   }
6037 
6038   if (hd.type == NGTCP2_PKT_INITIAL &&
6039       !(conn->flags & NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED)) {
6040     conn->flags |= NGTCP2_CONN_FLAG_CONN_ID_NEGOTIATED;
6041     if (!conn->server) {
6042       conn->dcid.current.cid = hd.scid;
6043     }
6044   }
6045 
6046   ngtcp2_qlog_pkt_received_start(&conn->qlog);
6047 
6048   for (; payloadlen;) {
6049     nread = ngtcp2_pkt_decode_frame(fr, payload, payloadlen);
6050     if (nread < 0) {
6051       return nread;
6052     }
6053 
6054     payload += nread;
6055     payloadlen -= (size_t)nread;
6056 
6057     switch (fr->type) {
6058     case NGTCP2_FRAME_ACK:
6059     case NGTCP2_FRAME_ACK_ECN:
6060       fr->ack.ack_delay = 0;
6061       fr->ack.ack_delay_unscaled = 0;
6062       break;
6063     }
6064 
6065     ngtcp2_log_rx_fr(&conn->log, &hd, fr);
6066 
6067     switch (fr->type) {
6068     case NGTCP2_FRAME_ACK:
6069     case NGTCP2_FRAME_ACK_ECN:
6070       if (!conn->server && hd.type == NGTCP2_PKT_HANDSHAKE) {
6071         conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
6072       }
6073       rv = conn_recv_ack(conn, pktns, &fr->ack, pkt_ts, ts);
6074       if (rv != 0) {
6075         return rv;
6076       }
6077       break;
6078     case NGTCP2_FRAME_PADDING:
6079       break;
6080     case NGTCP2_FRAME_CRYPTO:
6081       rv = conn_recv_crypto(conn, crypto_level, crypto, &fr->crypto);
6082       if (rv != 0) {
6083         return rv;
6084       }
6085       require_ack = 1;
6086       break;
6087     case NGTCP2_FRAME_CONNECTION_CLOSE:
6088       conn_recv_connection_close(conn, &fr->connection_close);
6089       break;
6090     case NGTCP2_FRAME_PING:
6091       require_ack = 1;
6092       break;
6093     default:
6094       return NGTCP2_ERR_PROTO;
6095     }
6096 
6097     ngtcp2_qlog_write_frame(&conn->qlog, fr);
6098   }
6099 
6100   if (conn->server && hd.type == NGTCP2_PKT_HANDSHAKE) {
6101     /* Successful processing of Handshake packet from client verifies
6102        source address. */
6103     conn->dcid.current.flags |= NGTCP2_DCID_FLAG_PATH_VALIDATED;
6104   }
6105 
6106   ngtcp2_qlog_pkt_received_end(&conn->qlog, &hd, pktlen);
6107 
6108   rv = pktns_commit_recv_pkt_num(pktns, hd.pkt_num, require_ack, pkt_ts);
6109   if (rv != 0) {
6110     return rv;
6111   }
6112 
6113   pktns_increase_ecn_counts(pktns, pi);
6114 
6115   /* TODO Initial and Handshake are always acknowledged without
6116      delay. */
6117   if (require_ack &&
6118       (++pktns->acktr.rx_npkt >= conn->local.settings.ack_thresh ||
6119        (pi->ecn & NGTCP2_ECN_MASK) == NGTCP2_ECN_CE)) {
6120     ngtcp2_acktr_immediate_ack(&pktns->acktr);
6121   }
6122 
6123   rv = ngtcp2_conn_sched_ack(conn, &pktns->acktr, hd.pkt_num, require_ack,
6124                              pkt_ts);
6125   if (rv != 0) {
6126     return rv;
6127   }
6128 
6129   conn_restart_timer_on_read(conn, ts);
6130 
6131   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
6132 
6133   conn_update_dcid_max_udp_payload_size(conn, &conn->dcid.current, dgramlen);
6134 
6135   return conn->state == NGTCP2_CS_DRAINING ? NGTCP2_ERR_DRAINING
6136                                            : (ngtcp2_ssize)pktlen;
6137 }
6138 
is_crypto_error(int liberr)6139 static int is_crypto_error(int liberr) {
6140   switch (liberr) {
6141   case NGTCP2_ERR_CRYPTO:
6142   case NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM:
6143   case NGTCP2_ERR_MALFORMED_TRANSPORT_PARAM:
6144   case NGTCP2_ERR_TRANSPORT_PARAM:
6145     return 1;
6146   }
6147 
6148   return 0;
6149 }
6150 
6151 /*
6152  * conn_recv_handshake_cpkt processes compound packet during
6153  * handshake.  The buffer pointed by |pkt| might contain multiple
6154  * packets.  The Short packet must be the last one because it does not
6155  * have payload length field.
6156  *
6157  * This function returns the same error code returned by
6158  * conn_recv_handshake_pkt.
6159  */
conn_recv_handshake_cpkt(ngtcp2_conn * conn,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,ngtcp2_tstamp ts)6160 static ngtcp2_ssize conn_recv_handshake_cpkt(ngtcp2_conn *conn,
6161                                              const ngtcp2_path *path,
6162                                              const ngtcp2_pkt_info *pi,
6163                                              const uint8_t *pkt, size_t pktlen,
6164                                              ngtcp2_tstamp ts) {
6165   ngtcp2_ssize nread;
6166   size_t dgramlen = pktlen;
6167   const uint8_t *origpkt = pkt;
6168 
6169   if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
6170     conn->dcid.current.bytes_recv += dgramlen;
6171   }
6172 
6173   while (pktlen) {
6174     nread =
6175         conn_recv_handshake_pkt(conn, path, pi, pkt, pktlen, dgramlen, ts, ts);
6176     if (nread < 0) {
6177       if (ngtcp2_err_is_fatal((int)nread)) {
6178         return nread;
6179       }
6180 
6181       if (nread == NGTCP2_ERR_DRAINING) {
6182         return NGTCP2_ERR_DRAINING;
6183       }
6184 
6185       if ((pkt[0] & NGTCP2_HEADER_FORM_BIT) &&
6186           /* Not a Version Negotiation packet */
6187           pktlen > 4 && ngtcp2_get_uint32(&pkt[1]) > 0 &&
6188           ngtcp2_pkt_get_type_long(pkt[0]) == NGTCP2_PKT_INITIAL) {
6189         if (conn->server) {
6190           if (is_crypto_error((int)nread)) {
6191             /* If server gets crypto error from TLS stack, it is
6192                unrecoverable, therefore drop connection. */
6193             return nread;
6194           }
6195 
6196           /* If server discards first Initial, then drop connection
6197              state.  This is because SCID in packet might be corrupted
6198              and the current connection state might wrongly discard
6199              valid packet and prevent the handshake from
6200              completing. */
6201           if (conn->in_pktns && conn->in_pktns->rx.max_pkt_num == -1) {
6202             return NGTCP2_ERR_DROP_CONN;
6203           }
6204 
6205           return (ngtcp2_ssize)dgramlen;
6206         }
6207         /* client */
6208         if (is_crypto_error((int)nread)) {
6209           /* If client gets crypto error from TLS stack, it is
6210              unrecoverable, therefore drop connection. */
6211           return nread;
6212         }
6213         return (ngtcp2_ssize)dgramlen;
6214       }
6215 
6216       if (nread == NGTCP2_ERR_DISCARD_PKT) {
6217         return (ngtcp2_ssize)dgramlen;
6218       }
6219 
6220       return nread;
6221     }
6222 
6223     if (nread == 0) {
6224       assert(!(pkt[0] & NGTCP2_HEADER_FORM_BIT));
6225       return pkt - origpkt;
6226     }
6227 
6228     assert(pktlen >= (size_t)nread);
6229     pkt += nread;
6230     pktlen -= (size_t)nread;
6231 
6232     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
6233                     "read packet %td left %zu", nread, pktlen);
6234   }
6235 
6236   return (ngtcp2_ssize)dgramlen;
6237 }
6238 
ngtcp2_conn_init_stream(ngtcp2_conn * conn,ngtcp2_strm * strm,int64_t stream_id,void * stream_user_data)6239 int ngtcp2_conn_init_stream(ngtcp2_conn *conn, ngtcp2_strm *strm,
6240                             int64_t stream_id, void *stream_user_data) {
6241   int rv;
6242   uint64_t max_rx_offset;
6243   uint64_t max_tx_offset;
6244   int local_stream = conn_local_stream(conn, stream_id);
6245 
6246   if (bidi_stream(stream_id)) {
6247     if (local_stream) {
6248       max_rx_offset =
6249           conn->local.transport_params.initial_max_stream_data_bidi_local;
6250       max_tx_offset =
6251           conn->remote.transport_params.initial_max_stream_data_bidi_remote;
6252     } else {
6253       max_rx_offset =
6254           conn->local.transport_params.initial_max_stream_data_bidi_remote;
6255       max_tx_offset =
6256           conn->remote.transport_params.initial_max_stream_data_bidi_local;
6257     }
6258   } else if (local_stream) {
6259     max_rx_offset = 0;
6260     max_tx_offset = conn->remote.transport_params.initial_max_stream_data_uni;
6261   } else {
6262     max_rx_offset = conn->local.transport_params.initial_max_stream_data_uni;
6263     max_tx_offset = 0;
6264   }
6265 
6266   rv = ngtcp2_strm_init(strm, stream_id, NGTCP2_STRM_FLAG_NONE, max_rx_offset,
6267                         max_tx_offset, stream_user_data, conn->mem);
6268   if (rv != 0) {
6269     return rv;
6270   }
6271 
6272   rv = ngtcp2_map_insert(&conn->strms, (ngtcp2_map_key_type)strm->stream_id,
6273                          strm);
6274   if (rv != 0) {
6275     assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
6276     goto fail;
6277   }
6278 
6279   return 0;
6280 
6281 fail:
6282   ngtcp2_strm_free(strm);
6283   return rv;
6284 }
6285 
6286 /*
6287  * conn_emit_pending_stream_data passes buffered ordered stream data
6288  * to the application.  |rx_offset| is the first offset to deliver to
6289  * the application.  This function assumes that the data up to
6290  * |rx_offset| has been delivered already.  This function only passes
6291  * the ordered data without any gap.  If there is a gap, it stops
6292  * providing the data to the application, and returns.
6293  *
6294  * This function returns 0 if it succeeds, or one of the following
6295  * negative error codes:
6296  *
6297  * NGTCP2_ERR_CALLBACK_FAILURE
6298  *     User callback failed.
6299  * NGTCP2_ERR_NOMEM
6300  *     Out of memory.
6301  */
conn_emit_pending_stream_data(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t rx_offset)6302 static int conn_emit_pending_stream_data(ngtcp2_conn *conn, ngtcp2_strm *strm,
6303                                          uint64_t rx_offset) {
6304   size_t datalen;
6305   const uint8_t *data;
6306   int rv;
6307   uint64_t offset;
6308   uint32_t sdflags;
6309   int handshake_completed = conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED;
6310 
6311   if (!strm->rx.rob) {
6312     return 0;
6313   }
6314 
6315   for (;;) {
6316     /* Stop calling callback if application has called
6317        ngtcp2_conn_shutdown_stream_read() inside the callback.
6318        Because it doubly counts connection window. */
6319     if (strm->flags & (NGTCP2_STRM_FLAG_STOP_SENDING)) {
6320       return 0;
6321     }
6322 
6323     datalen = ngtcp2_rob_data_at(strm->rx.rob, &data, rx_offset);
6324     if (datalen == 0) {
6325       assert(rx_offset == ngtcp2_strm_rx_offset(strm));
6326       return 0;
6327     }
6328 
6329     offset = rx_offset;
6330     rx_offset += datalen;
6331 
6332     sdflags = NGTCP2_STREAM_DATA_FLAG_NONE;
6333     if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
6334         rx_offset == strm->rx.last_offset) {
6335       sdflags |= NGTCP2_STREAM_DATA_FLAG_FIN;
6336     }
6337     if (!handshake_completed) {
6338       sdflags |= NGTCP2_STREAM_DATA_FLAG_EARLY;
6339     }
6340 
6341     rv = conn_call_recv_stream_data(conn, strm, sdflags, offset, data, datalen);
6342     if (rv != 0) {
6343       return rv;
6344     }
6345 
6346     ngtcp2_rob_pop(strm->rx.rob, rx_offset - datalen, datalen);
6347   }
6348 }
6349 
6350 /*
6351  * conn_recv_crypto is called when CRYPTO frame |fr| is received.
6352  * |rx_offset_base| is the offset in the entire TLS handshake stream.
6353  * fr->offset specifies the offset in each encryption level.
6354  * |max_rx_offset| is, if it is nonzero, the maximum offset in the
6355  * entire TLS handshake stream that |fr| can carry.  |crypto_level| is
6356  * the encryption level where this data is received.
6357  *
6358  * This function returns 0 if it succeeds, or one of the following
6359  * negative error codes:
6360  *
6361  * NGTCP2_ERR_PROTO
6362  *     CRYPTO frame has invalid offset.
6363  * NGTCP2_ERR_NOMEM
6364  *     Out of memory.
6365  * NGTCP2_ERR_CRYPTO
6366  *     TLS stack reported error.
6367  * NGTCP2_ERR_FRAME_ENCODING
6368  *     The end offset exceeds the maximum value.
6369  * NGTCP2_ERR_CALLBACK_FAILURE
6370  *     User-defined callback function failed.
6371  */
conn_recv_crypto(ngtcp2_conn * conn,ngtcp2_crypto_level crypto_level,ngtcp2_strm * crypto,const ngtcp2_crypto * fr)6372 static int conn_recv_crypto(ngtcp2_conn *conn, ngtcp2_crypto_level crypto_level,
6373                             ngtcp2_strm *crypto, const ngtcp2_crypto *fr) {
6374   uint64_t fr_end_offset;
6375   uint64_t rx_offset;
6376   int rv;
6377 
6378   if (fr->datacnt == 0) {
6379     return 0;
6380   }
6381 
6382   fr_end_offset = fr->offset + fr->data[0].len;
6383 
6384   if (NGTCP2_MAX_VARINT < fr_end_offset) {
6385     return NGTCP2_ERR_FRAME_ENCODING;
6386   }
6387 
6388   rx_offset = ngtcp2_strm_rx_offset(crypto);
6389 
6390   if (fr_end_offset <= rx_offset) {
6391     if (conn->server &&
6392         !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_EARLY_RETRANSMIT) &&
6393         crypto_level == NGTCP2_CRYPTO_LEVEL_INITIAL) {
6394       /* recovery draft: Speeding Up Handshake Completion
6395 
6396          When a server receives an Initial packet containing duplicate
6397          CRYPTO data, it can assume the client did not receive all of
6398          the server's CRYPTO data sent in Initial packets, or the
6399          client's estimated RTT is too small.  ...  To speed up
6400          handshake completion under these conditions, an endpoint MAY
6401          send a packet containing unacknowledged CRYPTO data earlier
6402          than the PTO expiry, subject to address validation limits;
6403          ... */
6404       conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_EARLY_RETRANSMIT;
6405       conn->in_pktns->rtb.probe_pkt_left = 1;
6406       conn->hs_pktns->rtb.probe_pkt_left = 1;
6407     }
6408     return 0;
6409   }
6410 
6411   crypto->rx.last_offset = ngtcp2_max(crypto->rx.last_offset, fr_end_offset);
6412 
6413   /* TODO Before dispatching incoming data to TLS stack, make sure
6414      that previous data in previous encryption level has been
6415      completely sent to TLS stack.  Usually, if data is left, it is an
6416      error because key is generated after consuming all data in the
6417      previous encryption level. */
6418   if (fr->offset <= rx_offset) {
6419     size_t ncut = (size_t)(rx_offset - fr->offset);
6420     const uint8_t *data = fr->data[0].base + ncut;
6421     size_t datalen = fr->data[0].len - ncut;
6422     uint64_t offset = rx_offset;
6423 
6424     rx_offset += datalen;
6425     rv = ngtcp2_strm_update_rx_offset(crypto, rx_offset);
6426     if (rv != 0) {
6427       return rv;
6428     }
6429 
6430     rv = conn_call_recv_crypto_data(conn, crypto_level, offset, data, datalen);
6431     if (rv != 0) {
6432       return rv;
6433     }
6434 
6435     rv = conn_emit_pending_crypto_data(conn, crypto_level, crypto, rx_offset);
6436     if (rv != 0) {
6437       return rv;
6438     }
6439 
6440     return 0;
6441   }
6442 
6443   if (fr_end_offset - rx_offset > NGTCP2_MAX_REORDERED_CRYPTO_DATA) {
6444     return NGTCP2_ERR_CRYPTO_BUFFER_EXCEEDED;
6445   }
6446 
6447   return ngtcp2_strm_recv_reordering(crypto, fr->data[0].base, fr->data[0].len,
6448                                      fr->offset);
6449 }
6450 
6451 /*
6452  * conn_max_data_violated returns nonzero if receiving |datalen|
6453  * violates connection flow control on local endpoint.
6454  */
conn_max_data_violated(ngtcp2_conn * conn,uint64_t datalen)6455 static int conn_max_data_violated(ngtcp2_conn *conn, uint64_t datalen) {
6456   return conn->rx.max_offset - conn->rx.offset < datalen;
6457 }
6458 
6459 /*
6460  * conn_recv_stream is called when STREAM frame |fr| is received.
6461  *
6462  * This function returns 0 if it succeeds, or one of the following
6463  * negative error codes:
6464  *
6465  * NGTCP2_ERR_STREAM_STATE
6466  *     STREAM frame is received for a local stream which is not
6467  *     initiated; or STREAM frame is received for a local
6468  *     unidirectional stream
6469  * NGTCP2_ERR_STREAM_LIMIT
6470  *     STREAM frame has remote stream ID which is strictly greater
6471  *     than the allowed limit.
6472  * NGTCP2_ERR_NOMEM
6473  *     Out of memory.
6474  * NGTCP2_ERR_CALLBACK_FAILURE
6475  *     User-defined callback function failed.
6476  * NGTCP2_ERR_FLOW_CONTROL
6477  *     Flow control limit is violated; or the end offset of stream
6478  *     data is beyond the NGTCP2_MAX_VARINT.
6479  * NGTCP2_ERR_FINAL_SIZE
6480  *     STREAM frame has strictly larger end offset than it is
6481  *     permitted.
6482  */
conn_recv_stream(ngtcp2_conn * conn,const ngtcp2_stream * fr)6483 static int conn_recv_stream(ngtcp2_conn *conn, const ngtcp2_stream *fr) {
6484   int rv;
6485   ngtcp2_strm *strm;
6486   ngtcp2_idtr *idtr;
6487   uint64_t rx_offset, fr_end_offset;
6488   int local_stream;
6489   int bidi;
6490   uint64_t datalen = ngtcp2_vec_len(fr->data, fr->datacnt);
6491   uint32_t sdflags = NGTCP2_STREAM_DATA_FLAG_NONE;
6492 
6493   local_stream = conn_local_stream(conn, fr->stream_id);
6494   bidi = bidi_stream(fr->stream_id);
6495 
6496   if (bidi) {
6497     if (local_stream) {
6498       if (conn->local.bidi.next_stream_id <= fr->stream_id) {
6499         return NGTCP2_ERR_STREAM_STATE;
6500       }
6501     } else if (conn->remote.bidi.max_streams <
6502                ngtcp2_ord_stream_id(fr->stream_id)) {
6503       return NGTCP2_ERR_STREAM_LIMIT;
6504     }
6505 
6506     idtr = &conn->remote.bidi.idtr;
6507   } else {
6508     if (local_stream) {
6509       return NGTCP2_ERR_STREAM_STATE;
6510     }
6511     if (conn->remote.uni.max_streams < ngtcp2_ord_stream_id(fr->stream_id)) {
6512       return NGTCP2_ERR_STREAM_LIMIT;
6513     }
6514 
6515     idtr = &conn->remote.uni.idtr;
6516   }
6517 
6518   if (NGTCP2_MAX_VARINT - datalen < fr->offset) {
6519     return NGTCP2_ERR_FLOW_CONTROL;
6520   }
6521 
6522   strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
6523   if (strm == NULL) {
6524     if (local_stream) {
6525       /* TODO The stream has been closed.  This should be responded
6526          with RESET_STREAM, or simply ignored. */
6527       return 0;
6528     }
6529 
6530     rv = ngtcp2_idtr_open(idtr, fr->stream_id);
6531     if (rv != 0) {
6532       if (ngtcp2_err_is_fatal(rv)) {
6533         return rv;
6534       }
6535       assert(rv == NGTCP2_ERR_STREAM_IN_USE);
6536       /* TODO The stream has been closed.  This should be responded
6537          with RESET_STREAM, or simply ignored. */
6538       return 0;
6539     }
6540 
6541     strm = ngtcp2_mem_malloc(conn->mem, sizeof(ngtcp2_strm));
6542     if (strm == NULL) {
6543       return NGTCP2_ERR_NOMEM;
6544     }
6545     /* TODO Perhaps, call new_stream callback? */
6546     rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
6547     if (rv != 0) {
6548       ngtcp2_mem_free(conn->mem, strm);
6549       return rv;
6550     }
6551 
6552     rv = conn_call_stream_open(conn, strm);
6553     if (rv != 0) {
6554       return rv;
6555     }
6556 
6557     if (!bidi) {
6558       ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_WR);
6559     }
6560   }
6561 
6562   fr_end_offset = fr->offset + datalen;
6563 
6564   if (strm->rx.max_offset < fr_end_offset) {
6565     return NGTCP2_ERR_FLOW_CONTROL;
6566   }
6567 
6568   if (strm->rx.last_offset < fr_end_offset) {
6569     uint64_t len = fr_end_offset - strm->rx.last_offset;
6570 
6571     if (conn_max_data_violated(conn, len)) {
6572       return NGTCP2_ERR_FLOW_CONTROL;
6573     }
6574 
6575     conn->rx.offset += len;
6576 
6577     if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
6578       ngtcp2_conn_extend_max_offset(conn, len);
6579     }
6580   }
6581 
6582   rx_offset = ngtcp2_strm_rx_offset(strm);
6583 
6584   if (fr->fin) {
6585     if (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) {
6586       if (strm->rx.last_offset != fr_end_offset) {
6587         return NGTCP2_ERR_FINAL_SIZE;
6588       }
6589 
6590       if (strm->flags &
6591           (NGTCP2_STRM_FLAG_STOP_SENDING | NGTCP2_STRM_FLAG_RECV_RST)) {
6592         return 0;
6593       }
6594 
6595       if (rx_offset == fr_end_offset) {
6596         return 0;
6597       }
6598     } else if (strm->rx.last_offset > fr_end_offset) {
6599       return NGTCP2_ERR_FINAL_SIZE;
6600     } else {
6601       strm->rx.last_offset = fr_end_offset;
6602 
6603       ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_RD);
6604 
6605       if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
6606         return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
6607       }
6608     }
6609   } else {
6610     if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
6611         strm->rx.last_offset < fr_end_offset) {
6612       return NGTCP2_ERR_FINAL_SIZE;
6613     }
6614 
6615     strm->rx.last_offset = ngtcp2_max(strm->rx.last_offset, fr_end_offset);
6616 
6617     if (fr_end_offset <= rx_offset) {
6618       return 0;
6619     }
6620 
6621     if (strm->flags &
6622         (NGTCP2_STRM_FLAG_STOP_SENDING | NGTCP2_STRM_FLAG_RECV_RST)) {
6623       return 0;
6624     }
6625   }
6626 
6627   if (fr->offset <= rx_offset) {
6628     size_t ncut = (size_t)(rx_offset - fr->offset);
6629     uint64_t offset = rx_offset;
6630     const uint8_t *data;
6631     int fin;
6632 
6633     if (fr->datacnt) {
6634       data = fr->data[0].base + ncut;
6635       datalen -= ncut;
6636 
6637       rx_offset += datalen;
6638       rv = ngtcp2_strm_update_rx_offset(strm, rx_offset);
6639       if (rv != 0) {
6640         return rv;
6641       }
6642     } else {
6643       data = NULL;
6644       datalen = 0;
6645     }
6646 
6647     fin = (strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
6648           rx_offset == strm->rx.last_offset;
6649 
6650     if (fin || datalen) {
6651       if (fin) {
6652         sdflags |= NGTCP2_STREAM_DATA_FLAG_FIN;
6653       }
6654       if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
6655         sdflags |= NGTCP2_STREAM_DATA_FLAG_EARLY;
6656       }
6657       rv = conn_call_recv_stream_data(conn, strm, sdflags, offset, data,
6658                                       (size_t)datalen);
6659       if (rv != 0) {
6660         return rv;
6661       }
6662 
6663       rv = conn_emit_pending_stream_data(conn, strm, rx_offset);
6664       if (rv != 0) {
6665         return rv;
6666       }
6667     }
6668   } else if (fr->datacnt) {
6669     rv = ngtcp2_strm_recv_reordering(strm, fr->data[0].base, fr->data[0].len,
6670                                      fr->offset);
6671     if (rv != 0) {
6672       return rv;
6673     }
6674   }
6675   return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
6676 }
6677 
6678 /*
6679  * conn_reset_stream adds RESET_STREAM frame to the transmission
6680  * queue.
6681  *
6682  * This function returns 0 if it succeeds, or one of the following
6683  * negative error codes:
6684  *
6685  * NGTCP2_ERR_NOMEM
6686  *     Out of memory.
6687  */
conn_reset_stream(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t app_error_code)6688 static int conn_reset_stream(ngtcp2_conn *conn, ngtcp2_strm *strm,
6689                              uint64_t app_error_code) {
6690   int rv;
6691   ngtcp2_frame_chain *frc;
6692   ngtcp2_pktns *pktns = &conn->pktns;
6693 
6694   rv = ngtcp2_frame_chain_new(&frc, conn->mem);
6695   if (rv != 0) {
6696     return rv;
6697   }
6698 
6699   frc->fr.type = NGTCP2_FRAME_RESET_STREAM;
6700   frc->fr.reset_stream.stream_id = strm->stream_id;
6701   frc->fr.reset_stream.app_error_code = app_error_code;
6702   frc->fr.reset_stream.final_size = strm->tx.offset;
6703 
6704   /* TODO This prepends RESET_STREAM to pktns->tx.frq. */
6705   frc->next = pktns->tx.frq;
6706   pktns->tx.frq = frc;
6707 
6708   return 0;
6709 }
6710 
6711 /*
6712  * conn_stop_sending adds STOP_SENDING frame to the transmission
6713  * queue.
6714  *
6715  * This function returns 0 if it succeeds, or one of the following
6716  * negative error codes:
6717  *
6718  * NGTCP2_ERR_NOMEM
6719  *     Out of memory.
6720  */
conn_stop_sending(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t app_error_code)6721 static int conn_stop_sending(ngtcp2_conn *conn, ngtcp2_strm *strm,
6722                              uint64_t app_error_code) {
6723   int rv;
6724   ngtcp2_frame_chain *frc;
6725   ngtcp2_pktns *pktns = &conn->pktns;
6726 
6727   rv = ngtcp2_frame_chain_new(&frc, conn->mem);
6728   if (rv != 0) {
6729     return rv;
6730   }
6731 
6732   frc->fr.type = NGTCP2_FRAME_STOP_SENDING;
6733   frc->fr.stop_sending.stream_id = strm->stream_id;
6734   frc->fr.stop_sending.app_error_code = app_error_code;
6735 
6736   /* TODO This prepends STOP_SENDING to pktns->tx.frq. */
6737   frc->next = pktns->tx.frq;
6738   pktns->tx.frq = frc;
6739 
6740   return 0;
6741 }
6742 
6743 /*
6744  * handle_max_remote_streams_extension extends
6745  * |*punsent_max_remote_streams| by |n| if a condition allows it.
6746  */
6747 static void
handle_max_remote_streams_extension(uint64_t * punsent_max_remote_streams,size_t n)6748 handle_max_remote_streams_extension(uint64_t *punsent_max_remote_streams,
6749                                     size_t n) {
6750   if (
6751 #if SIZE_MAX > UINT32_MAX
6752       NGTCP2_MAX_STREAMS < n ||
6753 #endif /* SIZE_MAX > UINT32_MAX */
6754       *punsent_max_remote_streams > (uint64_t)(NGTCP2_MAX_STREAMS - n)) {
6755     *punsent_max_remote_streams = NGTCP2_MAX_STREAMS;
6756   } else {
6757     *punsent_max_remote_streams += n;
6758   }
6759 }
6760 
6761 /*
6762  * conn_recv_reset_stream is called when RESET_STREAM |fr| is
6763  * received.
6764  *
6765  * This function returns 0 if it succeeds, or one of the following
6766  * negative error codes:
6767  *
6768  * NGTCP2_ERR_STREAM_STATE
6769  *     RESET_STREAM frame is received to the local stream which is not
6770  *     initiated.
6771  * NGTCP2_ERR_STREAM_LIMIT
6772  *     RESET_STREAM frame has remote stream ID which is strictly
6773  *     greater than the allowed limit.
6774  * NGTCP2_ERR_PROTO
6775  *     RESET_STREAM frame is received to the local unidirectional
6776  *     stream
6777  * NGTCP2_ERR_NOMEM
6778  *     Out of memory.
6779  * NGTCP2_ERR_CALLBACK_FAILURE
6780  *     User-defined callback function failed.
6781  * NGTCP2_ERR_FLOW_CONTROL
6782  *     Flow control limit is violated; or the final size is beyond the
6783  *     NGTCP2_MAX_VARINT.
6784  * NGTCP2_ERR_FINAL_SIZE
6785  *     The final offset is strictly larger than it is permitted.
6786  */
conn_recv_reset_stream(ngtcp2_conn * conn,const ngtcp2_reset_stream * fr)6787 static int conn_recv_reset_stream(ngtcp2_conn *conn,
6788                                   const ngtcp2_reset_stream *fr) {
6789   ngtcp2_strm *strm;
6790   int local_stream = conn_local_stream(conn, fr->stream_id);
6791   int bidi = bidi_stream(fr->stream_id);
6792   uint64_t datalen;
6793   ngtcp2_idtr *idtr;
6794   int rv;
6795 
6796   /* TODO share this piece of code */
6797   if (bidi) {
6798     if (local_stream) {
6799       if (conn->local.bidi.next_stream_id <= fr->stream_id) {
6800         return NGTCP2_ERR_STREAM_STATE;
6801       }
6802     } else if (conn->remote.bidi.max_streams <
6803                ngtcp2_ord_stream_id(fr->stream_id)) {
6804       return NGTCP2_ERR_STREAM_LIMIT;
6805     }
6806 
6807     idtr = &conn->remote.bidi.idtr;
6808   } else {
6809     if (local_stream) {
6810       return NGTCP2_ERR_PROTO;
6811     }
6812     if (conn->remote.uni.max_streams < ngtcp2_ord_stream_id(fr->stream_id)) {
6813       return NGTCP2_ERR_STREAM_LIMIT;
6814     }
6815 
6816     idtr = &conn->remote.uni.idtr;
6817   }
6818 
6819   if (NGTCP2_MAX_VARINT < fr->final_size) {
6820     return NGTCP2_ERR_FLOW_CONTROL;
6821   }
6822 
6823   strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
6824   if (strm == NULL) {
6825     if (local_stream) {
6826       return 0;
6827     }
6828 
6829     rv = ngtcp2_idtr_open(idtr, fr->stream_id);
6830     if (rv != 0) {
6831       if (ngtcp2_err_is_fatal(rv)) {
6832         return rv;
6833       }
6834       assert(rv == NGTCP2_ERR_STREAM_IN_USE);
6835       return 0;
6836     }
6837 
6838     if (conn_initial_stream_rx_offset(conn, fr->stream_id) < fr->final_size ||
6839         conn_max_data_violated(conn, fr->final_size)) {
6840       return NGTCP2_ERR_FLOW_CONTROL;
6841     }
6842 
6843     /* Stream is reset before we create ngtcp2_strm object. */
6844     conn->rx.offset += fr->final_size;
6845     ngtcp2_conn_extend_max_offset(conn, fr->final_size);
6846 
6847     rv = conn_call_stream_reset(conn, fr->stream_id, fr->final_size,
6848                                 fr->app_error_code, NULL);
6849     if (rv != 0) {
6850       return rv;
6851     }
6852 
6853     /* There will be no activity in this stream because we got
6854        RESET_STREAM and don't write stream data any further.  This
6855        effectively allows another new stream for peer. */
6856     if (bidi) {
6857       handle_max_remote_streams_extension(&conn->remote.bidi.unsent_max_streams,
6858                                           1);
6859     } else {
6860       handle_max_remote_streams_extension(&conn->remote.uni.unsent_max_streams,
6861                                           1);
6862     }
6863 
6864     return 0;
6865   }
6866 
6867   if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD)) {
6868     if (strm->rx.last_offset != fr->final_size) {
6869       return NGTCP2_ERR_FINAL_SIZE;
6870     }
6871   } else if (strm->rx.last_offset > fr->final_size) {
6872     return NGTCP2_ERR_FINAL_SIZE;
6873   }
6874 
6875   if (strm->flags & NGTCP2_STRM_FLAG_RECV_RST) {
6876     return 0;
6877   }
6878 
6879   if (strm->rx.max_offset < fr->final_size) {
6880     return NGTCP2_ERR_FLOW_CONTROL;
6881   }
6882 
6883   datalen = fr->final_size - strm->rx.last_offset;
6884 
6885   if (conn_max_data_violated(conn, datalen)) {
6886     return NGTCP2_ERR_FLOW_CONTROL;
6887   }
6888 
6889   rv = conn_call_stream_reset(conn, fr->stream_id, fr->final_size,
6890                               fr->app_error_code, strm->stream_user_data);
6891   if (rv != 0) {
6892     return rv;
6893   }
6894 
6895   /* Extend connection flow control window for the amount of data
6896      which are not passed to application. */
6897   if (!(strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING)) {
6898     ngtcp2_conn_extend_max_offset(conn, strm->rx.last_offset -
6899                                             ngtcp2_strm_rx_offset(strm));
6900   }
6901 
6902   conn->rx.offset += datalen;
6903   ngtcp2_conn_extend_max_offset(conn, datalen);
6904 
6905   strm->rx.last_offset = fr->final_size;
6906   strm->flags |= NGTCP2_STRM_FLAG_SHUT_RD | NGTCP2_STRM_FLAG_RECV_RST;
6907 
6908   ngtcp2_strm_set_app_error_code(strm, fr->app_error_code);
6909 
6910   return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
6911 }
6912 
6913 /*
6914  * conn_recv_stop_sending is called when STOP_SENDING |fr| is received.
6915  *
6916  * This function returns 0 if it succeeds, or one of the following
6917  * negative error codes:
6918  *
6919  * NGTCP2_ERR_STREAM_STATE
6920  *     STOP_SENDING frame is received for a local stream which is not
6921  *     initiated; or STOP_SENDING frame is received for a local
6922  *     unidirectional stream.
6923  * NGTCP2_ERR_STREAM_LIMIT
6924  *     STOP_SENDING frame has remote stream ID which is strictly
6925  *     greater than the allowed limit.
6926  * NGTCP2_ERR_NOMEM
6927  *     Out of memory.
6928  * NGTCP2_ERR_CALLBACK_FAILURE
6929  *     User-defined callback function failed.
6930  */
conn_recv_stop_sending(ngtcp2_conn * conn,const ngtcp2_stop_sending * fr)6931 static int conn_recv_stop_sending(ngtcp2_conn *conn,
6932                                   const ngtcp2_stop_sending *fr) {
6933   int rv;
6934   ngtcp2_strm *strm;
6935   ngtcp2_idtr *idtr;
6936   int local_stream = conn_local_stream(conn, fr->stream_id);
6937   int bidi = bidi_stream(fr->stream_id);
6938 
6939   if (bidi) {
6940     if (local_stream) {
6941       if (conn->local.bidi.next_stream_id <= fr->stream_id) {
6942         return NGTCP2_ERR_STREAM_STATE;
6943       }
6944     } else if (conn->remote.bidi.max_streams <
6945                ngtcp2_ord_stream_id(fr->stream_id)) {
6946       return NGTCP2_ERR_STREAM_LIMIT;
6947     }
6948 
6949     idtr = &conn->remote.bidi.idtr;
6950   } else {
6951     if (!local_stream || conn->local.uni.next_stream_id <= fr->stream_id) {
6952       return NGTCP2_ERR_STREAM_STATE;
6953     }
6954 
6955     idtr = &conn->remote.uni.idtr;
6956   }
6957 
6958   strm = ngtcp2_conn_find_stream(conn, fr->stream_id);
6959   if (strm == NULL) {
6960     if (local_stream) {
6961       return 0;
6962     }
6963     rv = ngtcp2_idtr_open(idtr, fr->stream_id);
6964     if (rv != 0) {
6965       if (ngtcp2_err_is_fatal(rv)) {
6966         return rv;
6967       }
6968       assert(rv == NGTCP2_ERR_STREAM_IN_USE);
6969       return 0;
6970     }
6971 
6972     /* Frame is received reset before we create ngtcp2_strm
6973        object. */
6974     strm = ngtcp2_mem_malloc(conn->mem, sizeof(ngtcp2_strm));
6975     if (strm == NULL) {
6976       return NGTCP2_ERR_NOMEM;
6977     }
6978     rv = ngtcp2_conn_init_stream(conn, strm, fr->stream_id, NULL);
6979     if (rv != 0) {
6980       ngtcp2_mem_free(conn->mem, strm);
6981       return rv;
6982     }
6983 
6984     rv = conn_call_stream_open(conn, strm);
6985     if (rv != 0) {
6986       return rv;
6987     }
6988   }
6989 
6990   ngtcp2_strm_set_app_error_code(strm, fr->app_error_code);
6991 
6992   /* No RESET_STREAM is required if we have sent FIN and all data have
6993      been acknowledged. */
6994   if ((!(strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) ||
6995        !ngtcp2_strm_is_all_tx_data_acked(strm)) &&
6996       !(strm->flags & NGTCP2_STRM_FLAG_SENT_RST)) {
6997     rv = conn_reset_stream(conn, strm, fr->app_error_code);
6998     if (rv != 0) {
6999       return rv;
7000     }
7001   }
7002 
7003   strm->flags |= NGTCP2_STRM_FLAG_SHUT_WR | NGTCP2_STRM_FLAG_SENT_RST;
7004 
7005   ngtcp2_strm_streamfrq_clear(strm);
7006 
7007   return ngtcp2_conn_close_stream_if_shut_rdwr(conn, strm);
7008 }
7009 
7010 /*
7011  * check_stateless_reset returns nonzero if Stateless Reset |sr|
7012  * coming via |path| is valid against |dcid|.
7013  */
check_stateless_reset(const ngtcp2_dcid * dcid,const ngtcp2_path * path,const ngtcp2_pkt_stateless_reset * sr)7014 static int check_stateless_reset(const ngtcp2_dcid *dcid,
7015                                  const ngtcp2_path *path,
7016                                  const ngtcp2_pkt_stateless_reset *sr) {
7017   return ngtcp2_path_eq(&dcid->ps.path, path) &&
7018          ngtcp2_dcid_verify_stateless_reset_token(
7019              dcid, sr->stateless_reset_token) == 0;
7020 }
7021 
7022 /*
7023  * conn_on_stateless_reset decodes Stateless Reset from the buffer
7024  * pointed by |payload| whose length is |payloadlen|.  |payload|
7025  * should start after first byte of packet.
7026  *
7027  * If Stateless Reset is decoded, and the Stateless Reset Token is
7028  * validated, the connection is closed.
7029  *
7030  * This function returns 0 if it succeeds, or one of the following
7031  * negative error codes:
7032  *
7033  * NGTCP2_ERR_INVALID_ARGUMENT
7034  *     Could not decode Stateless Reset; or Stateless Reset Token does
7035  *     not match; or No stateless reset token is available.
7036  * NGTCP2_ERR_CALLBACK_FAILURE
7037  *     User callback failed.
7038  */
conn_on_stateless_reset(ngtcp2_conn * conn,const ngtcp2_path * path,const uint8_t * payload,size_t payloadlen)7039 static int conn_on_stateless_reset(ngtcp2_conn *conn, const ngtcp2_path *path,
7040                                    const uint8_t *payload, size_t payloadlen) {
7041   int rv = 1;
7042   ngtcp2_pv *pv = conn->pv;
7043   ngtcp2_dcid *dcid;
7044   ngtcp2_pkt_stateless_reset sr;
7045   size_t len, i;
7046 
7047   rv = ngtcp2_pkt_decode_stateless_reset(&sr, payload, payloadlen);
7048   if (rv != 0) {
7049     return rv;
7050   }
7051 
7052   if (!check_stateless_reset(&conn->dcid.current, path, &sr) &&
7053       (!pv || (!check_stateless_reset(&pv->dcid, path, &sr) &&
7054                (!(pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) ||
7055                 !check_stateless_reset(&pv->fallback_dcid, path, &sr))))) {
7056     len = ngtcp2_ringbuf_len(&conn->dcid.retired);
7057     for (i = 0; i < len; ++i) {
7058       dcid = ngtcp2_ringbuf_get(&conn->dcid.retired, i);
7059       if (check_stateless_reset(dcid, path, &sr)) {
7060         break;
7061       }
7062     }
7063 
7064     if (i == len) {
7065       len = ngtcp2_ringbuf_len(&conn->dcid.bound);
7066       for (i = 0; i < len; ++i) {
7067         dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
7068         if (check_stateless_reset(dcid, path, &sr)) {
7069           break;
7070         }
7071       }
7072 
7073       if (i == len) {
7074         return NGTCP2_ERR_INVALID_ARGUMENT;
7075       }
7076     }
7077   }
7078 
7079   conn->state = NGTCP2_CS_DRAINING;
7080 
7081   ngtcp2_log_rx_sr(&conn->log, &sr);
7082 
7083   return conn_call_recv_stateless_reset(conn, &sr);
7084 }
7085 
7086 /*
7087  * conn_recv_max_streams processes the incoming MAX_STREAMS frame
7088  * |fr|.
7089  *
7090  * This function returns 0 if it succeeds, or one of the following
7091  * negative error codes:
7092  *
7093  * NGTCP2_ERR_CALLBACK_FAILURE
7094  *     User callback failed.
7095  * NGTCP2_ERR_FRAME_ENCODING
7096  *     The maximum streams field exceeds the maximum value.
7097  */
conn_recv_max_streams(ngtcp2_conn * conn,const ngtcp2_max_streams * fr)7098 static int conn_recv_max_streams(ngtcp2_conn *conn,
7099                                  const ngtcp2_max_streams *fr) {
7100   uint64_t n;
7101 
7102   if (fr->max_streams > NGTCP2_MAX_STREAMS) {
7103     return NGTCP2_ERR_FRAME_ENCODING;
7104   }
7105 
7106   n = ngtcp2_min(fr->max_streams, NGTCP2_MAX_STREAMS);
7107 
7108   if (fr->type == NGTCP2_FRAME_MAX_STREAMS_BIDI) {
7109     if (conn->local.bidi.max_streams < n) {
7110       conn->local.bidi.max_streams = n;
7111       return conn_call_extend_max_local_streams_bidi(conn, n);
7112     }
7113     return 0;
7114   }
7115 
7116   if (conn->local.uni.max_streams < n) {
7117     conn->local.uni.max_streams = n;
7118     return conn_call_extend_max_local_streams_uni(conn, n);
7119   }
7120   return 0;
7121 }
7122 
conn_retire_dcid_prior_to(ngtcp2_conn * conn,ngtcp2_ringbuf * rb,uint64_t retire_prior_to)7123 static int conn_retire_dcid_prior_to(ngtcp2_conn *conn, ngtcp2_ringbuf *rb,
7124                                      uint64_t retire_prior_to) {
7125   size_t i;
7126   ngtcp2_dcid *dcid, *last;
7127   int rv;
7128 
7129   for (i = 0; i < ngtcp2_ringbuf_len(rb);) {
7130     dcid = ngtcp2_ringbuf_get(rb, i);
7131     if (dcid->seq >= retire_prior_to) {
7132       ++i;
7133       continue;
7134     }
7135 
7136     rv = conn_retire_dcid_seq(conn, dcid->seq);
7137     if (rv != 0) {
7138       return rv;
7139     }
7140     if (i == 0) {
7141       ngtcp2_ringbuf_pop_front(rb);
7142     } else if (i == ngtcp2_ringbuf_len(rb) - 1) {
7143       ngtcp2_ringbuf_pop_back(rb);
7144       break;
7145     } else {
7146       last = ngtcp2_ringbuf_get(rb, ngtcp2_ringbuf_len(rb) - 1);
7147       ngtcp2_dcid_copy(dcid, last);
7148       ngtcp2_ringbuf_pop_back(rb);
7149     }
7150   }
7151 
7152   return 0;
7153 }
7154 
7155 /*
7156  * conn_recv_new_connection_id processes the incoming
7157  * NEW_CONNECTION_ID frame |fr|.
7158  *
7159  * This function returns 0 if it succeeds, or one of the following
7160  * negative error codes:
7161  *
7162  * NGTCP2_ERR_PROTO
7163  *     |fr| has the duplicated sequence number with different CID or
7164  *     token; or DCID is zero-length.
7165  */
conn_recv_new_connection_id(ngtcp2_conn * conn,const ngtcp2_new_connection_id * fr)7166 static int conn_recv_new_connection_id(ngtcp2_conn *conn,
7167                                        const ngtcp2_new_connection_id *fr) {
7168   size_t i, len;
7169   ngtcp2_dcid *dcid;
7170   ngtcp2_pv *pv = conn->pv;
7171   int rv;
7172   int found = 0;
7173   size_t extra_dcid = 0;
7174 
7175   if (conn->dcid.current.cid.datalen == 0) {
7176     return NGTCP2_ERR_PROTO;
7177   }
7178 
7179   if (fr->retire_prior_to > fr->seq) {
7180     return NGTCP2_ERR_FRAME_ENCODING;
7181   }
7182 
7183   rv = ngtcp2_dcid_verify_uniqueness(&conn->dcid.current, fr->seq, &fr->cid,
7184                                      fr->stateless_reset_token);
7185   if (rv != 0) {
7186     return rv;
7187   }
7188   if (ngtcp2_cid_eq(&conn->dcid.current.cid, &fr->cid)) {
7189     found = 1;
7190   }
7191 
7192   if (pv) {
7193     rv = ngtcp2_dcid_verify_uniqueness(&pv->dcid, fr->seq, &fr->cid,
7194                                        fr->stateless_reset_token);
7195     if (rv != 0) {
7196       return rv;
7197     }
7198     if (ngtcp2_cid_eq(&pv->dcid.cid, &fr->cid)) {
7199       found = 1;
7200     }
7201   }
7202 
7203   len = ngtcp2_ringbuf_len(&conn->dcid.bound);
7204 
7205   for (i = 0; i < len; ++i) {
7206     dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
7207     rv = ngtcp2_dcid_verify_uniqueness(dcid, fr->seq, &fr->cid,
7208                                        fr->stateless_reset_token);
7209     if (rv != 0) {
7210       return NGTCP2_ERR_PROTO;
7211     }
7212     if (ngtcp2_cid_eq(&dcid->cid, &fr->cid)) {
7213       found = 1;
7214     }
7215   }
7216 
7217   len = ngtcp2_ringbuf_len(&conn->dcid.unused);
7218 
7219   for (i = 0; i < len; ++i) {
7220     dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, i);
7221     rv = ngtcp2_dcid_verify_uniqueness(dcid, fr->seq, &fr->cid,
7222                                        fr->stateless_reset_token);
7223     if (rv != 0) {
7224       return NGTCP2_ERR_PROTO;
7225     }
7226     if (ngtcp2_cid_eq(&dcid->cid, &fr->cid)) {
7227       found = 1;
7228     }
7229   }
7230 
7231   if (conn->dcid.retire_prior_to < fr->retire_prior_to) {
7232     conn->dcid.retire_prior_to = fr->retire_prior_to;
7233 
7234     rv =
7235         conn_retire_dcid_prior_to(conn, &conn->dcid.bound, fr->retire_prior_to);
7236     if (rv != 0) {
7237       return rv;
7238     }
7239 
7240     rv = conn_retire_dcid_prior_to(conn, &conn->dcid.unused,
7241                                    conn->dcid.retire_prior_to);
7242     if (rv != 0) {
7243       return rv;
7244     }
7245   } else if (fr->seq < conn->dcid.retire_prior_to) {
7246     /* If packets are reordered, we might have retire_prior_to which
7247        is larger than fr->seq.
7248 
7249        A malicious peer might send crafted NEW_CONNECTION_ID to force
7250        local endpoint to create lots of RETIRE_CONNECTION_ID frames.
7251        For example, a peer might send seq = 50000 and retire_prior_to
7252        = 50000.  Then send NEW_CONNECTION_ID frames with seq <
7253        50000. */
7254     /* TODO we might queue lots of RETIRE_CONNECTION_ID frame here
7255        because conn->dcid.num_retire_queued is incremented when the
7256        frame is serialized. */
7257     if (conn->dcid.num_retire_queued < NGTCP2_MAX_DCID_POOL_SIZE * 2) {
7258       return conn_retire_dcid_seq(conn, fr->seq);
7259     }
7260     return 0;
7261   }
7262 
7263   if (found) {
7264     return 0;
7265   }
7266 
7267   if (ngtcp2_gaptr_is_pushed(&conn->dcid.seqgap, fr->seq, 1)) {
7268     return 0;
7269   }
7270 
7271   rv = ngtcp2_gaptr_push(&conn->dcid.seqgap, fr->seq, 1);
7272   if (rv != 0) {
7273     return rv;
7274   }
7275 
7276   if (ngtcp2_ksl_len(&conn->dcid.seqgap.gap) > 32) {
7277     ngtcp2_gaptr_drop_first_gap(&conn->dcid.seqgap);
7278   }
7279 
7280   len = ngtcp2_ringbuf_len(&conn->dcid.unused);
7281 
7282   if (conn->dcid.current.seq >= conn->dcid.retire_prior_to) {
7283     ++extra_dcid;
7284   }
7285   if (pv) {
7286     if (pv->dcid.seq != conn->dcid.current.seq &&
7287         pv->dcid.seq >= conn->dcid.retire_prior_to) {
7288       ++extra_dcid;
7289     }
7290     if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7291         pv->fallback_dcid.seq != conn->dcid.current.seq &&
7292         pv->fallback_dcid.seq >= conn->dcid.retire_prior_to) {
7293       ++extra_dcid;
7294     }
7295   }
7296 
7297   if (conn->local.transport_params.active_connection_id_limit <=
7298       len + extra_dcid) {
7299     return NGTCP2_ERR_CONNECTION_ID_LIMIT;
7300   }
7301 
7302   if (len >= NGTCP2_MAX_DCID_POOL_SIZE) {
7303     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "too many connection ID");
7304     return 0;
7305   }
7306 
7307   dcid = ngtcp2_ringbuf_push_back(&conn->dcid.unused);
7308   ngtcp2_dcid_init(dcid, fr->seq, &fr->cid, fr->stateless_reset_token);
7309 
7310   return 0;
7311 }
7312 
7313 /*
7314  * conn_post_process_recv_new_connection_id handles retirement request
7315  * of active DCIDs.
7316  *
7317  * This function returns 0 if it succeeds, or one of the following
7318  * negative error codes:
7319  *
7320  * NGTCP2_ERR_NOMEM
7321  *     Out of memory.
7322  * NGTCP2_ERR_CALLBACK_FAILURE
7323  *     User-defined callback function failed.
7324  */
conn_post_process_recv_new_connection_id(ngtcp2_conn * conn,ngtcp2_tstamp ts)7325 static int conn_post_process_recv_new_connection_id(ngtcp2_conn *conn,
7326                                                     ngtcp2_tstamp ts) {
7327   ngtcp2_pv *pv = conn->pv;
7328   ngtcp2_dcid *dcid;
7329   int rv;
7330 
7331   if (conn->dcid.current.seq < conn->dcid.retire_prior_to) {
7332     if (ngtcp2_ringbuf_len(&conn->dcid.unused) == 0) {
7333       return 0;
7334     }
7335 
7336     rv = conn_retire_dcid(conn, &conn->dcid.current, ts);
7337     if (rv != 0) {
7338       return rv;
7339     }
7340 
7341     dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
7342     if (pv) {
7343       if (conn->dcid.current.seq == pv->dcid.seq) {
7344         ngtcp2_dcid_copy_cid_token(&pv->dcid, dcid);
7345       }
7346       if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7347           conn->dcid.current.seq == pv->fallback_dcid.seq) {
7348         ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, dcid);
7349       }
7350     }
7351 
7352     ngtcp2_dcid_copy_cid_token(&conn->dcid.current, dcid);
7353     ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
7354 
7355     rv = conn_call_activate_dcid(conn, &conn->dcid.current);
7356     if (rv != 0) {
7357       return rv;
7358     }
7359   }
7360 
7361   if (pv) {
7362     if (pv->dcid.seq < conn->dcid.retire_prior_to) {
7363       if (ngtcp2_ringbuf_len(&conn->dcid.unused)) {
7364         rv = conn_retire_dcid(conn, &pv->dcid, ts);
7365         if (rv != 0) {
7366           return rv;
7367         }
7368 
7369         dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
7370 
7371         if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7372             pv->dcid.seq == pv->fallback_dcid.seq) {
7373           ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, dcid);
7374         }
7375 
7376         ngtcp2_dcid_copy_cid_token(&pv->dcid, dcid);
7377         ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
7378 
7379         rv = conn_call_activate_dcid(conn, &pv->dcid);
7380         if (rv != 0) {
7381           return rv;
7382         }
7383       } else {
7384         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
7385                         "path migration is aborted because connection ID is"
7386                         "retired and no unused connection ID is available");
7387 
7388         return conn_abort_pv(conn, ts);
7389       }
7390     }
7391     if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7392         pv->fallback_dcid.seq < conn->dcid.retire_prior_to) {
7393       if (ngtcp2_ringbuf_len(&conn->dcid.unused)) {
7394         rv = conn_retire_dcid(conn, &pv->fallback_dcid, ts);
7395         if (rv != 0) {
7396           return rv;
7397         }
7398 
7399         dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
7400         ngtcp2_dcid_copy_cid_token(&pv->fallback_dcid, dcid);
7401         ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
7402 
7403         rv = conn_call_activate_dcid(conn, &pv->fallback_dcid);
7404         if (rv != 0) {
7405           return rv;
7406         }
7407       } else {
7408         /* Now we have no fallback dcid. */
7409         return conn_abort_pv(conn, ts);
7410       }
7411     }
7412   }
7413 
7414   return 0;
7415 }
7416 
7417 /*
7418  * conn_recv_retire_connection_id processes the incoming
7419  * RETIRE_CONNECTION_ID frame |fr|.  |hd| is a packet header which
7420  * |fr| is included.
7421  *
7422  * This function returns 0 if it succeeds, or one of the following
7423  * negative error codes:
7424  *
7425  * NGTCP2_ERR_NOMEM
7426  *     Out of memory.
7427  * NGTCP2_ERR_PROTO
7428  *     SCID is zero-length.
7429  * NGTCP2_ERR_FRAME_ENCODING
7430  *     Attempt to retire CID which is used as DCID to send this frame.
7431  */
conn_recv_retire_connection_id(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd,const ngtcp2_retire_connection_id * fr,ngtcp2_tstamp ts)7432 static int conn_recv_retire_connection_id(ngtcp2_conn *conn,
7433                                           const ngtcp2_pkt_hd *hd,
7434                                           const ngtcp2_retire_connection_id *fr,
7435                                           ngtcp2_tstamp ts) {
7436   ngtcp2_ksl_it it;
7437   ngtcp2_scid *scid;
7438 
7439   if (conn->oscid.datalen == 0 || conn->scid.last_seq < fr->seq) {
7440     return NGTCP2_ERR_PROTO;
7441   }
7442 
7443   for (it = ngtcp2_ksl_begin(&conn->scid.set); !ngtcp2_ksl_it_end(&it);
7444        ngtcp2_ksl_it_next(&it)) {
7445     scid = ngtcp2_ksl_it_get(&it);
7446     if (scid->seq == fr->seq) {
7447       if (ngtcp2_cid_eq(&scid->cid, &hd->dcid)) {
7448         return NGTCP2_ERR_PROTO;
7449       }
7450 
7451       if (!(scid->flags & NGTCP2_SCID_FLAG_RETIRED)) {
7452         scid->flags |= NGTCP2_SCID_FLAG_RETIRED;
7453         ++conn->scid.num_retired;
7454       }
7455 
7456       if (scid->pe.index != NGTCP2_PQ_BAD_INDEX) {
7457         ngtcp2_pq_remove(&conn->scid.used, &scid->pe);
7458         scid->pe.index = NGTCP2_PQ_BAD_INDEX;
7459       }
7460 
7461       scid->retired_ts = ts;
7462 
7463       return ngtcp2_pq_push(&conn->scid.used, &scid->pe);
7464     }
7465   }
7466 
7467   return 0;
7468 }
7469 
7470 /*
7471  * conn_recv_new_token processes the incoming NEW_TOKEN frame |fr|.
7472  *
7473  * This function returns 0 if it succeeds, or one of the following
7474  * negative error codes:
7475  *
7476  * NGTCP2_ERR_FRAME_ENCODING
7477  *     Token is empty
7478  * NGTCP2_ERR_PROTO:
7479  *     Server received NEW_TOKEN.
7480  */
conn_recv_new_token(ngtcp2_conn * conn,const ngtcp2_new_token * fr)7481 static int conn_recv_new_token(ngtcp2_conn *conn, const ngtcp2_new_token *fr) {
7482   if (conn->server) {
7483     return NGTCP2_ERR_PROTO;
7484   }
7485 
7486   if (fr->token.len == 0) {
7487     return NGTCP2_ERR_FRAME_ENCODING;
7488   }
7489 
7490   return conn_call_recv_new_token(conn, &fr->token);
7491 }
7492 
7493 /*
7494  * conn_recv_streams_blocked_bidi processes the incoming
7495  * STREAMS_BLOCKED (0x16).
7496  *
7497  * This function returns 0 if it succeeds, or one of the following
7498  * negative error codes:
7499  *
7500  * NGTCP2_ERR_FRAME_ENCODING
7501  *     Maximum Streams is larger than advertised value.
7502  */
conn_recv_streams_blocked_bidi(ngtcp2_conn * conn,ngtcp2_streams_blocked * fr)7503 static int conn_recv_streams_blocked_bidi(ngtcp2_conn *conn,
7504                                           ngtcp2_streams_blocked *fr) {
7505   if (fr->max_streams > conn->remote.bidi.max_streams) {
7506     return NGTCP2_ERR_FRAME_ENCODING;
7507   }
7508 
7509   return 0;
7510 }
7511 
7512 /*
7513  * conn_recv_streams_blocked_uni processes the incoming
7514  * STREAMS_BLOCKED (0x17).
7515  *
7516  * This function returns 0 if it succeeds, or one of the following
7517  * negative error codes:
7518  *
7519  * NGTCP2_ERR_FRAME_ENCODING
7520  *     Maximum Streams is larger than advertised value.
7521  */
conn_recv_streams_blocked_uni(ngtcp2_conn * conn,ngtcp2_streams_blocked * fr)7522 static int conn_recv_streams_blocked_uni(ngtcp2_conn *conn,
7523                                          ngtcp2_streams_blocked *fr) {
7524   if (fr->max_streams > conn->remote.uni.max_streams) {
7525     return NGTCP2_ERR_FRAME_ENCODING;
7526   }
7527 
7528   return 0;
7529 }
7530 
7531 /*
7532  * conn_select_preferred_addr asks a client application to select a
7533  * server address from preferred addresses received from server.  If a
7534  * client chooses the address, path validation will start.
7535  *
7536  * This function returns 0 if it succeeds, or one of the following
7537  * negative error codes:
7538  *
7539  * NGTCP2_ERR_NOMEM
7540  *     Out of memory.
7541  * NGTCP2_ERR_CALLBACK_FAILURE
7542  *     User-defined callback function failed.
7543  */
conn_select_preferred_addr(ngtcp2_conn * conn)7544 static int conn_select_preferred_addr(ngtcp2_conn *conn) {
7545   ngtcp2_path_storage ps;
7546   int rv;
7547   ngtcp2_duration pto, initial_pto, timeout;
7548   ngtcp2_pv *pv;
7549   ngtcp2_dcid *dcid;
7550 
7551   if (ngtcp2_ringbuf_len(&conn->dcid.unused) == 0) {
7552     return 0;
7553   }
7554 
7555   ngtcp2_path_storage_zero(&ps);
7556   ngtcp2_addr_copy(&ps.path.local, &conn->dcid.current.ps.path.local);
7557 
7558   rv = conn_call_select_preferred_addr(conn, &ps.path);
7559   if (rv != 0) {
7560     return rv;
7561   }
7562 
7563   if (ps.path.remote.addrlen == 0 ||
7564       ngtcp2_addr_eq(&conn->dcid.current.ps.path.remote, &ps.path.remote)) {
7565     return 0;
7566   }
7567 
7568   assert(conn->pv == NULL);
7569 
7570   dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
7571   ngtcp2_dcid_set_path(dcid, &ps.path);
7572 
7573   pto = conn_compute_pto(conn, &conn->pktns);
7574   initial_pto = conn_compute_initial_pto(conn, &conn->pktns);
7575   timeout = 3 * ngtcp2_max(pto, initial_pto);
7576 
7577   rv = ngtcp2_pv_new(&pv, dcid, timeout, NGTCP2_PV_FLAG_PREFERRED_ADDR,
7578                      &conn->log, conn->mem);
7579   if (rv != 0) {
7580     /* TODO Call ngtcp2_dcid_free here if it is introduced */
7581     return rv;
7582   }
7583 
7584   ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
7585   conn->pv = pv;
7586 
7587   return conn_call_activate_dcid(conn, &pv->dcid);
7588 }
7589 
7590 /*
7591  * conn_recv_handshake_done processes the incoming HANDSHAKE_DONE
7592  * frame |fr|.
7593  *
7594  * This function returns 0 if it succeeds, or one of the following
7595  * negative error codes:
7596  *
7597  * NGTCP2_ERR_PROTO
7598  *     Server received HANDSHAKE_DONE frame.
7599  * NGTCP2_ERR_NOMEM
7600  *     Out of memory.
7601  * NGTCP2_ERR_CALLBACK_FAILURE
7602  *     User-defined callback function failed.
7603  */
conn_recv_handshake_done(ngtcp2_conn * conn,ngtcp2_tstamp ts)7604 static int conn_recv_handshake_done(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
7605   int rv;
7606 
7607   if (conn->server) {
7608     return NGTCP2_ERR_PROTO;
7609   }
7610 
7611   if (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) {
7612     return 0;
7613   }
7614 
7615   conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED |
7616                  NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
7617 
7618   conn->pktns.rtb.persistent_congestion_start_ts = ts;
7619 
7620   conn_discard_handshake_state(conn, ts);
7621 
7622   if (conn->remote.transport_params.preferred_address_present) {
7623     rv = conn_select_preferred_addr(conn);
7624     if (rv != 0) {
7625       return rv;
7626     }
7627   }
7628 
7629   rv = conn_call_handshake_confirmed(conn);
7630   if (rv != 0) {
7631     return rv;
7632   }
7633 
7634   /* Re-arm loss detection timer after handshake has been
7635      confirmed. */
7636   ngtcp2_conn_set_loss_detection_timer(conn, ts);
7637 
7638   return 0;
7639 }
7640 
7641 /*
7642  * conn_recv_datagram processes the incoming DATAGRAM frame |fr|.
7643  *
7644  * This function returns 0 if it succeeds, or one of the following
7645  * negative error codes:
7646  *
7647  * NGTCP2_ERR_CALLBACK_FAILURE
7648  *     User-defined callback function failed.
7649  */
conn_recv_datagram(ngtcp2_conn * conn,ngtcp2_datagram * fr)7650 static int conn_recv_datagram(ngtcp2_conn *conn, ngtcp2_datagram *fr) {
7651   assert(conn->local.transport_params.max_datagram_frame_size);
7652 
7653   return conn_call_recv_datagram(conn, fr);
7654 }
7655 
7656 /*
7657  * conn_key_phase_changed returns nonzero if |hd| indicates that the
7658  * key phase has unexpected value.
7659  */
conn_key_phase_changed(ngtcp2_conn * conn,const ngtcp2_pkt_hd * hd)7660 static int conn_key_phase_changed(ngtcp2_conn *conn, const ngtcp2_pkt_hd *hd) {
7661   ngtcp2_pktns *pktns = &conn->pktns;
7662 
7663   return !(pktns->crypto.rx.ckm->flags & NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE) ^
7664          !(hd->flags & NGTCP2_PKT_FLAG_KEY_PHASE);
7665 }
7666 
7667 /*
7668  * conn_prepare_key_update installs new updated keys.
7669  */
conn_prepare_key_update(ngtcp2_conn * conn,ngtcp2_tstamp ts)7670 static int conn_prepare_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
7671   int rv;
7672   ngtcp2_tstamp confirmed_ts = conn->crypto.key_update.confirmed_ts;
7673   ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
7674   ngtcp2_pktns *pktns = &conn->pktns;
7675   ngtcp2_crypto_km *rx_ckm = pktns->crypto.rx.ckm;
7676   ngtcp2_crypto_km *tx_ckm = pktns->crypto.tx.ckm;
7677   ngtcp2_crypto_km *new_rx_ckm, *new_tx_ckm;
7678   ngtcp2_crypto_aead_ctx rx_aead_ctx = {0}, tx_aead_ctx = {0};
7679   size_t secretlen, ivlen;
7680 
7681   if ((conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) &&
7682       tx_ckm->use_count >= pktns->crypto.ctx.max_encryption &&
7683       ngtcp2_conn_initiate_key_update(conn, ts) != 0) {
7684     return NGTCP2_ERR_AEAD_LIMIT_REACHED;
7685   }
7686 
7687   if ((conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED) ||
7688       (confirmed_ts != UINT64_MAX && confirmed_ts + pto > ts)) {
7689     return 0;
7690   }
7691 
7692   if (conn->crypto.key_update.new_rx_ckm ||
7693       conn->crypto.key_update.new_tx_ckm) {
7694     assert(conn->crypto.key_update.new_rx_ckm);
7695     assert(conn->crypto.key_update.new_tx_ckm);
7696     return 0;
7697   }
7698 
7699   secretlen = rx_ckm->secret.len;
7700   ivlen = rx_ckm->iv.len;
7701 
7702   rv = ngtcp2_crypto_km_nocopy_new(&conn->crypto.key_update.new_rx_ckm,
7703                                    secretlen, ivlen, conn->mem);
7704   if (rv != 0) {
7705     return rv;
7706   }
7707 
7708   rv = ngtcp2_crypto_km_nocopy_new(&conn->crypto.key_update.new_tx_ckm,
7709                                    secretlen, ivlen, conn->mem);
7710   if (rv != 0) {
7711     return rv;
7712   }
7713 
7714   new_rx_ckm = conn->crypto.key_update.new_rx_ckm;
7715   new_tx_ckm = conn->crypto.key_update.new_tx_ckm;
7716 
7717   rv = conn_call_update_key(
7718       conn, new_rx_ckm->secret.base, new_tx_ckm->secret.base, &rx_aead_ctx,
7719       new_rx_ckm->iv.base, &tx_aead_ctx, new_tx_ckm->iv.base,
7720       rx_ckm->secret.base, tx_ckm->secret.base, secretlen);
7721   if (rv != 0) {
7722     return rv;
7723   }
7724 
7725   new_rx_ckm->aead_ctx = rx_aead_ctx;
7726   new_tx_ckm->aead_ctx = tx_aead_ctx;
7727 
7728   if (!(rx_ckm->flags & NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE)) {
7729     new_rx_ckm->flags |= NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE;
7730     new_tx_ckm->flags |= NGTCP2_CRYPTO_KM_FLAG_KEY_PHASE_ONE;
7731   }
7732 
7733   if (conn->crypto.key_update.old_rx_ckm) {
7734     conn_call_delete_crypto_aead_ctx(
7735         conn, &conn->crypto.key_update.old_rx_ckm->aead_ctx);
7736     ngtcp2_crypto_km_del(conn->crypto.key_update.old_rx_ckm, conn->mem);
7737     conn->crypto.key_update.old_rx_ckm = NULL;
7738   }
7739 
7740   return 0;
7741 }
7742 
7743 /*
7744  * conn_rotate_keys rotates keys.  The current key moves to old key,
7745  * and new key moves to the current key.
7746  */
conn_rotate_keys(ngtcp2_conn * conn,int64_t pkt_num)7747 static void conn_rotate_keys(ngtcp2_conn *conn, int64_t pkt_num) {
7748   ngtcp2_pktns *pktns = &conn->pktns;
7749 
7750   assert(conn->crypto.key_update.new_rx_ckm);
7751   assert(conn->crypto.key_update.new_tx_ckm);
7752   assert(!conn->crypto.key_update.old_rx_ckm);
7753   assert(!(conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING));
7754 
7755   conn->crypto.key_update.old_rx_ckm = pktns->crypto.rx.ckm;
7756 
7757   pktns->crypto.rx.ckm = conn->crypto.key_update.new_rx_ckm;
7758   conn->crypto.key_update.new_rx_ckm = NULL;
7759   pktns->crypto.rx.ckm->pkt_num = pkt_num;
7760 
7761   assert(pktns->crypto.tx.ckm);
7762 
7763   conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
7764   ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
7765 
7766   pktns->crypto.tx.ckm = conn->crypto.key_update.new_tx_ckm;
7767   conn->crypto.key_update.new_tx_ckm = NULL;
7768   pktns->crypto.tx.ckm->pkt_num = pktns->tx.last_pkt_num + 1;
7769 
7770   conn->flags |= NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED;
7771 }
7772 
7773 /*
7774  * conn_path_validation_in_progress returns nonzero if path validation
7775  * against |path| is underway.
7776  */
conn_path_validation_in_progress(ngtcp2_conn * conn,const ngtcp2_path * path)7777 static int conn_path_validation_in_progress(ngtcp2_conn *conn,
7778                                             const ngtcp2_path *path) {
7779   ngtcp2_pv *pv = conn->pv;
7780 
7781   return pv && ngtcp2_path_eq(&pv->dcid.ps.path, path);
7782 }
7783 
7784 /*
7785  * conn_recv_non_probing_pkt_on_new_path is called when non-probing
7786  * packet is received via new path.  It starts path validation against
7787  * the new path.
7788  *
7789  * This function returns 0 if it succeeds, or one of the following
7790  * negative error codes:
7791  *
7792  * NGTCP2_ERR_CONN_ID_BLOCKED
7793  *     No DCID is available
7794  * NGTCP2_ERR_NOMEM
7795  *     Out of memory
7796  */
conn_recv_non_probing_pkt_on_new_path(ngtcp2_conn * conn,const ngtcp2_path * path,size_t dgramlen,int new_cid_used,ngtcp2_tstamp ts)7797 static int conn_recv_non_probing_pkt_on_new_path(ngtcp2_conn *conn,
7798                                                  const ngtcp2_path *path,
7799                                                  size_t dgramlen,
7800                                                  int new_cid_used,
7801                                                  ngtcp2_tstamp ts) {
7802 
7803   ngtcp2_dcid dcid, *bound_dcid, *last;
7804   ngtcp2_pv *pv;
7805   int rv;
7806   ngtcp2_duration pto, initial_pto, timeout;
7807   int require_new_cid;
7808   int local_addr_eq;
7809   uint32_t remote_addr_cmp;
7810   size_t len, i;
7811 
7812   assert(conn->server);
7813 
7814   if (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7815       ngtcp2_path_eq(&conn->pv->fallback_dcid.ps.path, path)) {
7816     /* If new path equals fallback path, that means connection
7817        migrated back to the original path.  Fallback path is
7818        considered to be validated. */
7819     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PTV,
7820                     "path is migrated back to the original path");
7821     ngtcp2_dcid_copy(&conn->dcid.current, &conn->pv->fallback_dcid);
7822     conn_reset_congestion_state(conn, ts);
7823     conn->dcid.current.bytes_recv += dgramlen;
7824     conn_reset_ecn_validation_state(conn);
7825     return conn_abort_pv(conn, ts);
7826   }
7827 
7828   remote_addr_cmp =
7829       ngtcp2_addr_compare(&conn->dcid.current.ps.path.remote, &path->remote);
7830   local_addr_eq =
7831       ngtcp2_addr_eq(&conn->dcid.current.ps.path.local, &path->local);
7832 
7833   /* The transport specification draft-27 says:
7834    *
7835    * An endpoint MUST use a new connection ID if it initiates
7836    * connection migration as described in Section 9.2 or probes a new
7837    * network path as described in Section 9.1. An endpoint MUST use a
7838    * new connection ID in response to a change in the address of a
7839    * peer if the packet with the new peer address uses an active
7840    * connection ID that has not been previously used by the peer.
7841    */
7842   require_new_cid = conn->dcid.current.cid.datalen &&
7843                     ((new_cid_used && remote_addr_cmp) || !local_addr_eq);
7844 
7845   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
7846                   "non-probing packet was received from new remote address");
7847 
7848   pto = conn_compute_pto(conn, &conn->pktns);
7849   initial_pto = conn_compute_initial_pto(conn, &conn->pktns);
7850   timeout = 3 * ngtcp2_max(pto, initial_pto);
7851 
7852   len = ngtcp2_ringbuf_len(&conn->dcid.bound);
7853 
7854   for (i = 0; i < len; ++i) {
7855     bound_dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
7856     if (ngtcp2_path_eq(&bound_dcid->ps.path, path)) {
7857       ngtcp2_log_info(
7858           &conn->log, NGTCP2_LOG_EVENT_CON,
7859           "Found DCID which has already been bound to the new path");
7860 
7861       ngtcp2_dcid_copy(&dcid, bound_dcid);
7862       if (i == 0) {
7863         ngtcp2_ringbuf_pop_front(&conn->dcid.bound);
7864       } else if (i == ngtcp2_ringbuf_len(&conn->dcid.bound) - 1) {
7865         ngtcp2_ringbuf_pop_back(&conn->dcid.bound);
7866       } else {
7867         last = ngtcp2_ringbuf_get(&conn->dcid.bound, len - 1);
7868         ngtcp2_dcid_copy(bound_dcid, last);
7869         ngtcp2_ringbuf_pop_back(&conn->dcid.bound);
7870       }
7871       require_new_cid = 0;
7872 
7873       if (dcid.cid.datalen) {
7874         rv = conn_call_activate_dcid(conn, &dcid);
7875         if (rv != 0) {
7876           return rv;
7877         }
7878       }
7879       break;
7880     }
7881   }
7882 
7883   if (i == len) {
7884     if (require_new_cid) {
7885       if (ngtcp2_ringbuf_len(&conn->dcid.unused) == 0) {
7886         return NGTCP2_ERR_CONN_ID_BLOCKED;
7887       }
7888       ngtcp2_dcid_copy(&dcid, ngtcp2_ringbuf_get(&conn->dcid.unused, 0));
7889       ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
7890 
7891       rv = conn_call_activate_dcid(conn, &dcid);
7892       if (rv != 0) {
7893         return rv;
7894       }
7895     } else {
7896       /* Use the current DCID if a remote endpoint does not change
7897          DCID. */
7898       ngtcp2_dcid_copy(&dcid, &conn->dcid.current);
7899       dcid.bytes_sent = 0;
7900       dcid.bytes_recv = 0;
7901       dcid.flags &= (uint8_t)~NGTCP2_DCID_FLAG_PATH_VALIDATED;
7902     }
7903   }
7904 
7905   ngtcp2_dcid_set_path(&dcid, path);
7906   dcid.bytes_recv += dgramlen;
7907 
7908   rv = ngtcp2_pv_new(&pv, &dcid, timeout, NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE,
7909                      &conn->log, conn->mem);
7910   if (rv != 0) {
7911     return rv;
7912   }
7913 
7914   if (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE)) {
7915     ngtcp2_dcid_copy(&pv->fallback_dcid, &conn->pv->fallback_dcid);
7916     pv->fallback_pto = conn->pv->fallback_pto;
7917     /* Unset the flag bit so that conn_stop_pv does not retire
7918        DCID. */
7919     conn->pv->flags &= (uint8_t)~NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE;
7920   } else {
7921     ngtcp2_dcid_copy(&pv->fallback_dcid, &conn->dcid.current);
7922     pv->fallback_pto = pto;
7923   }
7924 
7925   if (!local_addr_eq || (remote_addr_cmp & (NGTCP2_ADDR_COMPARE_FLAG_ADDR |
7926                                             NGTCP2_ADDR_COMPARE_FLAG_FAMILY))) {
7927     conn_reset_congestion_state(conn, ts);
7928   } else {
7929     /* For NAT rebinding, keep max_udp_payload_size since client most
7930        likely does not send a padded PATH_CHALLENGE. */
7931     dcid.max_udp_payload_size = ngtcp2_max(
7932         dcid.max_udp_payload_size, conn->dcid.current.max_udp_payload_size);
7933   }
7934 
7935   ngtcp2_dcid_copy(&conn->dcid.current, &dcid);
7936 
7937   conn_reset_ecn_validation_state(conn);
7938 
7939   if (conn->pv) {
7940     ngtcp2_log_info(
7941         &conn->log, NGTCP2_LOG_EVENT_PTV,
7942         "path migration is aborted because new migration has started");
7943     rv = conn_abort_pv(conn, ts);
7944     if (rv != 0) {
7945       return rv;
7946     }
7947   }
7948 
7949   conn->pv = pv;
7950 
7951   return 0;
7952 }
7953 
7954 /*
7955  * conn_recv_pkt_from_new_path is called when a Short packet is
7956  * received from new path (not current path).  This packet would be a
7957  * packet which only contains probing frame, or reordered packet, or a
7958  * path is being validated.
7959  *
7960  * This function returns 0 if it succeeds, or one of the following
7961  * negative error codes:
7962  *
7963  * NGTCP2_ERR_CONN_ID_BLOCKED
7964  *     No unused DCID is available
7965  * NGTCP2_ERR_NOMEM
7966  *     Out of memory
7967  */
conn_recv_pkt_from_new_path(ngtcp2_conn * conn,const ngtcp2_path * path,size_t dgramlen,int path_challenge_recved,ngtcp2_tstamp ts)7968 static int conn_recv_pkt_from_new_path(ngtcp2_conn *conn,
7969                                        const ngtcp2_path *path, size_t dgramlen,
7970                                        int path_challenge_recved,
7971                                        ngtcp2_tstamp ts) {
7972   ngtcp2_pv *pv = conn->pv;
7973   ngtcp2_dcid *bound_dcid;
7974   int rv;
7975 
7976   if (pv) {
7977     if (ngtcp2_path_eq(&pv->dcid.ps.path, path)) {
7978       pv->dcid.bytes_recv += dgramlen;
7979       return 0;
7980     }
7981 
7982     if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
7983         ngtcp2_path_eq(&pv->fallback_dcid.ps.path, path)) {
7984       pv->fallback_dcid.bytes_recv += dgramlen;
7985       return 0;
7986     }
7987   }
7988 
7989   if (!path_challenge_recved) {
7990     return 0;
7991   }
7992 
7993   rv = conn_bind_dcid(conn, &bound_dcid, path, ts);
7994   if (rv != 0) {
7995     return rv;
7996   }
7997 
7998   ngtcp2_dcid_set_path(bound_dcid, path);
7999   bound_dcid->bytes_recv += dgramlen;
8000   conn_update_dcid_max_udp_payload_size(conn, bound_dcid, dgramlen);
8001 
8002   return 0;
8003 }
8004 
8005 /*
8006  * conn_recv_delayed_handshake_pkt processes the received Handshake
8007  * packet which is received after handshake completed.  This function
8008  * does the minimal job, and its purpose is send acknowledgement of
8009  * this packet to the peer.  We assume that hd->type ==
8010  * NGTCP2_PKT_HANDSHAKE.
8011  *
8012  * This function returns 0 if it succeeds, or one of the following
8013  * negative error codes:
8014  *
8015  * NGTCP2_ERR_FRAME_ENCODING
8016  *     Frame is badly formatted; or frame type is unknown.
8017  * NGTCP2_ERR_NOMEM
8018  *     Out of memory
8019  * NGTCP2_ERR_DISCARD_PKT
8020  *     Packet was discarded.
8021  * NGTCP2_ERR_ACK_FRAME
8022  *     ACK frame is malformed.
8023  * NGTCP2_ERR_PROTO
8024  *     Frame that is not allowed in Handshake packet is received.
8025  */
8026 static int
conn_recv_delayed_handshake_pkt(ngtcp2_conn * conn,const ngtcp2_pkt_info * pi,const ngtcp2_pkt_hd * hd,size_t pktlen,const uint8_t * payload,size_t payloadlen,ngtcp2_tstamp pkt_ts,ngtcp2_tstamp ts)8027 conn_recv_delayed_handshake_pkt(ngtcp2_conn *conn, const ngtcp2_pkt_info *pi,
8028                                 const ngtcp2_pkt_hd *hd, size_t pktlen,
8029                                 const uint8_t *payload, size_t payloadlen,
8030                                 ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
8031   ngtcp2_ssize nread;
8032   ngtcp2_max_frame mfr;
8033   ngtcp2_frame *fr = &mfr.fr;
8034   int rv;
8035   int require_ack = 0;
8036   ngtcp2_pktns *pktns;
8037 
8038   assert(hd->type == NGTCP2_PKT_HANDSHAKE);
8039 
8040   pktns = conn->hs_pktns;
8041 
8042   if (payloadlen == 0) {
8043     /* QUIC packet must contain at least one frame */
8044     return NGTCP2_ERR_PROTO;
8045   }
8046 
8047   ngtcp2_qlog_pkt_received_start(&conn->qlog);
8048 
8049   for (; payloadlen;) {
8050     nread = ngtcp2_pkt_decode_frame(fr, payload, payloadlen);
8051     if (nread < 0) {
8052       return (int)nread;
8053     }
8054 
8055     payload += nread;
8056     payloadlen -= (size_t)nread;
8057 
8058     switch (fr->type) {
8059     case NGTCP2_FRAME_ACK:
8060     case NGTCP2_FRAME_ACK_ECN:
8061       fr->ack.ack_delay = 0;
8062       fr->ack.ack_delay_unscaled = 0;
8063       break;
8064     }
8065 
8066     ngtcp2_log_rx_fr(&conn->log, hd, fr);
8067 
8068     switch (fr->type) {
8069     case NGTCP2_FRAME_ACK:
8070     case NGTCP2_FRAME_ACK_ECN:
8071       if (!conn->server) {
8072         conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
8073       }
8074       rv = conn_recv_ack(conn, pktns, &fr->ack, pkt_ts, ts);
8075       if (rv != 0) {
8076         return rv;
8077       }
8078       break;
8079     case NGTCP2_FRAME_PADDING:
8080       break;
8081     case NGTCP2_FRAME_CONNECTION_CLOSE:
8082       conn_recv_connection_close(conn, &fr->connection_close);
8083       break;
8084     case NGTCP2_FRAME_CRYPTO:
8085     case NGTCP2_FRAME_PING:
8086       require_ack = 1;
8087       break;
8088     default:
8089       return NGTCP2_ERR_PROTO;
8090     }
8091 
8092     ngtcp2_qlog_write_frame(&conn->qlog, fr);
8093   }
8094 
8095   ngtcp2_qlog_pkt_received_end(&conn->qlog, hd, pktlen);
8096 
8097   rv = pktns_commit_recv_pkt_num(pktns, hd->pkt_num, require_ack, pkt_ts);
8098   if (rv != 0) {
8099     return rv;
8100   }
8101 
8102   pktns_increase_ecn_counts(pktns, pi);
8103 
8104   if (require_ack &&
8105       (++pktns->acktr.rx_npkt >= conn->local.settings.ack_thresh ||
8106        (pi->ecn & NGTCP2_ECN_MASK) == NGTCP2_ECN_CE)) {
8107     ngtcp2_acktr_immediate_ack(&pktns->acktr);
8108   }
8109 
8110   rv = ngtcp2_conn_sched_ack(conn, &pktns->acktr, hd->pkt_num, require_ack,
8111                              pkt_ts);
8112   if (rv != 0) {
8113     return rv;
8114   }
8115 
8116   conn_restart_timer_on_read(conn, ts);
8117 
8118   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
8119 
8120   return 0;
8121 }
8122 
8123 /*
8124  * conn_recv_pkt processes a packet contained in the buffer pointed by
8125  * |pkt| of length |pktlen|.  |pkt| may contain multiple QUIC packets.
8126  * This function only processes the first packet.  |pkt_ts| is the
8127  * timestamp when packet is received.  |ts| should be the current
8128  * time.  Usually they are the same, but for buffered packets,
8129  * |pkt_ts| would be earlier than |ts|.
8130  *
8131  * This function returns the number of bytes processed if it succeeds,
8132  * or one of the following negative error codes:
8133  *
8134  * NGTCP2_ERR_DISCARD_PKT
8135  *     Packet was discarded because plain text header was malformed;
8136  *     or its payload could not be decrypted.
8137  * NGTCP2_ERR_PROTO
8138  *     Packet is badly formatted; or 0RTT packet contains other than
8139  *     PADDING or STREAM frames; or other QUIC protocol violation is
8140  *     found.
8141  * NGTCP2_ERR_CALLBACK_FAILURE
8142  *     User-defined callback function failed.
8143  * NGTCP2_ERR_NOMEM
8144  *     Out of memory.
8145  * NGTCP2_ERR_FRAME_ENCODING
8146  *     Frame is badly formatted; or frame type is unknown.
8147  * NGTCP2_ERR_ACK_FRAME
8148  *     ACK frame is malformed.
8149  * NGTCP2_ERR_STREAM_STATE
8150  *     Frame is received to the local stream which is not initiated.
8151  * NGTCP2_ERR_STREAM_LIMIT
8152  *     Frame has remote stream ID which is strictly greater than the
8153  *     allowed limit.
8154  * NGTCP2_ERR_FLOW_CONTROL
8155  *     Flow control limit is violated.
8156  * NGTCP2_ERR_FINAL_SIZE
8157  *     Frame has strictly larger end offset than it is permitted.
8158  */
conn_recv_pkt(ngtcp2_conn * conn,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,size_t dgramlen,ngtcp2_tstamp pkt_ts,ngtcp2_tstamp ts)8159 static ngtcp2_ssize conn_recv_pkt(ngtcp2_conn *conn, const ngtcp2_path *path,
8160                                   const ngtcp2_pkt_info *pi, const uint8_t *pkt,
8161                                   size_t pktlen, size_t dgramlen,
8162                                   ngtcp2_tstamp pkt_ts, ngtcp2_tstamp ts) {
8163   ngtcp2_pkt_hd hd;
8164   int rv = 0;
8165   size_t hdpktlen;
8166   const uint8_t *payload;
8167   size_t payloadlen;
8168   ngtcp2_ssize nread, nwrite;
8169   ngtcp2_max_frame mfr;
8170   ngtcp2_frame *fr = &mfr.fr;
8171   int require_ack = 0;
8172   ngtcp2_crypto_aead *aead;
8173   ngtcp2_crypto_cipher *hp;
8174   ngtcp2_crypto_km *ckm;
8175   ngtcp2_crypto_cipher_ctx *hp_ctx;
8176   ngtcp2_hp_mask hp_mask;
8177   ngtcp2_decrypt decrypt;
8178   ngtcp2_pktns *pktns;
8179   int non_probing_pkt = 0;
8180   int key_phase_bit_changed = 0;
8181   int force_decrypt_failure = 0;
8182   int recv_ncid = 0;
8183   int new_cid_used = 0;
8184   int path_challenge_recved = 0;
8185 
8186   if (pkt[0] & NGTCP2_HEADER_FORM_BIT) {
8187     nread = ngtcp2_pkt_decode_hd_long(&hd, pkt, pktlen);
8188     if (nread < 0) {
8189       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8190                       "could not decode long header");
8191       return NGTCP2_ERR_DISCARD_PKT;
8192     }
8193 
8194     if (pktlen < (size_t)nread + hd.len || conn->version != hd.version) {
8195       return NGTCP2_ERR_DISCARD_PKT;
8196     }
8197 
8198     pktlen = (size_t)nread + hd.len;
8199 
8200     /* Quoted from spec: if subsequent packets of those types include
8201        a different Source Connection ID, they MUST be discarded. */
8202     if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &hd.scid)) {
8203       ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
8204       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8205                       "packet was ignored because of mismatched SCID");
8206       return NGTCP2_ERR_DISCARD_PKT;
8207     }
8208 
8209     switch (hd.type) {
8210     case NGTCP2_PKT_INITIAL:
8211       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8212                       "delayed Initial packet was discarded");
8213       return (ngtcp2_ssize)pktlen;
8214     case NGTCP2_PKT_HANDSHAKE:
8215       if (!conn->hs_pktns) {
8216         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8217                         "delayed Handshake packet was discarded");
8218         return (ngtcp2_ssize)pktlen;
8219       }
8220 
8221       pktns = conn->hs_pktns;
8222       aead = &pktns->crypto.ctx.aead;
8223       hp = &pktns->crypto.ctx.hp;
8224       ckm = pktns->crypto.rx.ckm;
8225       hp_ctx = &pktns->crypto.rx.hp_ctx;
8226       hp_mask = conn->callbacks.hp_mask;
8227       decrypt = conn->callbacks.decrypt;
8228       break;
8229     case NGTCP2_PKT_0RTT:
8230       if (!conn->server) {
8231         return NGTCP2_ERR_DISCARD_PKT;
8232       }
8233 
8234       if (!conn->early.ckm) {
8235         return (ngtcp2_ssize)pktlen;
8236       }
8237 
8238       pktns = &conn->pktns;
8239       aead = &conn->early.ctx.aead;
8240       hp = &conn->early.ctx.hp;
8241       ckm = conn->early.ckm;
8242       hp_ctx = &conn->early.hp_ctx;
8243       hp_mask = conn->callbacks.hp_mask;
8244       decrypt = conn->callbacks.decrypt;
8245       break;
8246     default:
8247       ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
8248       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8249                       "packet type 0x%02x was ignored", hd.type);
8250       return (ngtcp2_ssize)pktlen;
8251     }
8252   } else {
8253     nread = ngtcp2_pkt_decode_hd_short(&hd, pkt, pktlen, conn->oscid.datalen);
8254     if (nread < 0) {
8255       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8256                       "could not decode short header");
8257       return NGTCP2_ERR_DISCARD_PKT;
8258     }
8259 
8260     pktns = &conn->pktns;
8261     aead = &pktns->crypto.ctx.aead;
8262     hp = &pktns->crypto.ctx.hp;
8263     ckm = pktns->crypto.rx.ckm;
8264     hp_ctx = &pktns->crypto.rx.hp_ctx;
8265     hp_mask = conn->callbacks.hp_mask;
8266     decrypt = conn->callbacks.decrypt;
8267   }
8268 
8269   rv = conn_ensure_decrypt_hp_buffer(conn, (size_t)nread + 4);
8270   if (rv != 0) {
8271     return rv;
8272   }
8273 
8274   nwrite = decrypt_hp(&hd, conn->crypto.decrypt_hp_buf.base, hp, pkt, pktlen,
8275                       (size_t)nread, ckm, hp_ctx, hp_mask);
8276   if (nwrite < 0) {
8277     if (ngtcp2_err_is_fatal((int)nwrite)) {
8278       return nwrite;
8279     }
8280     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8281                     "could not decrypt packet number");
8282     return NGTCP2_ERR_DISCARD_PKT;
8283   }
8284 
8285   hdpktlen = (size_t)nwrite;
8286   payload = pkt + hdpktlen;
8287   payloadlen = pktlen - hdpktlen;
8288 
8289   hd.pkt_num = ngtcp2_pkt_adjust_pkt_num(pktns->rx.max_pkt_num, hd.pkt_num,
8290                                          pkt_num_bits(hd.pkt_numlen));
8291   if (hd.pkt_num > NGTCP2_MAX_PKT_NUM) {
8292     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8293                     "pkn=%" PRId64 " is greater than maximum pkn", hd.pkt_num);
8294     return NGTCP2_ERR_DISCARD_PKT;
8295   }
8296 
8297   ngtcp2_log_rx_pkt_hd(&conn->log, &hd);
8298 
8299   if (hd.type == NGTCP2_PKT_SHORT) {
8300     key_phase_bit_changed = conn_key_phase_changed(conn, &hd);
8301   }
8302 
8303   rv = conn_ensure_decrypt_buffer(conn, payloadlen);
8304   if (rv != 0) {
8305     return rv;
8306   }
8307 
8308   if (key_phase_bit_changed) {
8309     assert(hd.type == NGTCP2_PKT_SHORT);
8310 
8311     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT, "unexpected KEY_PHASE");
8312 
8313     if (ckm->pkt_num > hd.pkt_num) {
8314       if (conn->crypto.key_update.old_rx_ckm) {
8315         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8316                         "decrypting with old key");
8317         ckm = conn->crypto.key_update.old_rx_ckm;
8318       } else {
8319         force_decrypt_failure = 1;
8320       }
8321     } else if (pktns->rx.max_pkt_num < hd.pkt_num) {
8322       assert(ckm->pkt_num < hd.pkt_num);
8323       if (!conn->crypto.key_update.new_rx_ckm) {
8324         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8325                         "new key is not available");
8326         force_decrypt_failure = 1;
8327       } else {
8328         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8329                         "decrypting with new key");
8330         ckm = conn->crypto.key_update.new_rx_ckm;
8331       }
8332     } else {
8333       force_decrypt_failure = 1;
8334     }
8335   }
8336 
8337   nwrite = decrypt_pkt(conn->crypto.decrypt_buf.base, aead, payload, payloadlen,
8338                        conn->crypto.decrypt_hp_buf.base, hdpktlen, hd.pkt_num,
8339                        ckm, decrypt);
8340 
8341   if (force_decrypt_failure) {
8342     nwrite = NGTCP2_ERR_DECRYPT;
8343   }
8344 
8345   if (nwrite < 0) {
8346     if (ngtcp2_err_is_fatal((int)nwrite)) {
8347       return nwrite;
8348     }
8349 
8350     assert(NGTCP2_ERR_DECRYPT == nwrite);
8351 
8352     if (hd.type == NGTCP2_PKT_SHORT &&
8353         ++conn->crypto.decryption_failure_count >=
8354             pktns->crypto.ctx.max_decryption_failure) {
8355       return NGTCP2_ERR_AEAD_LIMIT_REACHED;
8356     }
8357 
8358     if (hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) {
8359       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8360                       "could not decrypt packet payload");
8361       return NGTCP2_ERR_DISCARD_PKT;
8362     }
8363 
8364     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8365                     "could not decrypt packet payload");
8366     return NGTCP2_ERR_DISCARD_PKT;
8367   }
8368 
8369   rv = ngtcp2_pkt_verify_reserved_bits(conn->crypto.decrypt_hp_buf.base[0]);
8370   if (rv != 0) {
8371     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8372                     "packet has incorrect reserved bits");
8373 
8374     return NGTCP2_ERR_PROTO;
8375   }
8376 
8377   if (pktns_pkt_num_is_duplicate(pktns, hd.pkt_num)) {
8378     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8379                     "packet was discarded because of duplicated packet number");
8380     return NGTCP2_ERR_DISCARD_PKT;
8381   }
8382 
8383   payload = conn->crypto.decrypt_buf.base;
8384   payloadlen = (size_t)nwrite;
8385 
8386   if (payloadlen == 0) {
8387     /* QUIC packet must contain at least one frame */
8388     return NGTCP2_ERR_PROTO;
8389   }
8390 
8391   if (hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) {
8392     switch (hd.type) {
8393     case NGTCP2_PKT_HANDSHAKE:
8394       rv = conn_verify_dcid(conn, NULL, &hd);
8395       if (rv != 0) {
8396         if (ngtcp2_err_is_fatal(rv)) {
8397           return rv;
8398         }
8399         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8400                         "packet was ignored because of mismatched DCID");
8401         return NGTCP2_ERR_DISCARD_PKT;
8402       }
8403 
8404       rv = conn_recv_delayed_handshake_pkt(conn, pi, &hd, pktlen, payload,
8405                                            payloadlen, pkt_ts, ts);
8406       if (rv < 0) {
8407         return (ngtcp2_ssize)rv;
8408       }
8409 
8410       return (ngtcp2_ssize)pktlen;
8411     case NGTCP2_PKT_0RTT:
8412       if (!ngtcp2_cid_eq(&conn->rcid, &hd.dcid)) {
8413         rv = conn_verify_dcid(conn, NULL, &hd);
8414         if (rv != 0) {
8415           if (ngtcp2_err_is_fatal(rv)) {
8416             return rv;
8417           }
8418           ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8419                           "packet was ignored because of mismatched DCID");
8420           return NGTCP2_ERR_DISCARD_PKT;
8421         }
8422       }
8423       break;
8424     default:
8425       /* Unreachable */
8426       assert(0);
8427     }
8428   } else {
8429     rv = conn_verify_dcid(conn, &new_cid_used, &hd);
8430     if (rv != 0) {
8431       if (ngtcp2_err_is_fatal(rv)) {
8432         return rv;
8433       }
8434       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8435                       "packet was ignored because of mismatched DCID");
8436       return NGTCP2_ERR_DISCARD_PKT;
8437     }
8438   }
8439 
8440   ngtcp2_qlog_pkt_received_start(&conn->qlog);
8441 
8442   for (; payloadlen;) {
8443     nread = ngtcp2_pkt_decode_frame(fr, payload, payloadlen);
8444     if (nread < 0) {
8445       return nread;
8446     }
8447 
8448     payload += nread;
8449     payloadlen -= (size_t)nread;
8450 
8451     switch (fr->type) {
8452     case NGTCP2_FRAME_ACK:
8453     case NGTCP2_FRAME_ACK_ECN:
8454       if ((hd.flags & NGTCP2_PKT_FLAG_LONG_FORM) &&
8455           hd.type == NGTCP2_PKT_0RTT) {
8456         return NGTCP2_ERR_PROTO;
8457       }
8458       assign_recved_ack_delay_unscaled(
8459           &fr->ack, conn->remote.transport_params.ack_delay_exponent);
8460       break;
8461     }
8462 
8463     ngtcp2_log_rx_fr(&conn->log, &hd, fr);
8464 
8465     if (hd.type == NGTCP2_PKT_0RTT) {
8466       switch (fr->type) {
8467       case NGTCP2_FRAME_PADDING:
8468       case NGTCP2_FRAME_PING:
8469       case NGTCP2_FRAME_RESET_STREAM:
8470       case NGTCP2_FRAME_STOP_SENDING:
8471       case NGTCP2_FRAME_STREAM:
8472       case NGTCP2_FRAME_MAX_DATA:
8473       case NGTCP2_FRAME_MAX_STREAM_DATA:
8474       case NGTCP2_FRAME_MAX_STREAMS_BIDI:
8475       case NGTCP2_FRAME_MAX_STREAMS_UNI:
8476       case NGTCP2_FRAME_DATA_BLOCKED:
8477       case NGTCP2_FRAME_STREAM_DATA_BLOCKED:
8478       case NGTCP2_FRAME_STREAMS_BLOCKED_BIDI:
8479       case NGTCP2_FRAME_STREAMS_BLOCKED_UNI:
8480       case NGTCP2_FRAME_NEW_CONNECTION_ID:
8481       case NGTCP2_FRAME_PATH_CHALLENGE:
8482       case NGTCP2_FRAME_CONNECTION_CLOSE:
8483       case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
8484       case NGTCP2_FRAME_DATAGRAM:
8485       case NGTCP2_FRAME_DATAGRAM_LEN:
8486         break;
8487       default:
8488         return NGTCP2_ERR_PROTO;
8489       }
8490     }
8491 
8492     switch (fr->type) {
8493     case NGTCP2_FRAME_ACK:
8494     case NGTCP2_FRAME_ACK_ECN:
8495     case NGTCP2_FRAME_PADDING:
8496     case NGTCP2_FRAME_CONNECTION_CLOSE:
8497     case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
8498       break;
8499     default:
8500       require_ack = 1;
8501     }
8502 
8503     switch (fr->type) {
8504     case NGTCP2_FRAME_ACK:
8505     case NGTCP2_FRAME_ACK_ECN:
8506       if (!conn->server) {
8507         conn->flags |= NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED;
8508       }
8509       rv = conn_recv_ack(conn, pktns, &fr->ack, pkt_ts, ts);
8510       if (rv != 0) {
8511         return rv;
8512       }
8513       non_probing_pkt = 1;
8514       break;
8515     case NGTCP2_FRAME_STREAM:
8516       rv = conn_recv_stream(conn, &fr->stream);
8517       if (rv != 0) {
8518         return rv;
8519       }
8520       non_probing_pkt = 1;
8521       break;
8522     case NGTCP2_FRAME_CRYPTO:
8523       rv = conn_recv_crypto(conn, NGTCP2_CRYPTO_LEVEL_APPLICATION,
8524                             &pktns->crypto.strm, &fr->crypto);
8525       if (rv != 0) {
8526         return rv;
8527       }
8528       non_probing_pkt = 1;
8529       break;
8530     case NGTCP2_FRAME_RESET_STREAM:
8531       rv = conn_recv_reset_stream(conn, &fr->reset_stream);
8532       if (rv != 0) {
8533         return rv;
8534       }
8535       non_probing_pkt = 1;
8536       break;
8537     case NGTCP2_FRAME_STOP_SENDING:
8538       rv = conn_recv_stop_sending(conn, &fr->stop_sending);
8539       if (rv != 0) {
8540         return rv;
8541       }
8542       non_probing_pkt = 1;
8543       break;
8544     case NGTCP2_FRAME_MAX_STREAM_DATA:
8545       rv = conn_recv_max_stream_data(conn, &fr->max_stream_data);
8546       if (rv != 0) {
8547         return rv;
8548       }
8549       non_probing_pkt = 1;
8550       break;
8551     case NGTCP2_FRAME_MAX_DATA:
8552       conn_recv_max_data(conn, &fr->max_data);
8553       non_probing_pkt = 1;
8554       break;
8555     case NGTCP2_FRAME_MAX_STREAMS_BIDI:
8556     case NGTCP2_FRAME_MAX_STREAMS_UNI:
8557       rv = conn_recv_max_streams(conn, &fr->max_streams);
8558       if (rv != 0) {
8559         return rv;
8560       }
8561       non_probing_pkt = 1;
8562       break;
8563     case NGTCP2_FRAME_CONNECTION_CLOSE:
8564     case NGTCP2_FRAME_CONNECTION_CLOSE_APP:
8565       conn_recv_connection_close(conn, &fr->connection_close);
8566       break;
8567     case NGTCP2_FRAME_PING:
8568       non_probing_pkt = 1;
8569       break;
8570     case NGTCP2_FRAME_PATH_CHALLENGE:
8571       conn_recv_path_challenge(conn, path, &fr->path_challenge);
8572       path_challenge_recved = 1;
8573       break;
8574     case NGTCP2_FRAME_PATH_RESPONSE:
8575       rv = conn_recv_path_response(conn, &fr->path_response, ts);
8576       if (rv != 0) {
8577         return rv;
8578       }
8579       break;
8580     case NGTCP2_FRAME_NEW_CONNECTION_ID:
8581       rv = conn_recv_new_connection_id(conn, &fr->new_connection_id);
8582       if (rv != 0) {
8583         return rv;
8584       }
8585       recv_ncid = 1;
8586       break;
8587     case NGTCP2_FRAME_RETIRE_CONNECTION_ID:
8588       rv = conn_recv_retire_connection_id(conn, &hd, &fr->retire_connection_id,
8589                                           ts);
8590       if (rv != 0) {
8591         return rv;
8592       }
8593       non_probing_pkt = 1;
8594       break;
8595     case NGTCP2_FRAME_NEW_TOKEN:
8596       rv = conn_recv_new_token(conn, &fr->new_token);
8597       if (rv != 0) {
8598         return rv;
8599       }
8600       non_probing_pkt = 1;
8601       break;
8602     case NGTCP2_FRAME_HANDSHAKE_DONE:
8603       rv = conn_recv_handshake_done(conn, ts);
8604       if (rv != 0) {
8605         return rv;
8606       }
8607       non_probing_pkt = 1;
8608       break;
8609     case NGTCP2_FRAME_STREAMS_BLOCKED_BIDI:
8610       rv = conn_recv_streams_blocked_bidi(conn, &fr->streams_blocked);
8611       if (rv != 0) {
8612         return rv;
8613       }
8614       non_probing_pkt = 1;
8615       break;
8616     case NGTCP2_FRAME_STREAMS_BLOCKED_UNI:
8617       rv = conn_recv_streams_blocked_uni(conn, &fr->streams_blocked);
8618       if (rv != 0) {
8619         return rv;
8620       }
8621       non_probing_pkt = 1;
8622       break;
8623     case NGTCP2_FRAME_DATA_BLOCKED:
8624       /* TODO Not implemented yet */
8625       non_probing_pkt = 1;
8626       break;
8627     case NGTCP2_FRAME_DATAGRAM:
8628     case NGTCP2_FRAME_DATAGRAM_LEN:
8629       if ((uint64_t)nread >
8630           conn->local.transport_params.max_datagram_frame_size) {
8631         return NGTCP2_ERR_PROTO;
8632       }
8633       rv = conn_recv_datagram(conn, &fr->datagram);
8634       if (rv != 0) {
8635         return rv;
8636       }
8637       non_probing_pkt = 1;
8638       break;
8639     }
8640 
8641     ngtcp2_qlog_write_frame(&conn->qlog, fr);
8642   }
8643 
8644   ngtcp2_qlog_pkt_received_end(&conn->qlog, &hd, pktlen);
8645 
8646   if (recv_ncid) {
8647     rv = conn_post_process_recv_new_connection_id(conn, ts);
8648     if (rv != 0) {
8649       return rv;
8650     }
8651   }
8652 
8653   if (conn->server && hd.type == NGTCP2_PKT_SHORT &&
8654       !ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
8655     if (non_probing_pkt && pktns->rx.max_pkt_num < hd.pkt_num &&
8656         !conn_path_validation_in_progress(conn, path)) {
8657       rv = conn_recv_non_probing_pkt_on_new_path(conn, path, dgramlen,
8658                                                  new_cid_used, ts);
8659       if (rv != 0) {
8660         if (ngtcp2_err_is_fatal(rv)) {
8661           return rv;
8662         }
8663 
8664         /* DCID is not available.  Just continue. */
8665         assert(NGTCP2_ERR_CONN_ID_BLOCKED == rv);
8666       }
8667     } else {
8668       rv = conn_recv_pkt_from_new_path(conn, path, dgramlen,
8669                                        path_challenge_recved, ts);
8670       if (rv != 0) {
8671         if (ngtcp2_err_is_fatal(rv)) {
8672           return rv;
8673         }
8674 
8675         /* DCID is not available.  Just continue. */
8676         assert(NGTCP2_ERR_CONN_ID_BLOCKED == rv);
8677       }
8678     }
8679   }
8680 
8681   if (hd.type == NGTCP2_PKT_SHORT) {
8682     if (ckm == conn->crypto.key_update.new_rx_ckm) {
8683       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "rotate keys");
8684       conn_rotate_keys(conn, hd.pkt_num);
8685     } else if (ckm->pkt_num > hd.pkt_num) {
8686       ckm->pkt_num = hd.pkt_num;
8687     }
8688 
8689     if (conn->server && conn->early.ckm &&
8690         conn->early.discard_started_ts == UINT64_MAX) {
8691       conn->early.discard_started_ts = ts;
8692     }
8693 
8694     if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
8695       conn_update_keep_alive_last_ts(conn, ts);
8696     }
8697   }
8698 
8699   rv = pktns_commit_recv_pkt_num(pktns, hd.pkt_num, require_ack, pkt_ts);
8700   if (rv != 0) {
8701     return rv;
8702   }
8703 
8704   pktns_increase_ecn_counts(pktns, pi);
8705 
8706   if (require_ack &&
8707       (++pktns->acktr.rx_npkt >= conn->local.settings.ack_thresh ||
8708        (pi->ecn & NGTCP2_ECN_MASK) == NGTCP2_ECN_CE)) {
8709     ngtcp2_acktr_immediate_ack(&pktns->acktr);
8710   }
8711 
8712   rv = ngtcp2_conn_sched_ack(conn, &pktns->acktr, hd.pkt_num, require_ack,
8713                              pkt_ts);
8714   if (rv != 0) {
8715     return rv;
8716   }
8717 
8718   conn_restart_timer_on_read(conn, ts);
8719 
8720   ngtcp2_qlog_metrics_updated(&conn->qlog, &conn->cstat);
8721 
8722   if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
8723     conn_update_dcid_max_udp_payload_size(conn, &conn->dcid.current, dgramlen);
8724   }
8725 
8726   return conn->state == NGTCP2_CS_DRAINING ? NGTCP2_ERR_DRAINING
8727                                            : (ngtcp2_ssize)pktlen;
8728 }
8729 
8730 /*
8731  * conn_process_buffered_protected_pkt processes buffered 0RTT or
8732  * Short packets.
8733  *
8734  * This function returns 0 if it succeeds, or the same negative error
8735  * codes from conn_recv_pkt.
8736  */
conn_process_buffered_protected_pkt(ngtcp2_conn * conn,ngtcp2_pktns * pktns,ngtcp2_tstamp ts)8737 static int conn_process_buffered_protected_pkt(ngtcp2_conn *conn,
8738                                                ngtcp2_pktns *pktns,
8739                                                ngtcp2_tstamp ts) {
8740   ngtcp2_ssize nread;
8741   ngtcp2_pkt_chain **ppc, *next;
8742   int rv;
8743 
8744   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
8745                   "processing buffered protected packet");
8746 
8747   for (ppc = &pktns->rx.buffed_pkts; *ppc;) {
8748     next = (*ppc)->next;
8749     nread = conn_recv_pkt(conn, &(*ppc)->path.path, &(*ppc)->pi, (*ppc)->pkt,
8750                           (*ppc)->pktlen, (*ppc)->dgramlen, (*ppc)->ts, ts);
8751     if (nread < 0 && !ngtcp2_err_is_fatal((int)nread) &&
8752         nread != NGTCP2_ERR_DRAINING) {
8753       /* TODO We don't know this is the first QUIC packet in a
8754          datagram. */
8755       rv = conn_on_stateless_reset(conn, &(*ppc)->path.path, (*ppc)->pkt,
8756                                    (*ppc)->pktlen);
8757       if (rv == 0) {
8758         ngtcp2_pkt_chain_del(*ppc, conn->mem);
8759         *ppc = next;
8760         return NGTCP2_ERR_DRAINING;
8761       }
8762     }
8763 
8764     ngtcp2_pkt_chain_del(*ppc, conn->mem);
8765     *ppc = next;
8766     if (nread < 0) {
8767       if (nread == NGTCP2_ERR_DISCARD_PKT) {
8768         continue;
8769       }
8770       return (int)nread;
8771     }
8772   }
8773 
8774   return 0;
8775 }
8776 
8777 /*
8778  * conn_process_buffered_handshake_pkt processes buffered Handshake
8779  * packets.
8780  *
8781  * This function returns 0 if it succeeds, or the same negative error
8782  * codes from conn_recv_handshake_pkt.
8783  */
conn_process_buffered_handshake_pkt(ngtcp2_conn * conn,ngtcp2_tstamp ts)8784 static int conn_process_buffered_handshake_pkt(ngtcp2_conn *conn,
8785                                                ngtcp2_tstamp ts) {
8786   ngtcp2_pktns *pktns = conn->hs_pktns;
8787   ngtcp2_ssize nread;
8788   ngtcp2_pkt_chain **ppc, *next;
8789 
8790   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
8791                   "processing buffered handshake packet");
8792 
8793   for (ppc = &pktns->rx.buffed_pkts; *ppc;) {
8794     next = (*ppc)->next;
8795     nread = conn_recv_handshake_pkt(conn, &(*ppc)->path.path, &(*ppc)->pi,
8796                                     (*ppc)->pkt, (*ppc)->pktlen,
8797                                     (*ppc)->dgramlen, (*ppc)->ts, ts);
8798     ngtcp2_pkt_chain_del(*ppc, conn->mem);
8799     *ppc = next;
8800     if (nread < 0) {
8801       if (nread == NGTCP2_ERR_DISCARD_PKT) {
8802         continue;
8803       }
8804       return (int)nread;
8805     }
8806   }
8807 
8808   return 0;
8809 }
8810 
conn_sync_stream_id_limit(ngtcp2_conn * conn)8811 static void conn_sync_stream_id_limit(ngtcp2_conn *conn) {
8812   ngtcp2_transport_params *params = &conn->remote.transport_params;
8813 
8814   conn->local.bidi.max_streams = params->initial_max_streams_bidi;
8815   conn->local.uni.max_streams = params->initial_max_streams_uni;
8816 }
8817 
strm_set_max_offset(void * data,void * ptr)8818 static int strm_set_max_offset(void *data, void *ptr) {
8819   ngtcp2_conn *conn = ptr;
8820   ngtcp2_transport_params *params = &conn->remote.transport_params;
8821   ngtcp2_strm *strm = data;
8822   uint64_t max_offset;
8823   int rv;
8824 
8825   if (!conn_local_stream(conn, strm->stream_id)) {
8826     return 0;
8827   }
8828 
8829   if (bidi_stream(strm->stream_id)) {
8830     max_offset = params->initial_max_stream_data_bidi_remote;
8831   } else {
8832     max_offset = params->initial_max_stream_data_uni;
8833   }
8834 
8835   if (strm->tx.max_offset < max_offset) {
8836     strm->tx.max_offset = max_offset;
8837 
8838     /* Don't call callback if stream is half-closed local */
8839     if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
8840       return 0;
8841     }
8842 
8843     rv = conn_call_extend_max_stream_data(conn, strm, strm->stream_id,
8844                                           strm->tx.max_offset);
8845     if (rv != 0) {
8846       return rv;
8847     }
8848   }
8849 
8850   return 0;
8851 }
8852 
conn_sync_stream_data_limit(ngtcp2_conn * conn)8853 static int conn_sync_stream_data_limit(ngtcp2_conn *conn) {
8854   return ngtcp2_map_each(&conn->strms, strm_set_max_offset, conn);
8855 }
8856 
8857 /*
8858  * conn_handshake_completed is called once cryptographic handshake has
8859  * completed.
8860  *
8861  * This function returns 0 if it succeeds, or one of the following
8862  * negative error codes:
8863  *
8864  * NGTCP2_ERR_CALLBACK_FAILURE
8865  *     User callback failed.
8866  */
conn_handshake_completed(ngtcp2_conn * conn)8867 static int conn_handshake_completed(ngtcp2_conn *conn) {
8868   int rv;
8869 
8870   conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED;
8871 
8872   rv = conn_call_handshake_completed(conn);
8873   if (rv != 0) {
8874     return rv;
8875   }
8876 
8877   if (conn->local.bidi.max_streams > 0) {
8878     rv = conn_call_extend_max_local_streams_bidi(conn,
8879                                                  conn->local.bidi.max_streams);
8880     if (rv != 0) {
8881       return rv;
8882     }
8883   }
8884   if (conn->local.uni.max_streams > 0) {
8885     rv = conn_call_extend_max_local_streams_uni(conn,
8886                                                 conn->local.uni.max_streams);
8887     if (rv != 0) {
8888       return rv;
8889     }
8890   }
8891 
8892   return 0;
8893 }
8894 
8895 /*
8896  * conn_recv_cpkt processes compound packet after handshake.  The
8897  * buffer pointed by |pkt| might contain multiple packets.  The Short
8898  * packet must be the last one because it does not have payload length
8899  * field.
8900  *
8901  * This function returns 0 if it succeeds, or the same negative error
8902  * codes from conn_recv_pkt except for NGTCP2_ERR_DISCARD_PKT.
8903  */
conn_recv_cpkt(ngtcp2_conn * conn,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,ngtcp2_tstamp ts)8904 static int conn_recv_cpkt(ngtcp2_conn *conn, const ngtcp2_path *path,
8905                           const ngtcp2_pkt_info *pi, const uint8_t *pkt,
8906                           size_t pktlen, ngtcp2_tstamp ts) {
8907   ngtcp2_ssize nread;
8908   int rv;
8909   const uint8_t *origpkt = pkt;
8910   size_t dgramlen = pktlen;
8911 
8912   if (ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
8913     conn->dcid.current.bytes_recv += dgramlen;
8914   }
8915 
8916   while (pktlen) {
8917     nread = conn_recv_pkt(conn, path, pi, pkt, pktlen, dgramlen, ts, ts);
8918     if (nread < 0) {
8919       if (ngtcp2_err_is_fatal((int)nread)) {
8920         return (int)nread;
8921       }
8922 
8923       if (nread == NGTCP2_ERR_DRAINING) {
8924         return NGTCP2_ERR_DRAINING;
8925       }
8926 
8927       if (origpkt == pkt) {
8928         rv = conn_on_stateless_reset(conn, path, origpkt, dgramlen);
8929         if (rv == 0) {
8930           return NGTCP2_ERR_DRAINING;
8931         }
8932       }
8933       if (nread == NGTCP2_ERR_DISCARD_PKT) {
8934         return 0;
8935       }
8936       return (int)nread;
8937     }
8938 
8939     assert(pktlen >= (size_t)nread);
8940     pkt += nread;
8941     pktlen -= (size_t)nread;
8942 
8943     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_PKT,
8944                     "read packet %td left %zu", nread, pktlen);
8945   }
8946 
8947   return 0;
8948 }
8949 
8950 /*
8951  * conn_is_retired_path returns nonzero if |path| is included in
8952  * retired path list.
8953  */
conn_is_retired_path(ngtcp2_conn * conn,const ngtcp2_path * path)8954 static int conn_is_retired_path(ngtcp2_conn *conn, const ngtcp2_path *path) {
8955   size_t i, len = ngtcp2_ringbuf_len(&conn->dcid.retired);
8956   ngtcp2_dcid *dcid;
8957 
8958   for (i = 0; i < len; ++i) {
8959     dcid = ngtcp2_ringbuf_get(&conn->dcid.retired, i);
8960     if (ngtcp2_path_eq(&dcid->ps.path, path)) {
8961       return 1;
8962     }
8963   }
8964 
8965   return 0;
8966 }
8967 
8968 /*
8969  * conn_enqueue_handshake_done enqueues HANDSHAKE_DONE frame for
8970  * transmission.
8971  */
conn_enqueue_handshake_done(ngtcp2_conn * conn)8972 static int conn_enqueue_handshake_done(ngtcp2_conn *conn) {
8973   ngtcp2_pktns *pktns = &conn->pktns;
8974   ngtcp2_frame_chain *nfrc;
8975   int rv;
8976 
8977   assert(conn->server);
8978 
8979   rv = ngtcp2_frame_chain_new(&nfrc, conn->mem);
8980   if (rv != 0) {
8981     return rv;
8982   }
8983 
8984   nfrc->fr.type = NGTCP2_FRAME_HANDSHAKE_DONE;
8985   nfrc->next = pktns->tx.frq;
8986   pktns->tx.frq = nfrc;
8987 
8988   return 0;
8989 }
8990 
8991 /**
8992  * @function
8993  *
8994  * `conn_read_handshake` performs QUIC cryptographic handshake by
8995  * reading given data.  |pkt| points to the buffer to read and
8996  * |pktlen| is the length of the buffer.  |path| is the network path.
8997  *
8998  * This function returns the number of bytes processed.  Unless the
8999  * last packet is Short packet and an application decryption key has
9000  * been installed, it returns |pktlen| if it succeeds.  If it finds
9001  * Short packet and an application decryption key has been installed,
9002  * it returns the number of bytes just before Short packet begins.
9003  *
9004  * This function returns the number of bytes processed if it succeeds,
9005  * or one of the following negative error codes: (TBD).
9006  */
conn_read_handshake(ngtcp2_conn * conn,const ngtcp2_path * path,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,ngtcp2_tstamp ts)9007 static ngtcp2_ssize conn_read_handshake(ngtcp2_conn *conn,
9008                                         const ngtcp2_path *path,
9009                                         const ngtcp2_pkt_info *pi,
9010                                         const uint8_t *pkt, size_t pktlen,
9011                                         ngtcp2_tstamp ts) {
9012   int rv;
9013   ngtcp2_ssize nread;
9014 
9015   switch (conn->state) {
9016   case NGTCP2_CS_CLIENT_INITIAL:
9017     /* TODO Better to log something when we ignore input */
9018     return (ngtcp2_ssize)pktlen;
9019   case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
9020     nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
9021     if (nread < 0) {
9022       return nread;
9023     }
9024 
9025     if (conn->state == NGTCP2_CS_CLIENT_INITIAL) {
9026       /* Retry packet was received */
9027       return (ngtcp2_ssize)pktlen;
9028     }
9029 
9030     assert(conn->hs_pktns);
9031 
9032     if (conn->hs_pktns->crypto.rx.ckm && conn->in_pktns) {
9033       rv = conn_process_buffered_handshake_pkt(conn, ts);
9034       if (rv != 0) {
9035         return rv;
9036       }
9037     }
9038 
9039     if ((conn->flags & (NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED |
9040                         NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED)) ==
9041         NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) {
9042       rv = conn_handshake_completed(conn);
9043       if (rv != 0) {
9044         return rv;
9045       }
9046 
9047       rv = conn_process_buffered_protected_pkt(conn, &conn->pktns, ts);
9048       if (rv != 0) {
9049         return rv;
9050       }
9051     }
9052 
9053     return nread;
9054   case NGTCP2_CS_SERVER_INITIAL:
9055     nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
9056     if (nread < 0) {
9057       return nread;
9058     }
9059 
9060     /*
9061      * Client ServerHello might not fit into single Initial packet
9062      * (e.g., resuming session with client authentication).  If we get
9063      * Client Initial which does not increase offset or it is 0RTT
9064      * packet buffered, perform address validation in order to buffer
9065      * validated data only.
9066      */
9067     if (ngtcp2_strm_rx_offset(&conn->in_pktns->crypto.strm) == 0) {
9068       if (conn->in_pktns->crypto.strm.rx.rob &&
9069           ngtcp2_rob_data_buffered(conn->in_pktns->crypto.strm.rx.rob)) {
9070         /* Address has been validated with token */
9071         if (conn->local.settings.token.len) {
9072           return nread;
9073         }
9074         return NGTCP2_ERR_RETRY;
9075       }
9076       if (conn->in_pktns->rx.buffed_pkts) {
9077         /* 0RTT is buffered, force retry */
9078         return NGTCP2_ERR_RETRY;
9079       }
9080       /* If neither CRYPTO frame nor 0RTT packet is processed, just
9081          drop connection. */
9082       return NGTCP2_ERR_DROP_CONN;
9083     }
9084 
9085     /* Process re-ordered 0-RTT packets which arrived before Initial
9086        packet. */
9087     if (conn->early.ckm) {
9088       assert(conn->in_pktns);
9089 
9090       rv = conn_process_buffered_protected_pkt(conn, conn->in_pktns, ts);
9091       if (rv != 0) {
9092         return rv;
9093       }
9094     }
9095 
9096     return nread;
9097   case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
9098     nread = conn_recv_handshake_cpkt(conn, path, pi, pkt, pktlen, ts);
9099     if (nread < 0) {
9100       return nread;
9101     }
9102 
9103     if (conn->hs_pktns->crypto.rx.ckm) {
9104       rv = conn_process_buffered_handshake_pkt(conn, ts);
9105       if (rv != 0) {
9106         return rv;
9107       }
9108     }
9109 
9110     if (conn->hs_pktns->rx.max_pkt_num != -1) {
9111       conn_discard_initial_state(conn, ts);
9112     }
9113 
9114     if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
9115       /* If server hits amplification limit, it cancels loss detection
9116          timer.  If server receives a packet from client, the limit is
9117          increased and server can send more.  If server has
9118          ack-eliciting Initial or Handshake packets, it should resend
9119          it if timer fired but timer is not armed in this case.  So
9120          instead of resending Initial/Handshake packets, if server has
9121          1RTT data to send, it might send them and then might hit
9122          amplification limit again until it hits stream data limit.
9123          Initial/Handshake data is not resent.  In order to avoid this
9124          situation, try to arm loss detection and check the expiry
9125          here so that on next write call, we can resend
9126          Initial/Handshake first. */
9127       if (conn->cstat.loss_detection_timer == UINT64_MAX) {
9128         ngtcp2_conn_set_loss_detection_timer(conn, ts);
9129         if (ngtcp2_conn_loss_detection_expiry(conn) <= ts) {
9130           rv = ngtcp2_conn_on_loss_detection_timer(conn, ts);
9131           if (rv != 0) {
9132             return rv;
9133           }
9134         }
9135       }
9136 
9137       if ((size_t)nread < pktlen) {
9138         /* We have Short packet and application rx key, but the
9139            handshake has not completed yet. */
9140         ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
9141                         "buffering Short packet len=%zu",
9142                         pktlen - (size_t)nread);
9143 
9144         rv = conn_buffer_pkt(conn, &conn->pktns, path, pi, pkt + nread,
9145                              pktlen - (size_t)nread, pktlen, ts);
9146         if (rv != 0) {
9147           assert(ngtcp2_err_is_fatal(rv));
9148           return rv;
9149         }
9150 
9151         return (ssize_t)pktlen;
9152       }
9153 
9154       return nread;
9155     }
9156 
9157     if (!(conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED)) {
9158       return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
9159     }
9160 
9161     rv = conn_handshake_completed(conn);
9162     if (rv != 0) {
9163       return rv;
9164     }
9165     conn->state = NGTCP2_CS_POST_HANDSHAKE;
9166 
9167     rv = conn_call_activate_dcid(conn, &conn->dcid.current);
9168     if (rv != 0) {
9169       return rv;
9170     }
9171 
9172     rv = conn_process_buffered_protected_pkt(conn, &conn->pktns, ts);
9173     if (rv != 0) {
9174       return rv;
9175     }
9176 
9177     conn_discard_handshake_state(conn, ts);
9178 
9179     rv = conn_enqueue_handshake_done(conn);
9180     if (rv != 0) {
9181       return rv;
9182     }
9183 
9184     conn->pktns.rtb.persistent_congestion_start_ts = ts;
9185 
9186     /* Re-arm loss detection timer here after handshake has been
9187        confirmed. */
9188     ngtcp2_conn_set_loss_detection_timer(conn, ts);
9189 
9190     return nread;
9191   case NGTCP2_CS_CLOSING:
9192     return NGTCP2_ERR_CLOSING;
9193   case NGTCP2_CS_DRAINING:
9194     return NGTCP2_ERR_DRAINING;
9195   default:
9196     return (ngtcp2_ssize)pktlen;
9197   }
9198 }
9199 
ngtcp2_conn_read_pkt_versioned(ngtcp2_conn * conn,const ngtcp2_path * path,int pkt_info_version,const ngtcp2_pkt_info * pi,const uint8_t * pkt,size_t pktlen,ngtcp2_tstamp ts)9200 int ngtcp2_conn_read_pkt_versioned(ngtcp2_conn *conn, const ngtcp2_path *path,
9201                                    int pkt_info_version,
9202                                    const ngtcp2_pkt_info *pi,
9203                                    const uint8_t *pkt, size_t pktlen,
9204                                    ngtcp2_tstamp ts) {
9205   int rv = 0;
9206   ngtcp2_ssize nread = 0;
9207   (void)pkt_info_version;
9208 
9209   conn->log.last_ts = ts;
9210   conn->qlog.last_ts = ts;
9211 
9212   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON, "recv packet len=%zu",
9213                   pktlen);
9214 
9215   if (pktlen == 0) {
9216     return NGTCP2_ERR_INVALID_ARGUMENT;
9217   }
9218 
9219   /* client does not expect a packet from unknown path. */
9220   if (!conn->server && !ngtcp2_path_eq(&conn->dcid.current.ps.path, path) &&
9221       (!conn->pv || !ngtcp2_path_eq(&conn->pv->dcid.ps.path, path)) &&
9222       !conn_is_retired_path(conn, path)) {
9223     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
9224                     "ignore packet from unknown path");
9225     return 0;
9226   }
9227 
9228   switch (conn->state) {
9229   case NGTCP2_CS_CLIENT_INITIAL:
9230   case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
9231   case NGTCP2_CS_CLIENT_TLS_HANDSHAKE_FAILED:
9232     nread = conn_read_handshake(conn, path, pi, pkt, pktlen, ts);
9233     if (nread < 0) {
9234       return (int)nread;
9235     }
9236 
9237     if ((size_t)nread == pktlen) {
9238       return 0;
9239     }
9240 
9241     assert(conn->pktns.crypto.rx.ckm);
9242 
9243     pkt += nread;
9244     pktlen -= (size_t)nread;
9245 
9246     break;
9247   case NGTCP2_CS_SERVER_INITIAL:
9248   case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
9249   case NGTCP2_CS_SERVER_TLS_HANDSHAKE_FAILED:
9250     if (!ngtcp2_path_eq(&conn->dcid.current.ps.path, path)) {
9251       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
9252                       "ignore packet from unknown path during handshake");
9253 
9254       if (conn->state == NGTCP2_CS_SERVER_INITIAL &&
9255           ngtcp2_strm_rx_offset(&conn->in_pktns->crypto.strm) == 0 &&
9256           (!conn->in_pktns->crypto.strm.rx.rob ||
9257            !ngtcp2_rob_data_buffered(conn->in_pktns->crypto.strm.rx.rob))) {
9258         return NGTCP2_ERR_DROP_CONN;
9259       }
9260 
9261       return 0;
9262     }
9263 
9264     nread = conn_read_handshake(conn, path, pi, pkt, pktlen, ts);
9265     if (nread < 0) {
9266       return (int)nread;
9267     }
9268 
9269     if ((size_t)nread == pktlen) {
9270       return 0;
9271     }
9272 
9273     assert(conn->pktns.crypto.rx.ckm);
9274 
9275     pkt += nread;
9276     pktlen -= (size_t)nread;
9277 
9278     break;
9279   case NGTCP2_CS_CLOSING:
9280     return NGTCP2_ERR_CLOSING;
9281   case NGTCP2_CS_DRAINING:
9282     return NGTCP2_ERR_DRAINING;
9283   case NGTCP2_CS_POST_HANDSHAKE:
9284     rv = conn_prepare_key_update(conn, ts);
9285     if (rv != 0) {
9286       return rv;
9287     }
9288     break;
9289   default:
9290     assert(0);
9291     abort();
9292   }
9293 
9294   return conn_recv_cpkt(conn, path, pi, pkt, pktlen, ts);
9295 }
9296 
9297 /*
9298  * conn_check_pkt_num_exhausted returns nonzero if packet number is
9299  * exhausted in at least one of packet number space.
9300  */
conn_check_pkt_num_exhausted(ngtcp2_conn * conn)9301 static int conn_check_pkt_num_exhausted(ngtcp2_conn *conn) {
9302   ngtcp2_pktns *in_pktns = conn->in_pktns;
9303   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
9304 
9305   return (in_pktns && in_pktns->tx.last_pkt_num == NGTCP2_MAX_PKT_NUM) ||
9306          (hs_pktns && hs_pktns->tx.last_pkt_num == NGTCP2_MAX_PKT_NUM) ||
9307          conn->pktns.tx.last_pkt_num == NGTCP2_MAX_PKT_NUM;
9308 }
9309 
9310 /*
9311  * conn_retransmit_retry_early retransmits 0RTT packet after Retry is
9312  * received from server.
9313  */
conn_retransmit_retry_early(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_tstamp ts)9314 static ngtcp2_ssize conn_retransmit_retry_early(ngtcp2_conn *conn,
9315                                                 ngtcp2_pkt_info *pi,
9316                                                 uint8_t *dest, size_t destlen,
9317                                                 ngtcp2_tstamp ts) {
9318   return conn_write_pkt(conn, pi, dest, destlen, NULL, NGTCP2_PKT_0RTT,
9319                         NGTCP2_WRITE_PKT_FLAG_NONE, ts);
9320 }
9321 
9322 /*
9323  * conn_handshake_probe_left returns nonzero if there are probe
9324  * packets to be sent for Initial or Handshake packet number space
9325  * left.
9326  */
conn_handshake_probe_left(ngtcp2_conn * conn)9327 static int conn_handshake_probe_left(ngtcp2_conn *conn) {
9328   return (conn->in_pktns && conn->in_pktns->rtb.probe_pkt_left) ||
9329          conn->hs_pktns->rtb.probe_pkt_left;
9330 }
9331 
9332 /*
9333  * conn_validate_early_transport_params_limits validates that the
9334  * limits in transport parameters remembered by client for early data
9335  * are not reduced.  This function is only used by client and should
9336  * only be called when early data is accepted by server.
9337  */
conn_validate_early_transport_params_limits(ngtcp2_conn * conn)9338 static int conn_validate_early_transport_params_limits(ngtcp2_conn *conn) {
9339   const ngtcp2_transport_params *params = &conn->remote.transport_params;
9340 
9341   assert(!conn->server);
9342 
9343   if (conn->early.transport_params.active_connection_id_limit >
9344           params->active_connection_id_limit ||
9345       conn->early.transport_params.initial_max_data >
9346           params->initial_max_data ||
9347       conn->early.transport_params.initial_max_stream_data_bidi_local >
9348           params->initial_max_stream_data_bidi_local ||
9349       conn->early.transport_params.initial_max_stream_data_bidi_remote >
9350           params->initial_max_stream_data_bidi_remote ||
9351       conn->early.transport_params.initial_max_stream_data_uni >
9352           params->initial_max_stream_data_uni ||
9353       conn->early.transport_params.initial_max_streams_bidi >
9354           params->initial_max_streams_bidi ||
9355       conn->early.transport_params.initial_max_streams_uni >
9356           params->initial_max_streams_uni ||
9357       conn->early.transport_params.max_datagram_frame_size >
9358           params->max_datagram_frame_size) {
9359     return NGTCP2_ERR_PROTO;
9360   }
9361 
9362   return 0;
9363 }
9364 
9365 /*
9366  * conn_write_handshake writes QUIC handshake packets to the buffer
9367  * pointed by |dest| of length |destlen|.  |write_datalen| specifies
9368  * the expected length of 0RTT or Short packet payload.  Specify 0 to
9369  * |write_datalen| if there is no such data.
9370  *
9371  * This function returns the number of bytes written to the buffer, or
9372  * one of the following negative error codes:
9373  *
9374  * NGTCP2_ERR_PKT_NUM_EXHAUSTED
9375  *     Packet number is exhausted.
9376  * NGTCP2_ERR_NOMEM
9377  *     Out of memory
9378  * NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM
9379  *     Required transport parameter is missing.
9380  * NGTCP2_CS_CLOSING
9381  *     Connection is in closing state.
9382  * NGTCP2_CS_DRAINING
9383  *     Connection is in draining state.
9384  *
9385  * In addition to the above negative error codes, the same error codes
9386  * from conn_recv_pkt may also be returned.
9387  */
conn_write_handshake(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint64_t write_datalen,ngtcp2_tstamp ts)9388 static ngtcp2_ssize conn_write_handshake(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
9389                                          uint8_t *dest, size_t destlen,
9390                                          uint64_t write_datalen,
9391                                          ngtcp2_tstamp ts) {
9392   int rv;
9393   ngtcp2_ssize res = 0, nwrite = 0, early_spktlen = 0;
9394   size_t origlen = destlen;
9395   uint64_t pending_early_datalen;
9396   ngtcp2_dcid *dcid;
9397   ngtcp2_preferred_addr *paddr;
9398 
9399   switch (conn->state) {
9400   case NGTCP2_CS_CLIENT_INITIAL:
9401     pending_early_datalen = conn_retry_early_payloadlen(conn);
9402     if (pending_early_datalen) {
9403       write_datalen = pending_early_datalen;
9404     }
9405 
9406     if (!(conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY)) {
9407       nwrite =
9408           conn_write_client_initial(conn, pi, dest, destlen, write_datalen, ts);
9409       if (nwrite <= 0) {
9410         return nwrite;
9411       }
9412     } else {
9413       nwrite = conn_write_handshake_pkt(
9414           conn, pi, dest, destlen, NGTCP2_PKT_INITIAL,
9415           NGTCP2_WRITE_PKT_FLAG_NONE, write_datalen, ts);
9416       if (nwrite < 0) {
9417         return nwrite;
9418       }
9419     }
9420 
9421     if (pending_early_datalen) {
9422       early_spktlen = conn_retransmit_retry_early(conn, pi, dest + nwrite,
9423                                                   destlen - (size_t)nwrite, ts);
9424 
9425       if (early_spktlen < 0) {
9426         assert(ngtcp2_err_is_fatal((int)early_spktlen));
9427         return early_spktlen;
9428       }
9429     }
9430 
9431     conn->state = NGTCP2_CS_CLIENT_WAIT_HANDSHAKE;
9432 
9433     res = nwrite + early_spktlen;
9434 
9435     return res;
9436   case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
9437     if (!conn_handshake_probe_left(conn) && conn_cwnd_is_zero(conn)) {
9438       destlen = 0;
9439     } else {
9440       if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED)) {
9441         pending_early_datalen = conn_retry_early_payloadlen(conn);
9442         if (pending_early_datalen) {
9443           write_datalen = pending_early_datalen;
9444         }
9445       }
9446 
9447       nwrite =
9448           conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
9449       if (nwrite < 0) {
9450         return nwrite;
9451       }
9452 
9453       res += nwrite;
9454       dest += nwrite;
9455       destlen -= (size_t)nwrite;
9456     }
9457 
9458     if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
9459       if (!(conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED)) {
9460         nwrite = conn_retransmit_retry_early(conn, pi, dest, destlen, ts);
9461         if (nwrite < 0) {
9462           return nwrite;
9463         }
9464 
9465         res += nwrite;
9466       }
9467 
9468       if (res == 0) {
9469         nwrite = conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
9470         if (nwrite < 0) {
9471           return nwrite;
9472         }
9473         res = nwrite;
9474       }
9475 
9476       return res;
9477     }
9478 
9479     if (!(conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED)) {
9480       return NGTCP2_ERR_REQUIRED_TRANSPORT_PARAM;
9481     }
9482 
9483     if ((conn->flags & NGTCP2_CONN_FLAG_EARLY_KEY_INSTALLED) &&
9484         !(conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED)) {
9485       rv = conn_validate_early_transport_params_limits(conn);
9486       if (rv != 0) {
9487         return rv;
9488       }
9489     }
9490 
9491     /* Server might increase stream data limits.  Extend it if we have
9492        streams created for early data. */
9493     rv = conn_sync_stream_data_limit(conn);
9494     if (rv != 0) {
9495       return rv;
9496     }
9497 
9498     conn->state = NGTCP2_CS_POST_HANDSHAKE;
9499 
9500     if (conn->remote.transport_params.preferred_address_present) {
9501       assert(!ngtcp2_ringbuf_full(&conn->dcid.unused));
9502 
9503       paddr = &conn->remote.transport_params.preferred_address;
9504       dcid = ngtcp2_ringbuf_push_back(&conn->dcid.unused);
9505       ngtcp2_dcid_init(dcid, 1, &paddr->cid, paddr->stateless_reset_token);
9506 
9507       rv = ngtcp2_gaptr_push(&conn->dcid.seqgap, 1, 1);
9508       if (rv != 0) {
9509         return (ngtcp2_ssize)rv;
9510       }
9511     }
9512 
9513     if (conn->remote.transport_params.stateless_reset_token_present) {
9514       assert(conn->dcid.current.seq == 0);
9515       assert(!(conn->dcid.current.flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT));
9516       ngtcp2_dcid_set_token(
9517           &conn->dcid.current,
9518           conn->remote.transport_params.stateless_reset_token);
9519     }
9520 
9521     rv = conn_call_activate_dcid(conn, &conn->dcid.current);
9522     if (rv != 0) {
9523       return rv;
9524     }
9525 
9526     conn_process_early_rtb(conn);
9527 
9528     return res;
9529   case NGTCP2_CS_SERVER_INITIAL:
9530     nwrite =
9531         conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
9532     if (nwrite < 0) {
9533       return nwrite;
9534     }
9535 
9536     if (nwrite) {
9537       conn->state = NGTCP2_CS_SERVER_WAIT_HANDSHAKE;
9538     }
9539 
9540     return nwrite;
9541   case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
9542     if (conn_handshake_probe_left(conn) || !conn_cwnd_is_zero(conn)) {
9543       nwrite =
9544           conn_write_handshake_pkts(conn, pi, dest, destlen, write_datalen, ts);
9545       if (nwrite < 0) {
9546         return nwrite;
9547       }
9548 
9549       res += nwrite;
9550       dest += nwrite;
9551       destlen -= (size_t)nwrite;
9552     }
9553 
9554     if (res == 0) {
9555       nwrite = conn_write_handshake_ack_pkts(conn, pi, dest, origlen, ts);
9556       if (nwrite < 0) {
9557         return nwrite;
9558       }
9559 
9560       res += nwrite;
9561       dest += nwrite;
9562       origlen -= (size_t)nwrite;
9563     }
9564 
9565     return res;
9566   case NGTCP2_CS_CLOSING:
9567     return NGTCP2_ERR_CLOSING;
9568   case NGTCP2_CS_DRAINING:
9569     return NGTCP2_ERR_DRAINING;
9570   default:
9571     return 0;
9572   }
9573 }
9574 
9575 /**
9576  * @function
9577  *
9578  * `conn_client_write_handshake` writes client side handshake data and
9579  * 0RTT packet.
9580  *
9581  * In order to send STREAM data in 0RTT packet, specify
9582  * |vmsg|->stream.  |vmsg|->stream.strm, |vmsg|->stream.fin,
9583  * |vmsg|->stream.data, and |vmsg|->stream.datacnt are stream to which
9584  * 0-RTT data is sent, whether it is a last data chunk in this stream,
9585  * a vector of 0-RTT data, and its number of elements respectively.
9586  * The amount of 0RTT data sent is assigned to
9587  * *|vmsg|->stream.pdatalen.  If no data is sent, -1 is assigned.
9588  * Note that 0 length STREAM frame is allowed in QUIC, so 0 might be
9589  * assigned to *|vmsg|->stream.pdatalen.
9590  *
9591  * This function returns 0 if it cannot write any frame because buffer
9592  * is too small, or packet is congestion limited.  Application should
9593  * keep reading and wait for congestion window to grow.
9594  *
9595  * This function returns the number of bytes written to the buffer
9596  * pointed by |dest| if it succeeds, or one of the following negative
9597  * error codes: (TBD).
9598  */
conn_client_write_handshake(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_vmsg * vmsg,ngtcp2_tstamp ts)9599 static ngtcp2_ssize conn_client_write_handshake(ngtcp2_conn *conn,
9600                                                 ngtcp2_pkt_info *pi,
9601                                                 uint8_t *dest, size_t destlen,
9602                                                 ngtcp2_vmsg *vmsg,
9603                                                 ngtcp2_tstamp ts) {
9604   int send_stream = 0;
9605   int send_datagram = 0;
9606   ngtcp2_ssize spktlen, early_spktlen;
9607   uint64_t datalen;
9608   uint64_t write_datalen = 0;
9609   uint8_t wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
9610   int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
9611 
9612   assert(!conn->server);
9613 
9614   /* conn->early.ckm might be created in the first call of
9615      conn_handshake().  Check it later. */
9616   if (vmsg) {
9617     switch (vmsg->type) {
9618     case NGTCP2_VMSG_TYPE_STREAM:
9619       datalen = ngtcp2_vec_len(vmsg->stream.data, vmsg->stream.datacnt);
9620       send_stream =
9621           conn_retry_early_payloadlen(conn) == 0 &&
9622           /* 0 length STREAM frame is allowed */
9623           (datalen == 0 ||
9624            (datalen > 0 &&
9625             (vmsg->stream.strm->tx.max_offset - vmsg->stream.strm->tx.offset) &&
9626             (conn->tx.max_offset - conn->tx.offset)));
9627       if (send_stream) {
9628         write_datalen =
9629             conn_enforce_flow_control(conn, vmsg->stream.strm, datalen);
9630         write_datalen =
9631             ngtcp2_min(write_datalen, NGTCP2_MIN_COALESCED_PAYLOADLEN);
9632         write_datalen += NGTCP2_STREAM_OVERHEAD;
9633 
9634         if (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_MORE) {
9635           wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
9636         }
9637       } else {
9638         vmsg = NULL;
9639       }
9640       break;
9641     case NGTCP2_VMSG_TYPE_DATAGRAM:
9642       datalen = ngtcp2_vec_len(vmsg->datagram.data, vmsg->datagram.datacnt);
9643       send_datagram = conn_retry_early_payloadlen(conn) == 0;
9644       if (send_datagram) {
9645         write_datalen = datalen + NGTCP2_DATAGRAM_OVERHEAD;
9646 
9647         if (vmsg->datagram.flags & NGTCP2_WRITE_DATAGRAM_FLAG_MORE) {
9648           wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
9649         }
9650       } else {
9651         vmsg = NULL;
9652       }
9653       break;
9654     }
9655   }
9656 
9657   if (!ppe_pending) {
9658     spktlen = conn_write_handshake(conn, pi, dest, destlen, write_datalen, ts);
9659 
9660     if (spktlen < 0) {
9661       return spktlen;
9662     }
9663 
9664     if ((conn->flags & NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED) ||
9665         !conn->early.ckm || (!send_stream && !send_datagram)) {
9666       return spktlen;
9667     }
9668 
9669     /* If spktlen > 0, we are making a compound packet.  If Initial
9670        packet is written, we have to pad bytes to 0-RTT packet. */
9671     if (spktlen > 0 &&
9672         ngtcp2_pkt_get_type_long(dest[0]) == NGTCP2_PKT_INITIAL) {
9673       wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
9674       conn->pkt.require_padding = 1;
9675     } else {
9676       conn->pkt.require_padding = 0;
9677     }
9678   } else {
9679     assert(!conn->pktns.crypto.rx.ckm);
9680     assert(!conn->pktns.crypto.tx.ckm);
9681     assert(conn->early.ckm);
9682 
9683     if (conn->pkt.require_padding) {
9684       wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
9685     }
9686     spktlen = conn->pkt.hs_spktlen;
9687   }
9688 
9689   dest += spktlen;
9690   destlen -= (size_t)spktlen;
9691 
9692   if (conn_cwnd_is_zero(conn)) {
9693     return spktlen;
9694   }
9695 
9696   early_spktlen = conn_write_pkt(conn, pi, dest, destlen, vmsg, NGTCP2_PKT_0RTT,
9697                                  wflags, ts);
9698 
9699   if (early_spktlen < 0) {
9700     switch (early_spktlen) {
9701     case NGTCP2_ERR_STREAM_DATA_BLOCKED:
9702       return spktlen;
9703     case NGTCP2_ERR_WRITE_MORE:
9704       conn->pkt.hs_spktlen = spktlen;
9705       break;
9706     }
9707     return early_spktlen;
9708   }
9709 
9710   return spktlen + early_spktlen;
9711 }
9712 
ngtcp2_conn_handshake_completed(ngtcp2_conn * conn)9713 void ngtcp2_conn_handshake_completed(ngtcp2_conn *conn) {
9714   conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED;
9715   if (conn->server) {
9716     conn->flags |= NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED;
9717   }
9718 }
9719 
ngtcp2_conn_get_handshake_completed(ngtcp2_conn * conn)9720 int ngtcp2_conn_get_handshake_completed(ngtcp2_conn *conn) {
9721   return (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) &&
9722          (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED);
9723 }
9724 
ngtcp2_conn_sched_ack(ngtcp2_conn * conn,ngtcp2_acktr * acktr,int64_t pkt_num,int active_ack,ngtcp2_tstamp ts)9725 int ngtcp2_conn_sched_ack(ngtcp2_conn *conn, ngtcp2_acktr *acktr,
9726                           int64_t pkt_num, int active_ack, ngtcp2_tstamp ts) {
9727   int rv;
9728   (void)conn;
9729 
9730   rv = ngtcp2_acktr_add(acktr, pkt_num, active_ack, ts);
9731   if (rv != 0) {
9732     assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
9733     return rv;
9734   }
9735 
9736   return 0;
9737 }
9738 
ngtcp2_accept(ngtcp2_pkt_hd * dest,const uint8_t * pkt,size_t pktlen)9739 int ngtcp2_accept(ngtcp2_pkt_hd *dest, const uint8_t *pkt, size_t pktlen) {
9740   ngtcp2_ssize nread;
9741   ngtcp2_pkt_hd hd, *p;
9742 
9743   if (dest) {
9744     p = dest;
9745   } else {
9746     p = &hd;
9747   }
9748 
9749   if (pktlen == 0 || (pkt[0] & NGTCP2_HEADER_FORM_BIT) == 0) {
9750     return NGTCP2_ERR_INVALID_ARGUMENT;
9751   }
9752 
9753   nread = ngtcp2_pkt_decode_hd_long(p, pkt, pktlen);
9754   if (nread < 0) {
9755     return (int)nread;
9756   }
9757 
9758   if (p->version != NGTCP2_PROTO_VER_V1 &&
9759       (p->version < NGTCP2_PROTO_VER_DRAFT_MIN ||
9760        NGTCP2_PROTO_VER_DRAFT_MAX < p->version)) {
9761     return NGTCP2_ERR_VERSION_NEGOTIATION;
9762   }
9763 
9764   switch (p->type) {
9765   case NGTCP2_PKT_INITIAL:
9766     break;
9767   case NGTCP2_PKT_0RTT:
9768     /* 0-RTT packet may arrive before Initial packet due to
9769        re-ordering.  ngtcp2 does not buffer 0RTT packet unless the
9770        very first Initial packet is received or token is received. */
9771     return NGTCP2_ERR_RETRY;
9772   default:
9773     return NGTCP2_ERR_INVALID_ARGUMENT;
9774   }
9775 
9776   if (pktlen < NGTCP2_MAX_UDP_PAYLOAD_SIZE ||
9777       (p->token.len == 0 && p->dcid.datalen < NGTCP2_MIN_INITIAL_DCIDLEN)) {
9778     return NGTCP2_ERR_INVALID_ARGUMENT;
9779   }
9780 
9781   return 0;
9782 }
9783 
ngtcp2_conn_install_initial_key(ngtcp2_conn * conn,const ngtcp2_crypto_aead_ctx * rx_aead_ctx,const uint8_t * rx_iv,const ngtcp2_crypto_cipher_ctx * rx_hp_ctx,const ngtcp2_crypto_aead_ctx * tx_aead_ctx,const uint8_t * tx_iv,const ngtcp2_crypto_cipher_ctx * tx_hp_ctx,size_t ivlen)9784 int ngtcp2_conn_install_initial_key(
9785     ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *rx_aead_ctx,
9786     const uint8_t *rx_iv, const ngtcp2_crypto_cipher_ctx *rx_hp_ctx,
9787     const ngtcp2_crypto_aead_ctx *tx_aead_ctx, const uint8_t *tx_iv,
9788     const ngtcp2_crypto_cipher_ctx *tx_hp_ctx, size_t ivlen) {
9789   ngtcp2_pktns *pktns = conn->in_pktns;
9790   int rv;
9791 
9792   assert(ivlen >= 8);
9793   assert(pktns);
9794 
9795   conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.rx.hp_ctx);
9796   pktns->crypto.rx.hp_ctx.native_handle = NULL;
9797 
9798   if (pktns->crypto.rx.ckm) {
9799     conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.rx.ckm->aead_ctx);
9800     ngtcp2_crypto_km_del(pktns->crypto.rx.ckm, conn->mem);
9801     pktns->crypto.rx.ckm = NULL;
9802   }
9803 
9804   conn_call_delete_crypto_cipher_ctx(conn, &pktns->crypto.tx.hp_ctx);
9805   pktns->crypto.tx.hp_ctx.native_handle = NULL;
9806 
9807   if (pktns->crypto.tx.ckm) {
9808     conn_call_delete_crypto_aead_ctx(conn, &pktns->crypto.tx.ckm->aead_ctx);
9809     ngtcp2_crypto_km_del(pktns->crypto.tx.ckm, conn->mem);
9810     pktns->crypto.tx.ckm = NULL;
9811   }
9812 
9813   rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, NULL, 0, NULL, rx_iv, ivlen,
9814                             conn->mem);
9815   if (rv != 0) {
9816     return rv;
9817   }
9818 
9819   rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, NULL, 0, NULL, tx_iv, ivlen,
9820                             conn->mem);
9821   if (rv != 0) {
9822     return rv;
9823   }
9824 
9825   /* Take owner ship after we are sure that no failure occurs, so that
9826      caller can delete these contexts on failure. */
9827   pktns->crypto.rx.ckm->aead_ctx = *rx_aead_ctx;
9828   pktns->crypto.rx.hp_ctx = *rx_hp_ctx;
9829   pktns->crypto.tx.ckm->aead_ctx = *tx_aead_ctx;
9830   pktns->crypto.tx.hp_ctx = *tx_hp_ctx;
9831 
9832   return 0;
9833 }
9834 
ngtcp2_conn_install_rx_handshake_key(ngtcp2_conn * conn,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,size_t ivlen,const ngtcp2_crypto_cipher_ctx * hp_ctx)9835 int ngtcp2_conn_install_rx_handshake_key(
9836     ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *aead_ctx,
9837     const uint8_t *iv, size_t ivlen, const ngtcp2_crypto_cipher_ctx *hp_ctx) {
9838   ngtcp2_pktns *pktns = conn->hs_pktns;
9839   int rv;
9840 
9841   assert(ivlen >= 8);
9842   assert(pktns);
9843   assert(!pktns->crypto.rx.hp_ctx.native_handle);
9844   assert(!pktns->crypto.rx.ckm);
9845 
9846   rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, NULL, 0, aead_ctx, iv, ivlen,
9847                             conn->mem);
9848   if (rv != 0) {
9849     return rv;
9850   }
9851 
9852   pktns->crypto.rx.hp_ctx = *hp_ctx;
9853 
9854   return 0;
9855 }
9856 
ngtcp2_conn_install_tx_handshake_key(ngtcp2_conn * conn,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,size_t ivlen,const ngtcp2_crypto_cipher_ctx * hp_ctx)9857 int ngtcp2_conn_install_tx_handshake_key(
9858     ngtcp2_conn *conn, const ngtcp2_crypto_aead_ctx *aead_ctx,
9859     const uint8_t *iv, size_t ivlen, const ngtcp2_crypto_cipher_ctx *hp_ctx) {
9860   ngtcp2_pktns *pktns = conn->hs_pktns;
9861   int rv;
9862 
9863   assert(ivlen >= 8);
9864   assert(pktns);
9865   assert(!pktns->crypto.tx.hp_ctx.native_handle);
9866   assert(!pktns->crypto.tx.ckm);
9867 
9868   rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, NULL, 0, aead_ctx, iv, ivlen,
9869                             conn->mem);
9870   if (rv != 0) {
9871     return rv;
9872   }
9873 
9874   pktns->crypto.tx.hp_ctx = *hp_ctx;
9875 
9876   if (conn->server) {
9877     return ngtcp2_conn_commit_local_transport_params(conn);
9878   }
9879 
9880   return 0;
9881 }
9882 
ngtcp2_conn_install_early_key(ngtcp2_conn * conn,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,size_t ivlen,const ngtcp2_crypto_cipher_ctx * hp_ctx)9883 int ngtcp2_conn_install_early_key(ngtcp2_conn *conn,
9884                                   const ngtcp2_crypto_aead_ctx *aead_ctx,
9885                                   const uint8_t *iv, size_t ivlen,
9886                                   const ngtcp2_crypto_cipher_ctx *hp_ctx) {
9887   int rv;
9888 
9889   assert(ivlen >= 8);
9890   assert(!conn->early.hp_ctx.native_handle);
9891   assert(!conn->early.ckm);
9892 
9893   rv = ngtcp2_crypto_km_new(&conn->early.ckm, NULL, 0, aead_ctx, iv, ivlen,
9894                             conn->mem);
9895   if (rv != 0) {
9896     return rv;
9897   }
9898 
9899   conn->early.hp_ctx = *hp_ctx;
9900 
9901   conn->flags |= NGTCP2_CONN_FLAG_EARLY_KEY_INSTALLED;
9902 
9903   return 0;
9904 }
9905 
ngtcp2_conn_install_rx_key(ngtcp2_conn * conn,const uint8_t * secret,size_t secretlen,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,size_t ivlen,const ngtcp2_crypto_cipher_ctx * hp_ctx)9906 int ngtcp2_conn_install_rx_key(ngtcp2_conn *conn, const uint8_t *secret,
9907                                size_t secretlen,
9908                                const ngtcp2_crypto_aead_ctx *aead_ctx,
9909                                const uint8_t *iv, size_t ivlen,
9910                                const ngtcp2_crypto_cipher_ctx *hp_ctx) {
9911   ngtcp2_pktns *pktns = &conn->pktns;
9912   int rv;
9913 
9914   assert(ivlen >= 8);
9915   assert(!pktns->crypto.rx.hp_ctx.native_handle);
9916   assert(!pktns->crypto.rx.ckm);
9917 
9918   rv = ngtcp2_crypto_km_new(&pktns->crypto.rx.ckm, secret, secretlen, aead_ctx,
9919                             iv, ivlen, conn->mem);
9920   if (rv != 0) {
9921     return rv;
9922   }
9923 
9924   pktns->crypto.rx.hp_ctx = *hp_ctx;
9925 
9926   if (!conn->server) {
9927     conn->remote.transport_params = conn->remote.pending_transport_params;
9928     conn_sync_stream_id_limit(conn);
9929     conn->tx.max_offset = conn->remote.transport_params.initial_max_data;
9930 
9931     if (conn->early.ckm) {
9932       conn_discard_early_key(conn);
9933     }
9934   }
9935 
9936   return 0;
9937 }
9938 
ngtcp2_conn_install_tx_key(ngtcp2_conn * conn,const uint8_t * secret,size_t secretlen,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,size_t ivlen,const ngtcp2_crypto_cipher_ctx * hp_ctx)9939 int ngtcp2_conn_install_tx_key(ngtcp2_conn *conn, const uint8_t *secret,
9940                                size_t secretlen,
9941                                const ngtcp2_crypto_aead_ctx *aead_ctx,
9942                                const uint8_t *iv, size_t ivlen,
9943                                const ngtcp2_crypto_cipher_ctx *hp_ctx) {
9944   ngtcp2_pktns *pktns = &conn->pktns;
9945   int rv;
9946 
9947   assert(ivlen >= 8);
9948   assert(!pktns->crypto.tx.hp_ctx.native_handle);
9949   assert(!pktns->crypto.tx.ckm);
9950 
9951   rv = ngtcp2_crypto_km_new(&pktns->crypto.tx.ckm, secret, secretlen, aead_ctx,
9952                             iv, ivlen, conn->mem);
9953   if (rv != 0) {
9954     return rv;
9955   }
9956 
9957   pktns->crypto.tx.hp_ctx = *hp_ctx;
9958 
9959   if (conn->server) {
9960     conn->remote.transport_params = conn->remote.pending_transport_params;
9961     conn_sync_stream_id_limit(conn);
9962     conn->tx.max_offset = conn->remote.transport_params.initial_max_data;
9963   } else if (conn->early.ckm) {
9964     conn_discard_early_key(conn);
9965   }
9966 
9967   return 0;
9968 }
9969 
ngtcp2_conn_initiate_key_update(ngtcp2_conn * conn,ngtcp2_tstamp ts)9970 int ngtcp2_conn_initiate_key_update(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
9971   ngtcp2_tstamp confirmed_ts = conn->crypto.key_update.confirmed_ts;
9972   ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
9973 
9974   assert(conn->state == NGTCP2_CS_POST_HANDSHAKE);
9975 
9976   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) ||
9977       (conn->flags & NGTCP2_CONN_FLAG_KEY_UPDATE_NOT_CONFIRMED) ||
9978       !conn->crypto.key_update.new_tx_ckm ||
9979       !conn->crypto.key_update.new_rx_ckm ||
9980       (confirmed_ts != UINT64_MAX && confirmed_ts + 3 * pto > ts)) {
9981     return NGTCP2_ERR_INVALID_STATE;
9982   }
9983 
9984   conn_rotate_keys(conn, NGTCP2_MAX_PKT_NUM);
9985 
9986   return 0;
9987 }
9988 
9989 /*
9990  * conn_retire_stale_bound_dcid retires stale destination connection
9991  * ID in conn->dcid.bound to keep some unused destination connection
9992  * IDs available.
9993  *
9994  * This function returns 0 if it succeeds, or one of the following
9995  * negative error codes:
9996  *
9997  * NGTCP2_ERR_NOMEM
9998  *     Out of memory.
9999  */
conn_retire_stale_bound_dcid(ngtcp2_conn * conn,ngtcp2_duration timeout,ngtcp2_tstamp ts)10000 static int conn_retire_stale_bound_dcid(ngtcp2_conn *conn,
10001                                         ngtcp2_duration timeout,
10002                                         ngtcp2_tstamp ts) {
10003   size_t i;
10004   ngtcp2_dcid *dcid, *last;
10005   int rv;
10006 
10007   for (i = 0; i < ngtcp2_ringbuf_len(&conn->dcid.bound);) {
10008     dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
10009 
10010     assert(dcid->cid.datalen);
10011 
10012     if (dcid->bound_ts + timeout > ts) {
10013       ++i;
10014       continue;
10015     }
10016 
10017     rv = conn_retire_dcid_seq(conn, dcid->seq);
10018     if (rv != 0) {
10019       return rv;
10020     }
10021 
10022     if (i == 0) {
10023       ngtcp2_ringbuf_pop_front(&conn->dcid.bound);
10024       continue;
10025     }
10026 
10027     if (i == ngtcp2_ringbuf_len(&conn->dcid.bound) - 1) {
10028       ngtcp2_ringbuf_pop_back(&conn->dcid.bound);
10029       break;
10030     }
10031 
10032     last = ngtcp2_ringbuf_get(&conn->dcid.bound,
10033                               ngtcp2_ringbuf_len(&conn->dcid.bound) - 1);
10034     ngtcp2_dcid_copy(dcid, last);
10035     ngtcp2_ringbuf_pop_back(&conn->dcid.bound);
10036   }
10037 
10038   return 0;
10039 }
10040 
ngtcp2_conn_loss_detection_expiry(ngtcp2_conn * conn)10041 ngtcp2_tstamp ngtcp2_conn_loss_detection_expiry(ngtcp2_conn *conn) {
10042   return conn->cstat.loss_detection_timer;
10043 }
10044 
ngtcp2_conn_internal_expiry(ngtcp2_conn * conn)10045 ngtcp2_tstamp ngtcp2_conn_internal_expiry(ngtcp2_conn *conn) {
10046   ngtcp2_tstamp res = UINT64_MAX, t;
10047   ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
10048   ngtcp2_scid *scid;
10049   ngtcp2_dcid *dcid;
10050   size_t i, len;
10051 
10052   if (conn->pv) {
10053     res = ngtcp2_pv_next_expiry(conn->pv);
10054   }
10055 
10056   if (!ngtcp2_pq_empty(&conn->scid.used)) {
10057     scid = ngtcp2_struct_of(ngtcp2_pq_top(&conn->scid.used), ngtcp2_scid, pe);
10058     if (scid->retired_ts != UINT64_MAX) {
10059       res = ngtcp2_min(res, scid->retired_ts + pto);
10060     }
10061   }
10062 
10063   if (ngtcp2_ringbuf_len(&conn->dcid.retired)) {
10064     dcid = ngtcp2_ringbuf_get(&conn->dcid.retired, 0);
10065     res = ngtcp2_min(res, dcid->retired_ts + pto);
10066   }
10067 
10068   if (conn->dcid.current.cid.datalen) {
10069     len = ngtcp2_ringbuf_len(&conn->dcid.bound);
10070     for (i = 0; i < len; ++i) {
10071       dcid = ngtcp2_ringbuf_get(&conn->dcid.bound, i);
10072 
10073       assert(dcid->cid.datalen);
10074       assert(dcid->bound_ts != UINT64_MAX);
10075 
10076       res = ngtcp2_min(res, dcid->bound_ts + 3 * pto);
10077     }
10078   }
10079 
10080   if (conn->server && conn->early.ckm &&
10081       conn->early.discard_started_ts != UINT64_MAX) {
10082     t = conn->early.discard_started_ts + 3 * pto;
10083     res = ngtcp2_min(res, t);
10084   }
10085 
10086   return res;
10087 }
10088 
ngtcp2_conn_ack_delay_expiry(ngtcp2_conn * conn)10089 ngtcp2_tstamp ngtcp2_conn_ack_delay_expiry(ngtcp2_conn *conn) {
10090   ngtcp2_acktr *acktr = &conn->pktns.acktr;
10091 
10092   if (!(acktr->flags & NGTCP2_ACKTR_FLAG_CANCEL_TIMER) &&
10093       acktr->first_unacked_ts != UINT64_MAX) {
10094     return acktr->first_unacked_ts + conn_compute_ack_delay(conn);
10095   }
10096   return UINT64_MAX;
10097 }
10098 
ngtcp2_conn_get_expiry(ngtcp2_conn * conn)10099 ngtcp2_tstamp ngtcp2_conn_get_expiry(ngtcp2_conn *conn) {
10100   ngtcp2_tstamp t1 = ngtcp2_conn_loss_detection_expiry(conn);
10101   ngtcp2_tstamp t2 = ngtcp2_conn_ack_delay_expiry(conn);
10102   ngtcp2_tstamp t3 = ngtcp2_conn_internal_expiry(conn);
10103   ngtcp2_tstamp t4 = ngtcp2_conn_lost_pkt_expiry(conn);
10104   ngtcp2_tstamp t5 = conn_keep_alive_expiry(conn);
10105   ngtcp2_tstamp res = ngtcp2_min(t1, t2);
10106   res = ngtcp2_min(res, t3);
10107   res = ngtcp2_min(res, t4);
10108   res = ngtcp2_min(res, t5);
10109   return ngtcp2_min(res, conn->tx.pacing.next_ts);
10110 }
10111 
ngtcp2_conn_handle_expiry(ngtcp2_conn * conn,ngtcp2_tstamp ts)10112 int ngtcp2_conn_handle_expiry(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
10113   int rv;
10114   ngtcp2_duration pto = conn_compute_pto(conn, &conn->pktns);
10115 
10116   ngtcp2_conn_cancel_expired_ack_delay_timer(conn, ts);
10117 
10118   conn_cancel_expired_keep_alive_timer(conn, ts);
10119 
10120   conn_cancel_expired_pkt_tx_timer(conn, ts);
10121 
10122   ngtcp2_conn_remove_lost_pkt(conn, ts);
10123 
10124   if (conn->pv) {
10125     ngtcp2_pv_cancel_expired_timer(conn->pv, ts);
10126   }
10127 
10128   if (ngtcp2_conn_loss_detection_expiry(conn) <= ts) {
10129     rv = ngtcp2_conn_on_loss_detection_timer(conn, ts);
10130     if (rv != 0) {
10131       return rv;
10132     }
10133   }
10134 
10135   if (conn->dcid.current.cid.datalen) {
10136     rv = conn_retire_stale_bound_dcid(conn, 3 * pto, ts);
10137     if (rv != 0) {
10138       return rv;
10139     }
10140   }
10141 
10142   rv = conn_remove_retired_connection_id(conn, pto, ts);
10143   if (rv != 0) {
10144     return rv;
10145   }
10146 
10147   if (conn->server && conn->early.ckm &&
10148       conn->early.discard_started_ts != UINT64_MAX) {
10149     if (conn->early.discard_started_ts + 3 * pto <= ts) {
10150       conn_discard_early_key(conn);
10151     }
10152   }
10153 
10154   return 0;
10155 }
10156 
acktr_cancel_expired_ack_delay_timer(ngtcp2_acktr * acktr,ngtcp2_duration max_ack_delay,ngtcp2_tstamp ts)10157 static void acktr_cancel_expired_ack_delay_timer(ngtcp2_acktr *acktr,
10158                                                  ngtcp2_duration max_ack_delay,
10159                                                  ngtcp2_tstamp ts) {
10160   if (!(acktr->flags & NGTCP2_ACKTR_FLAG_CANCEL_TIMER) &&
10161       acktr->first_unacked_ts != UINT64_MAX &&
10162       acktr->first_unacked_ts + max_ack_delay <= ts) {
10163     acktr->flags |= NGTCP2_ACKTR_FLAG_CANCEL_TIMER;
10164   }
10165 }
10166 
ngtcp2_conn_cancel_expired_ack_delay_timer(ngtcp2_conn * conn,ngtcp2_tstamp ts)10167 void ngtcp2_conn_cancel_expired_ack_delay_timer(ngtcp2_conn *conn,
10168                                                 ngtcp2_tstamp ts) {
10169   ngtcp2_duration ack_delay = conn_compute_ack_delay(conn);
10170 
10171   if (conn->in_pktns) {
10172     acktr_cancel_expired_ack_delay_timer(&conn->in_pktns->acktr, 0, ts);
10173   }
10174   if (conn->hs_pktns) {
10175     acktr_cancel_expired_ack_delay_timer(&conn->hs_pktns->acktr, 0, ts);
10176   }
10177   acktr_cancel_expired_ack_delay_timer(&conn->pktns.acktr, ack_delay, ts);
10178 }
10179 
ngtcp2_conn_lost_pkt_expiry(ngtcp2_conn * conn)10180 ngtcp2_tstamp ngtcp2_conn_lost_pkt_expiry(ngtcp2_conn *conn) {
10181   ngtcp2_tstamp res = UINT64_MAX, ts;
10182 
10183   if (conn->in_pktns) {
10184     ts = ngtcp2_rtb_lost_pkt_ts(&conn->in_pktns->rtb);
10185     if (ts != UINT64_MAX) {
10186       ts += conn_compute_pto(conn, conn->in_pktns);
10187       res = ngtcp2_min(res, ts);
10188     }
10189   }
10190 
10191   if (conn->hs_pktns) {
10192     ts = ngtcp2_rtb_lost_pkt_ts(&conn->hs_pktns->rtb);
10193     if (ts != UINT64_MAX) {
10194       ts += conn_compute_pto(conn, conn->hs_pktns);
10195       res = ngtcp2_min(res, ts);
10196     }
10197   }
10198 
10199   ts = ngtcp2_rtb_lost_pkt_ts(&conn->pktns.rtb);
10200   if (ts != UINT64_MAX) {
10201     ts += conn_compute_pto(conn, &conn->pktns);
10202     res = ngtcp2_min(res, ts);
10203   }
10204 
10205   return res;
10206 }
10207 
ngtcp2_conn_remove_lost_pkt(ngtcp2_conn * conn,ngtcp2_tstamp ts)10208 void ngtcp2_conn_remove_lost_pkt(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
10209   ngtcp2_duration pto;
10210 
10211   if (conn->in_pktns) {
10212     pto = conn_compute_pto(conn, conn->in_pktns);
10213     ngtcp2_rtb_remove_expired_lost_pkt(&conn->in_pktns->rtb, pto, ts);
10214   }
10215   if (conn->hs_pktns) {
10216     pto = conn_compute_pto(conn, conn->hs_pktns);
10217     ngtcp2_rtb_remove_expired_lost_pkt(&conn->hs_pktns->rtb, pto, ts);
10218   }
10219   pto = conn_compute_pto(conn, &conn->pktns);
10220   ngtcp2_rtb_remove_expired_lost_pkt(&conn->pktns.rtb, pto, ts);
10221 }
10222 
10223 /*
10224  * conn_client_validate_transport_params validates |params| as client.
10225  * |params| must be sent with Encrypted Extensions.
10226  *
10227  * This function returns 0 if it succeeds, or one of the following
10228  * negative error codes:
10229  *
10230  * NGTCP2_ERR_PROTO
10231  *     Validation against either of original_dcid and retry_scid is
10232  *     failed.
10233  * NGTCP2_ERR_TRANSPORT_PARAM
10234  *     params contains preferred address but server chose zero-length
10235  *     connection ID.
10236  */
10237 static int
conn_client_validate_transport_params(ngtcp2_conn * conn,const ngtcp2_transport_params * params)10238 conn_client_validate_transport_params(ngtcp2_conn *conn,
10239                                       const ngtcp2_transport_params *params) {
10240   if (!ngtcp2_cid_eq(&conn->rcid, &params->original_dcid)) {
10241     return NGTCP2_ERR_TRANSPORT_PARAM;
10242   }
10243 
10244   if (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) {
10245     if (!params->retry_scid_present) {
10246       return NGTCP2_ERR_TRANSPORT_PARAM;
10247     }
10248     if (!ngtcp2_cid_eq(&conn->retry_scid, &params->retry_scid)) {
10249       return NGTCP2_ERR_TRANSPORT_PARAM;
10250     }
10251   } else if (params->retry_scid_present) {
10252     return NGTCP2_ERR_TRANSPORT_PARAM;
10253   }
10254 
10255   if (params->preferred_address_present &&
10256       conn->dcid.current.cid.datalen == 0) {
10257     return NGTCP2_ERR_TRANSPORT_PARAM;
10258   }
10259 
10260   return 0;
10261 }
10262 
ngtcp2_conn_set_remote_transport_params_versioned(ngtcp2_conn * conn,int transport_params_version,const ngtcp2_transport_params * params)10263 int ngtcp2_conn_set_remote_transport_params_versioned(
10264     ngtcp2_conn *conn, int transport_params_version,
10265     const ngtcp2_transport_params *params) {
10266   int rv;
10267   (void)transport_params_version;
10268 
10269   assert(!(conn->flags & NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED));
10270 
10271   /* Assume that ngtcp2_decode_transport_params sets default value if
10272      active_connection_id_limit is omitted. */
10273   if (params->active_connection_id_limit <
10274       NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT) {
10275     return NGTCP2_ERR_TRANSPORT_PARAM;
10276   }
10277 
10278   /* We assume that conn->dcid.current.cid is still the initial one.
10279      This requires that transport parameter must be fed into
10280      ngtcp2_conn as early as possible. */
10281   if (!ngtcp2_cid_eq(&conn->dcid.current.cid, &params->initial_scid)) {
10282     return NGTCP2_ERR_TRANSPORT_PARAM;
10283   }
10284 
10285   if (params->max_udp_payload_size < NGTCP2_MAX_UDP_PAYLOAD_SIZE) {
10286     return NGTCP2_ERR_TRANSPORT_PARAM;
10287   }
10288 
10289   if (!conn->server) {
10290     rv = conn_client_validate_transport_params(conn, params);
10291     if (rv != 0) {
10292       return rv;
10293     }
10294   }
10295 
10296   ngtcp2_log_remote_tp(&conn->log,
10297                        conn->server
10298                            ? NGTCP2_TRANSPORT_PARAMS_TYPE_CLIENT_HELLO
10299                            : NGTCP2_TRANSPORT_PARAMS_TYPE_ENCRYPTED_EXTENSIONS,
10300                        params);
10301 
10302   ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, params, conn->server,
10303                                               NGTCP2_QLOG_SIDE_REMOTE);
10304 
10305   if ((conn->server && conn->pktns.crypto.tx.ckm) ||
10306       (!conn->server && conn->pktns.crypto.rx.ckm)) {
10307     conn->remote.transport_params = *params;
10308     conn_sync_stream_id_limit(conn);
10309     conn->tx.max_offset = conn->remote.transport_params.initial_max_data;
10310   } else {
10311     conn->remote.pending_transport_params = *params;
10312   }
10313 
10314   conn->flags |= NGTCP2_CONN_FLAG_TRANSPORT_PARAM_RECVED;
10315 
10316   return 0;
10317 }
10318 
ngtcp2_conn_get_remote_transport_params_versioned(ngtcp2_conn * conn,int transport_params_version,ngtcp2_transport_params * params)10319 void ngtcp2_conn_get_remote_transport_params_versioned(
10320     ngtcp2_conn *conn, int transport_params_version,
10321     ngtcp2_transport_params *params) {
10322   (void)transport_params_version;
10323 
10324   if (conn->pktns.crypto.rx.ckm) {
10325     *params = conn->remote.transport_params;
10326   } else {
10327     *params = conn->remote.pending_transport_params;
10328   }
10329 }
10330 
ngtcp2_conn_set_early_remote_transport_params_versioned(ngtcp2_conn * conn,int transport_params_version,const ngtcp2_transport_params * params)10331 void ngtcp2_conn_set_early_remote_transport_params_versioned(
10332     ngtcp2_conn *conn, int transport_params_version,
10333     const ngtcp2_transport_params *params) {
10334   ngtcp2_transport_params *p = &conn->remote.transport_params;
10335   (void)transport_params_version;
10336 
10337   assert(!conn->server);
10338 
10339   memset(p, 0, sizeof(*p));
10340 
10341   p->initial_max_streams_bidi = params->initial_max_streams_bidi;
10342   p->initial_max_streams_uni = params->initial_max_streams_uni;
10343   p->initial_max_stream_data_bidi_local =
10344       params->initial_max_stream_data_bidi_local;
10345   p->initial_max_stream_data_bidi_remote =
10346       params->initial_max_stream_data_bidi_remote;
10347   p->initial_max_stream_data_uni = params->initial_max_stream_data_uni;
10348   p->initial_max_data = params->initial_max_data;
10349   p->active_connection_id_limit = params->active_connection_id_limit;
10350   p->max_idle_timeout = params->max_idle_timeout;
10351   p->max_udp_payload_size = params->max_udp_payload_size;
10352   p->disable_active_migration = params->disable_active_migration;
10353   p->max_datagram_frame_size = params->max_datagram_frame_size;
10354 
10355   /* These parameters are treated specially.  If server accepts early
10356      data, it must not set values for these parameters that are
10357      smaller than these remembered values. */
10358   conn->early.transport_params.initial_max_streams_bidi =
10359       params->initial_max_streams_bidi;
10360   conn->early.transport_params.initial_max_streams_uni =
10361       params->initial_max_streams_uni;
10362   conn->early.transport_params.initial_max_stream_data_bidi_local =
10363       params->initial_max_stream_data_bidi_local;
10364   conn->early.transport_params.initial_max_stream_data_bidi_remote =
10365       params->initial_max_stream_data_bidi_remote;
10366   conn->early.transport_params.initial_max_stream_data_uni =
10367       params->initial_max_stream_data_uni;
10368   conn->early.transport_params.initial_max_data = params->initial_max_data;
10369   conn->early.transport_params.active_connection_id_limit =
10370       params->active_connection_id_limit;
10371   conn->early.transport_params.max_datagram_frame_size =
10372       params->max_datagram_frame_size;
10373 
10374   conn_sync_stream_id_limit(conn);
10375 
10376   conn->tx.max_offset = p->initial_max_data;
10377 
10378   ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, p, conn->server,
10379                                               NGTCP2_QLOG_SIDE_REMOTE);
10380 }
10381 
ngtcp2_conn_set_local_transport_params_versioned(ngtcp2_conn * conn,int transport_params_version,const ngtcp2_transport_params * params)10382 int ngtcp2_conn_set_local_transport_params_versioned(
10383     ngtcp2_conn *conn, int transport_params_version,
10384     const ngtcp2_transport_params *params) {
10385   (void)transport_params_version;
10386 
10387   assert(conn->server);
10388   assert(params->active_connection_id_limit <= NGTCP2_MAX_DCID_POOL_SIZE);
10389 
10390   if (conn->hs_pktns == NULL || conn->hs_pktns->crypto.tx.ckm) {
10391     return NGTCP2_ERR_INVALID_STATE;
10392   }
10393 
10394   conn->local.transport_params = *params;
10395 
10396   return 0;
10397 }
10398 
ngtcp2_conn_commit_local_transport_params(ngtcp2_conn * conn)10399 int ngtcp2_conn_commit_local_transport_params(ngtcp2_conn *conn) {
10400   const ngtcp2_mem *mem = conn->mem;
10401   ngtcp2_transport_params *params = &conn->local.transport_params;
10402   ngtcp2_scid *scident;
10403   int rv;
10404 
10405   assert(1 == ngtcp2_ksl_len(&conn->scid.set));
10406 
10407   if (params->active_connection_id_limit == 0) {
10408     params->active_connection_id_limit =
10409         NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT;
10410   }
10411 
10412   params->initial_scid = conn->oscid;
10413 
10414   if (conn->oscid.datalen == 0) {
10415     params->preferred_address_present = 0;
10416   }
10417 
10418   if (conn->server && params->preferred_address_present) {
10419     scident = ngtcp2_mem_malloc(mem, sizeof(*scident));
10420     if (scident == NULL) {
10421       return NGTCP2_ERR_NOMEM;
10422     }
10423 
10424     ngtcp2_scid_init(scident, 1, &params->preferred_address.cid);
10425 
10426     rv = ngtcp2_ksl_insert(&conn->scid.set, NULL, &scident->cid, scident);
10427     if (rv != 0) {
10428       ngtcp2_mem_free(mem, scident);
10429       return rv;
10430     }
10431 
10432     conn->scid.last_seq = 1;
10433   }
10434 
10435   conn->rx.window = conn->rx.unsent_max_offset = conn->rx.max_offset =
10436       params->initial_max_data;
10437   conn->remote.bidi.unsent_max_streams = params->initial_max_streams_bidi;
10438   conn->remote.bidi.max_streams = params->initial_max_streams_bidi;
10439   conn->remote.uni.unsent_max_streams = params->initial_max_streams_uni;
10440   conn->remote.uni.max_streams = params->initial_max_streams_uni;
10441 
10442   conn->flags |= NGTCP2_CONN_FLAG_LOCAL_TRANSPORT_PARAMS_COMMITTED;
10443 
10444   ngtcp2_qlog_parameters_set_transport_params(&conn->qlog, params, conn->server,
10445                                               NGTCP2_QLOG_SIDE_LOCAL);
10446 
10447   return 0;
10448 }
10449 
ngtcp2_conn_get_local_transport_params_versioned(ngtcp2_conn * conn,int transport_params_version,ngtcp2_transport_params * params)10450 void ngtcp2_conn_get_local_transport_params_versioned(
10451     ngtcp2_conn *conn, int transport_params_version,
10452     ngtcp2_transport_params *params) {
10453   (void)transport_params_version;
10454 
10455   *params = conn->local.transport_params;
10456 }
10457 
ngtcp2_conn_open_bidi_stream(ngtcp2_conn * conn,int64_t * pstream_id,void * stream_user_data)10458 int ngtcp2_conn_open_bidi_stream(ngtcp2_conn *conn, int64_t *pstream_id,
10459                                  void *stream_user_data) {
10460   int rv;
10461   ngtcp2_strm *strm;
10462 
10463   if (ngtcp2_conn_get_streams_bidi_left(conn) == 0) {
10464     return NGTCP2_ERR_STREAM_ID_BLOCKED;
10465   }
10466 
10467   strm = ngtcp2_mem_malloc(conn->mem, sizeof(ngtcp2_strm));
10468   if (strm == NULL) {
10469     return NGTCP2_ERR_NOMEM;
10470   }
10471 
10472   rv = ngtcp2_conn_init_stream(conn, strm, conn->local.bidi.next_stream_id,
10473                                stream_user_data);
10474   if (rv != 0) {
10475     ngtcp2_mem_free(conn->mem, strm);
10476     return rv;
10477   }
10478 
10479   *pstream_id = conn->local.bidi.next_stream_id;
10480   conn->local.bidi.next_stream_id += 4;
10481 
10482   return 0;
10483 }
10484 
ngtcp2_conn_open_uni_stream(ngtcp2_conn * conn,int64_t * pstream_id,void * stream_user_data)10485 int ngtcp2_conn_open_uni_stream(ngtcp2_conn *conn, int64_t *pstream_id,
10486                                 void *stream_user_data) {
10487   int rv;
10488   ngtcp2_strm *strm;
10489 
10490   if (ngtcp2_conn_get_streams_uni_left(conn) == 0) {
10491     return NGTCP2_ERR_STREAM_ID_BLOCKED;
10492   }
10493 
10494   strm = ngtcp2_mem_malloc(conn->mem, sizeof(ngtcp2_strm));
10495   if (strm == NULL) {
10496     return NGTCP2_ERR_NOMEM;
10497   }
10498 
10499   rv = ngtcp2_conn_init_stream(conn, strm, conn->local.uni.next_stream_id,
10500                                stream_user_data);
10501   if (rv != 0) {
10502     ngtcp2_mem_free(conn->mem, strm);
10503     return rv;
10504   }
10505   ngtcp2_strm_shutdown(strm, NGTCP2_STRM_FLAG_SHUT_RD);
10506 
10507   *pstream_id = conn->local.uni.next_stream_id;
10508   conn->local.uni.next_stream_id += 4;
10509 
10510   return 0;
10511 }
10512 
ngtcp2_conn_find_stream(ngtcp2_conn * conn,int64_t stream_id)10513 ngtcp2_strm *ngtcp2_conn_find_stream(ngtcp2_conn *conn, int64_t stream_id) {
10514   return ngtcp2_map_find(&conn->strms, (uint64_t)stream_id);
10515 }
10516 
ngtcp2_conn_write_stream_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_ssize * pdatalen,uint32_t flags,int64_t stream_id,const uint8_t * data,size_t datalen,ngtcp2_tstamp ts)10517 ngtcp2_ssize ngtcp2_conn_write_stream_versioned(
10518     ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
10519     ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, ngtcp2_ssize *pdatalen,
10520     uint32_t flags, int64_t stream_id, const uint8_t *data, size_t datalen,
10521     ngtcp2_tstamp ts) {
10522   ngtcp2_vec datav;
10523 
10524   datav.len = datalen;
10525   datav.base = (uint8_t *)data;
10526 
10527   return ngtcp2_conn_writev_stream_versioned(conn, path, pkt_info_version, pi,
10528                                              dest, destlen, pdatalen, flags,
10529                                              stream_id, &datav, 1, ts);
10530 }
10531 
ngtcp2_conn_writev_stream_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_ssize * pdatalen,uint32_t flags,int64_t stream_id,const ngtcp2_vec * datav,size_t datavcnt,ngtcp2_tstamp ts)10532 ngtcp2_ssize ngtcp2_conn_writev_stream_versioned(
10533     ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
10534     ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, ngtcp2_ssize *pdatalen,
10535     uint32_t flags, int64_t stream_id, const ngtcp2_vec *datav, size_t datavcnt,
10536     ngtcp2_tstamp ts) {
10537   ngtcp2_vmsg vmsg, *pvmsg;
10538   ngtcp2_strm *strm;
10539   int64_t datalen;
10540 
10541   if (pdatalen) {
10542     *pdatalen = -1;
10543   }
10544 
10545   if (stream_id != -1) {
10546     strm = ngtcp2_conn_find_stream(conn, stream_id);
10547     if (strm == NULL) {
10548       return NGTCP2_ERR_STREAM_NOT_FOUND;
10549     }
10550 
10551     if (strm->flags & NGTCP2_STRM_FLAG_SHUT_WR) {
10552       return NGTCP2_ERR_STREAM_SHUT_WR;
10553     }
10554 
10555     datalen = ngtcp2_vec_len_varint(datav, datavcnt);
10556     if (datalen == -1) {
10557       return NGTCP2_ERR_INVALID_ARGUMENT;
10558     }
10559 
10560     if ((uint64_t)datalen > NGTCP2_MAX_VARINT - strm->tx.offset ||
10561         (uint64_t)datalen > NGTCP2_MAX_VARINT - conn->tx.offset) {
10562       return NGTCP2_ERR_INVALID_ARGUMENT;
10563     }
10564 
10565     vmsg.type = NGTCP2_VMSG_TYPE_STREAM;
10566     vmsg.stream.strm = strm;
10567     vmsg.stream.flags = flags;
10568     vmsg.stream.data = datav;
10569     vmsg.stream.datacnt = datavcnt;
10570     vmsg.stream.pdatalen = pdatalen;
10571 
10572     pvmsg = &vmsg;
10573   } else {
10574     pvmsg = NULL;
10575   }
10576 
10577   return ngtcp2_conn_write_vmsg(conn, path, pkt_info_version, pi, dest, destlen,
10578                                 pvmsg, ts);
10579 }
10580 
ngtcp2_conn_writev_datagram_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,int * paccepted,uint32_t flags,uint64_t dgram_id,const ngtcp2_vec * datav,size_t datavcnt,ngtcp2_tstamp ts)10581 ngtcp2_ssize ngtcp2_conn_writev_datagram_versioned(
10582     ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
10583     ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, int *paccepted,
10584     uint32_t flags, uint64_t dgram_id, const ngtcp2_vec *datav, size_t datavcnt,
10585     ngtcp2_tstamp ts) {
10586   ngtcp2_vmsg vmsg;
10587   int64_t datalen;
10588 
10589   if (paccepted) {
10590     *paccepted = 0;
10591   }
10592 
10593   if (conn->remote.transport_params.max_datagram_frame_size == 0) {
10594     return NGTCP2_ERR_INVALID_STATE;
10595   }
10596 
10597   datalen = ngtcp2_vec_len_varint(datav, datavcnt);
10598   if (datalen == -1 || (uint64_t)datalen > SIZE_MAX) {
10599     return NGTCP2_ERR_INVALID_STATE;
10600   }
10601 
10602   if (conn->remote.transport_params.max_datagram_frame_size <
10603       ngtcp2_pkt_datagram_framelen((size_t)datalen)) {
10604     return NGTCP2_ERR_INVALID_ARGUMENT;
10605   }
10606 
10607   vmsg.type = NGTCP2_VMSG_TYPE_DATAGRAM;
10608   vmsg.datagram.dgram_id = dgram_id;
10609   vmsg.datagram.flags = flags;
10610   vmsg.datagram.data = datav;
10611   vmsg.datagram.datacnt = datavcnt;
10612   vmsg.datagram.paccepted = paccepted;
10613 
10614   return ngtcp2_conn_write_vmsg(conn, path, pkt_info_version, pi, dest, destlen,
10615                                 &vmsg, ts);
10616 }
10617 
ngtcp2_conn_write_vmsg(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,ngtcp2_vmsg * vmsg,ngtcp2_tstamp ts)10618 ngtcp2_ssize ngtcp2_conn_write_vmsg(ngtcp2_conn *conn, ngtcp2_path *path,
10619                                     int pkt_info_version, ngtcp2_pkt_info *pi,
10620                                     uint8_t *dest, size_t destlen,
10621                                     ngtcp2_vmsg *vmsg, ngtcp2_tstamp ts) {
10622   ngtcp2_ssize nwrite;
10623   ngtcp2_pktns *pktns = &conn->pktns;
10624   size_t origlen;
10625   size_t origdestlen = destlen;
10626   int rv;
10627   uint8_t wflags = NGTCP2_WRITE_PKT_FLAG_NONE;
10628   int ppe_pending = (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) != 0;
10629   ngtcp2_conn_stat *cstat = &conn->cstat;
10630   ngtcp2_ssize res = 0;
10631   uint64_t server_tx_left;
10632   uint64_t datalen;
10633   uint64_t write_datalen = 0;
10634   int64_t prev_in_pkt_num = -1;
10635   ngtcp2_ksl_it it;
10636   ngtcp2_rtb_entry *rtbent;
10637   (void)pkt_info_version;
10638   (void)pktns;
10639 
10640   conn->log.last_ts = ts;
10641   conn->qlog.last_ts = ts;
10642 
10643   if (path) {
10644     ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
10645   }
10646 
10647   origlen = destlen =
10648       conn_shape_udp_payload(conn, &conn->dcid.current, destlen);
10649 
10650   if (!ppe_pending && pi) {
10651     pi->ecn = NGTCP2_ECN_NOT_ECT;
10652   }
10653 
10654   if (!conn_pacing_pkt_tx_allowed(conn, ts)) {
10655     return 0;
10656   }
10657 
10658   switch (conn->state) {
10659   case NGTCP2_CS_CLIENT_INITIAL:
10660   case NGTCP2_CS_CLIENT_WAIT_HANDSHAKE:
10661   case NGTCP2_CS_CLIENT_TLS_HANDSHAKE_FAILED:
10662     nwrite = conn_client_write_handshake(conn, pi, dest, destlen, vmsg, ts);
10663     if (nwrite < 0) {
10664       return nwrite;
10665     }
10666     if (conn->state != NGTCP2_CS_POST_HANDSHAKE) {
10667       return nwrite;
10668     }
10669 
10670     assert(nwrite);
10671     assert(dest[0] & NGTCP2_HEADER_FORM_BIT);
10672 
10673     if (ngtcp2_pkt_get_type_long(dest[0]) == NGTCP2_PKT_INITIAL) {
10674       /* We have added padding already, but in that case, there is no
10675          space left to write Short packet. */
10676       wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
10677     }
10678 
10679     res = nwrite;
10680     dest += nwrite;
10681     destlen -= (size_t)nwrite;
10682     /* Break here so that we can coalesces Short packets. */
10683     break;
10684   case NGTCP2_CS_SERVER_INITIAL:
10685   case NGTCP2_CS_SERVER_WAIT_HANDSHAKE:
10686   case NGTCP2_CS_SERVER_TLS_HANDSHAKE_FAILED:
10687     if (!ppe_pending) {
10688       if (!(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
10689         server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
10690         if (server_tx_left == 0) {
10691           if (cstat->loss_detection_timer != UINT64_MAX) {
10692             ngtcp2_log_info(
10693                 &conn->log, NGTCP2_LOG_EVENT_RCV,
10694                 "loss detection timer canceled due to amplification limit");
10695             cstat->loss_detection_timer = UINT64_MAX;
10696           }
10697 
10698           return 0;
10699         }
10700 
10701         destlen = (size_t)ngtcp2_min((uint64_t)destlen, server_tx_left);
10702       }
10703 
10704       if (vmsg) {
10705         switch (vmsg->type) {
10706         case NGTCP2_VMSG_TYPE_STREAM:
10707           datalen = ngtcp2_vec_len(vmsg->stream.data, vmsg->stream.datacnt);
10708           if (datalen == 0 || (datalen > 0 &&
10709                                (vmsg->stream.strm->tx.max_offset -
10710                                 vmsg->stream.strm->tx.offset) &&
10711                                (conn->tx.max_offset - conn->tx.offset))) {
10712             write_datalen =
10713                 conn_enforce_flow_control(conn, vmsg->stream.strm, datalen);
10714             write_datalen =
10715                 ngtcp2_min(write_datalen, NGTCP2_MIN_COALESCED_PAYLOADLEN);
10716             write_datalen += NGTCP2_STREAM_OVERHEAD;
10717           }
10718           break;
10719         case NGTCP2_VMSG_TYPE_DATAGRAM:
10720           write_datalen =
10721               ngtcp2_vec_len(vmsg->datagram.data, vmsg->datagram.datacnt) +
10722               NGTCP2_DATAGRAM_OVERHEAD;
10723           break;
10724         default:
10725           assert(0);
10726         }
10727 
10728         if (conn->in_pktns && write_datalen > 0) {
10729           it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
10730           if (!ngtcp2_ksl_it_end(&it)) {
10731             rtbent = ngtcp2_ksl_it_get(&it);
10732             prev_in_pkt_num = rtbent->hd.pkt_num;
10733           }
10734         }
10735       }
10736 
10737       nwrite = conn_write_handshake(conn, pi, dest, destlen, write_datalen, ts);
10738       if (nwrite < 0) {
10739         return nwrite;
10740       }
10741 
10742       res = nwrite;
10743       dest += nwrite;
10744       destlen -= (size_t)nwrite;
10745 
10746       if (conn->in_pktns && write_datalen > 0) {
10747         it = ngtcp2_rtb_head(&conn->in_pktns->rtb);
10748         if (!ngtcp2_ksl_it_end(&it)) {
10749           rtbent = ngtcp2_ksl_it_get(&it);
10750           if (rtbent->hd.pkt_num != prev_in_pkt_num &&
10751               (rtbent->flags & NGTCP2_RTB_ENTRY_FLAG_ACK_ELICITING)) {
10752             /* We have added padding already, but in that case, there
10753                is no space left to write Short packet. */
10754             wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
10755           }
10756         }
10757       }
10758     }
10759     if (conn->state != NGTCP2_CS_POST_HANDSHAKE &&
10760         conn->pktns.crypto.tx.ckm == NULL) {
10761       return res;
10762     }
10763     break;
10764   case NGTCP2_CS_POST_HANDSHAKE:
10765     break;
10766   case NGTCP2_CS_CLOSING:
10767     return NGTCP2_ERR_CLOSING;
10768   case NGTCP2_CS_DRAINING:
10769     return NGTCP2_ERR_DRAINING;
10770   default:
10771     return 0;
10772   }
10773 
10774   assert(pktns->crypto.tx.ckm);
10775 
10776   if (conn_check_pkt_num_exhausted(conn)) {
10777     return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
10778   }
10779 
10780   if (vmsg) {
10781     switch (vmsg->type) {
10782     case NGTCP2_VMSG_TYPE_STREAM:
10783       if (vmsg->stream.flags & NGTCP2_WRITE_STREAM_FLAG_MORE) {
10784         wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
10785       }
10786       break;
10787     case NGTCP2_VMSG_TYPE_DATAGRAM:
10788       if (vmsg->datagram.flags & NGTCP2_WRITE_DATAGRAM_FLAG_MORE) {
10789         wflags |= NGTCP2_WRITE_PKT_FLAG_MORE;
10790       }
10791       break;
10792     default:
10793       break;
10794     }
10795   }
10796 
10797   if (ppe_pending) {
10798     res = conn->pkt.hs_spktlen;
10799     conn->pkt.hs_spktlen = 0;
10800     if (conn->pkt.require_padding) {
10801       wflags |= NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING;
10802     }
10803     /* dest and destlen have already been adjusted in ppe in the first
10804        run.  They are adjusted for probe packet later. */
10805     nwrite = conn_write_pkt(conn, pi, dest, destlen, vmsg, NGTCP2_PKT_SHORT,
10806                             wflags, ts);
10807     goto fin;
10808   } else {
10809     conn->pkt.require_padding =
10810         (wflags & NGTCP2_WRITE_PKT_FLAG_REQUIRE_PADDING);
10811 
10812     if (conn->state == NGTCP2_CS_POST_HANDSHAKE) {
10813       rv = conn_prepare_key_update(conn, ts);
10814       if (rv != 0) {
10815         return rv;
10816       }
10817     }
10818 
10819     if (!conn->pktns.rtb.probe_pkt_left && conn_cwnd_is_zero(conn)) {
10820       destlen = 0;
10821     } else {
10822       if (res == 0) {
10823         nwrite =
10824             conn_write_path_response(conn, path, pi, dest, origdestlen, ts);
10825         if (nwrite) {
10826           goto fin;
10827         }
10828 
10829         if (conn->pv) {
10830           nwrite =
10831               conn_write_path_challenge(conn, path, pi, dest, origdestlen, ts);
10832           if (nwrite) {
10833             goto fin;
10834           }
10835         }
10836       }
10837 
10838       if (conn->server &&
10839           !(conn->dcid.current.flags & NGTCP2_DCID_FLAG_PATH_VALIDATED)) {
10840         server_tx_left = conn_server_tx_left(conn, &conn->dcid.current);
10841         origlen = (size_t)ngtcp2_min((uint64_t)origlen, server_tx_left);
10842         destlen = (size_t)ngtcp2_min((uint64_t)destlen, server_tx_left);
10843 
10844         if (server_tx_left == 0 &&
10845             conn->cstat.loss_detection_timer != UINT64_MAX) {
10846           ngtcp2_log_info(
10847               &conn->log, NGTCP2_LOG_EVENT_RCV,
10848               "loss detection timer canceled due to amplification limit");
10849           conn->cstat.loss_detection_timer = UINT64_MAX;
10850         }
10851       }
10852     }
10853   }
10854 
10855   if (res == 0) {
10856     if (conn_handshake_remnants_left(conn)) {
10857       if (conn_handshake_probe_left(conn)) {
10858         destlen = origlen;
10859       }
10860       nwrite = conn_write_handshake_pkts(conn, pi, dest, destlen,
10861                                          /* write_datalen = */ 0, ts);
10862       if (nwrite < 0) {
10863         return nwrite;
10864       }
10865       if (nwrite > 0) {
10866         res = nwrite;
10867         dest += nwrite;
10868         destlen -= (size_t)nwrite;
10869       }
10870     }
10871   }
10872 
10873   if (conn->pktns.rtb.probe_pkt_left) {
10874     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_CON,
10875                     "transmit probe pkt left=%zu",
10876                     conn->pktns.rtb.probe_pkt_left);
10877 
10878     nwrite = conn_write_pkt(conn, pi, dest, destlen, vmsg, NGTCP2_PKT_SHORT,
10879                             wflags, ts);
10880 
10881     goto fin;
10882   }
10883 
10884   nwrite = conn_write_pkt(conn, pi, dest, destlen, vmsg, NGTCP2_PKT_SHORT,
10885                           wflags, ts);
10886   if (nwrite) {
10887     assert(nwrite != NGTCP2_ERR_NOBUF);
10888     goto fin;
10889   }
10890 
10891   if (res == 0) {
10892     nwrite = conn_write_ack_pkt(conn, pi, dest, origlen, NGTCP2_PKT_SHORT, ts);
10893   }
10894 
10895 fin:
10896   conn->pkt.hs_spktlen = 0;
10897 
10898   if (nwrite >= 0) {
10899     res += nwrite;
10900     return res;
10901   }
10902   /* NGTCP2_CONN_FLAG_PPE_PENDING is set in conn_write_pkt above.
10903      ppe_pending cannot be used here. */
10904   if (conn->flags & NGTCP2_CONN_FLAG_PPE_PENDING) {
10905     conn->pkt.hs_spktlen = res;
10906   }
10907 
10908   return nwrite;
10909 }
10910 
10911 static ngtcp2_ssize
conn_write_connection_close(ngtcp2_conn * conn,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint8_t pkt_type,uint64_t error_code,ngtcp2_tstamp ts)10912 conn_write_connection_close(ngtcp2_conn *conn, ngtcp2_pkt_info *pi,
10913                             uint8_t *dest, size_t destlen, uint8_t pkt_type,
10914                             uint64_t error_code, ngtcp2_tstamp ts) {
10915   ngtcp2_pktns *in_pktns = conn->in_pktns;
10916   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
10917   ngtcp2_ssize res = 0, nwrite;
10918   ngtcp2_frame fr;
10919 
10920   fr.type = NGTCP2_FRAME_CONNECTION_CLOSE;
10921   fr.connection_close.error_code = error_code;
10922   fr.connection_close.frame_type = 0;
10923   fr.connection_close.reasonlen = 0;
10924   fr.connection_close.reason = NULL;
10925 
10926   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) &&
10927       pkt_type != NGTCP2_PKT_INITIAL) {
10928     if (in_pktns && conn->server) {
10929       nwrite = ngtcp2_conn_write_single_frame_pkt(
10930           conn, pi, dest, destlen, NGTCP2_PKT_INITIAL, &conn->dcid.current.cid,
10931           &fr, NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
10932       if (nwrite < 0) {
10933         return nwrite;
10934       }
10935 
10936       dest += nwrite;
10937       destlen -= (size_t)nwrite;
10938       res += nwrite;
10939     }
10940 
10941     if (pkt_type != NGTCP2_PKT_HANDSHAKE && hs_pktns &&
10942         hs_pktns->crypto.tx.ckm) {
10943       nwrite = ngtcp2_conn_write_single_frame_pkt(
10944           conn, pi, dest, destlen, NGTCP2_PKT_HANDSHAKE,
10945           &conn->dcid.current.cid, &fr, NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
10946       if (nwrite < 0) {
10947         return nwrite;
10948       }
10949 
10950       dest += nwrite;
10951       destlen -= (size_t)nwrite;
10952       res += nwrite;
10953     }
10954   }
10955 
10956   nwrite = ngtcp2_conn_write_single_frame_pkt(
10957       conn, pi, dest, destlen, pkt_type, &conn->dcid.current.cid, &fr,
10958       NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
10959 
10960   if (nwrite < 0) {
10961     return nwrite;
10962   }
10963 
10964   res += nwrite;
10965 
10966   if (res == 0) {
10967     return NGTCP2_ERR_NOBUF;
10968   }
10969 
10970   return res;
10971 }
10972 
ngtcp2_conn_write_connection_close_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint64_t error_code,ngtcp2_tstamp ts)10973 ngtcp2_ssize ngtcp2_conn_write_connection_close_versioned(
10974     ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
10975     ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, uint64_t error_code,
10976     ngtcp2_tstamp ts) {
10977   ngtcp2_pktns *in_pktns = conn->in_pktns;
10978   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
10979   uint8_t pkt_type;
10980   ngtcp2_ssize nwrite;
10981   (void)pkt_info_version;
10982 
10983   conn->log.last_ts = ts;
10984   conn->qlog.last_ts = ts;
10985 
10986   if (conn_check_pkt_num_exhausted(conn)) {
10987     return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
10988   }
10989 
10990   switch (conn->state) {
10991   case NGTCP2_CS_CLIENT_INITIAL:
10992   case NGTCP2_CS_CLOSING:
10993   case NGTCP2_CS_DRAINING:
10994     return NGTCP2_ERR_INVALID_STATE;
10995   default:
10996     break;
10997   }
10998 
10999   if (path) {
11000     ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
11001   }
11002 
11003   if (pi) {
11004     pi->ecn = NGTCP2_ECN_NOT_ECT;
11005   }
11006 
11007   if (conn->state == NGTCP2_CS_POST_HANDSHAKE ||
11008       (conn->server && conn->pktns.crypto.tx.ckm)) {
11009     pkt_type = NGTCP2_PKT_SHORT;
11010   } else if (hs_pktns && hs_pktns->crypto.tx.ckm) {
11011     pkt_type = NGTCP2_PKT_HANDSHAKE;
11012   } else if (in_pktns && in_pktns->crypto.tx.ckm) {
11013     pkt_type = NGTCP2_PKT_INITIAL;
11014   } else {
11015     /* This branch is taken if server has not read any Initial packet
11016        from client. */
11017     return NGTCP2_ERR_INVALID_STATE;
11018   }
11019 
11020   nwrite = conn_write_connection_close(conn, pi, dest, destlen, pkt_type,
11021                                        error_code, ts);
11022   if (nwrite < 0) {
11023     return nwrite;
11024   }
11025 
11026   conn->state = NGTCP2_CS_CLOSING;
11027 
11028   return nwrite;
11029 }
11030 
ngtcp2_conn_write_application_close_versioned(ngtcp2_conn * conn,ngtcp2_path * path,int pkt_info_version,ngtcp2_pkt_info * pi,uint8_t * dest,size_t destlen,uint64_t app_error_code,ngtcp2_tstamp ts)11031 ngtcp2_ssize ngtcp2_conn_write_application_close_versioned(
11032     ngtcp2_conn *conn, ngtcp2_path *path, int pkt_info_version,
11033     ngtcp2_pkt_info *pi, uint8_t *dest, size_t destlen, uint64_t app_error_code,
11034     ngtcp2_tstamp ts) {
11035   ngtcp2_ssize nwrite;
11036   ngtcp2_ssize res = 0;
11037   ngtcp2_frame fr;
11038   (void)pkt_info_version;
11039 
11040   conn->log.last_ts = ts;
11041   conn->qlog.last_ts = ts;
11042 
11043   if (conn_check_pkt_num_exhausted(conn)) {
11044     return NGTCP2_ERR_PKT_NUM_EXHAUSTED;
11045   }
11046 
11047   switch (conn->state) {
11048   case NGTCP2_CS_CLIENT_INITIAL:
11049   case NGTCP2_CS_CLOSING:
11050   case NGTCP2_CS_DRAINING:
11051     return NGTCP2_ERR_INVALID_STATE;
11052   default:
11053     break;
11054   }
11055 
11056   if (path) {
11057     ngtcp2_path_copy(path, &conn->dcid.current.ps.path);
11058   }
11059 
11060   if (pi) {
11061     pi->ecn = NGTCP2_ECN_NOT_ECT;
11062   }
11063 
11064   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)) {
11065     nwrite = conn_write_connection_close(conn, pi, dest, destlen,
11066                                          conn->hs_pktns->crypto.tx.ckm
11067                                              ? NGTCP2_PKT_HANDSHAKE
11068                                              : NGTCP2_PKT_INITIAL,
11069                                          NGTCP2_APPLICATION_ERROR, ts);
11070     if (nwrite < 0) {
11071       return nwrite;
11072     }
11073     res = nwrite;
11074     dest += nwrite;
11075     destlen -= (size_t)nwrite;
11076   }
11077 
11078   if (conn->state != NGTCP2_CS_POST_HANDSHAKE) {
11079     assert(res);
11080 
11081     if (!conn->server || !conn->pktns.crypto.tx.ckm) {
11082       return res;
11083     }
11084   }
11085 
11086   assert(conn->pktns.crypto.tx.ckm);
11087 
11088   fr.type = NGTCP2_FRAME_CONNECTION_CLOSE_APP;
11089   fr.connection_close.error_code = app_error_code;
11090   fr.connection_close.frame_type = 0;
11091   fr.connection_close.reasonlen = 0;
11092   fr.connection_close.reason = NULL;
11093 
11094   nwrite = ngtcp2_conn_write_single_frame_pkt(
11095       conn, pi, dest, destlen, NGTCP2_PKT_SHORT, &conn->dcid.current.cid, &fr,
11096       NGTCP2_RTB_ENTRY_FLAG_NONE, NULL, ts);
11097 
11098   if (nwrite < 0) {
11099     return nwrite;
11100   }
11101 
11102   res += nwrite;
11103 
11104   if (res == 0) {
11105     return NGTCP2_ERR_NOBUF;
11106   }
11107 
11108   conn->state = NGTCP2_CS_CLOSING;
11109 
11110   return res;
11111 }
11112 
ngtcp2_conn_is_in_closing_period(ngtcp2_conn * conn)11113 int ngtcp2_conn_is_in_closing_period(ngtcp2_conn *conn) {
11114   return conn->state == NGTCP2_CS_CLOSING;
11115 }
11116 
ngtcp2_conn_is_in_draining_period(ngtcp2_conn * conn)11117 int ngtcp2_conn_is_in_draining_period(ngtcp2_conn *conn) {
11118   return conn->state == NGTCP2_CS_DRAINING;
11119 }
11120 
ngtcp2_conn_close_stream(ngtcp2_conn * conn,ngtcp2_strm * strm)11121 int ngtcp2_conn_close_stream(ngtcp2_conn *conn, ngtcp2_strm *strm) {
11122   int rv;
11123 
11124   rv = ngtcp2_map_remove(&conn->strms, (ngtcp2_map_key_type)strm->stream_id);
11125   if (rv != 0) {
11126     assert(rv != NGTCP2_ERR_INVALID_ARGUMENT);
11127     return rv;
11128   }
11129 
11130   rv = conn_call_stream_close(conn, strm);
11131   if (rv != 0) {
11132     goto fin;
11133   }
11134 
11135   if (ngtcp2_strm_is_tx_queued(strm)) {
11136     ngtcp2_pq_remove(&conn->tx.strmq, &strm->pe);
11137   }
11138 
11139 fin:
11140   ngtcp2_strm_free(strm);
11141   ngtcp2_mem_free(conn->mem, strm);
11142 
11143   return rv;
11144 }
11145 
ngtcp2_conn_close_stream_if_shut_rdwr(ngtcp2_conn * conn,ngtcp2_strm * strm)11146 int ngtcp2_conn_close_stream_if_shut_rdwr(ngtcp2_conn *conn,
11147                                           ngtcp2_strm *strm) {
11148   if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RDWR) ==
11149           NGTCP2_STRM_FLAG_SHUT_RDWR &&
11150       ((strm->flags & NGTCP2_STRM_FLAG_RECV_RST) ||
11151        ngtcp2_strm_rx_offset(strm) == strm->rx.last_offset) &&
11152       (((strm->flags & NGTCP2_STRM_FLAG_SENT_RST) &&
11153         (strm->flags & NGTCP2_STRM_FLAG_RST_ACKED)) ||
11154        (!(strm->flags & NGTCP2_STRM_FLAG_SENT_RST) &&
11155         ngtcp2_strm_is_all_tx_data_acked(strm)))) {
11156     return ngtcp2_conn_close_stream(conn, strm);
11157   }
11158   return 0;
11159 }
11160 
11161 /*
11162  * conn_shutdown_stream_write closes send stream with error code
11163  * |app_error_code|.  RESET_STREAM frame is scheduled.
11164  *
11165  * This function returns 0 if it succeeds, or one of the following
11166  * negative error codes:
11167  *
11168  * NGTCP2_ERR_NOMEM
11169  *     Out of memory.
11170  */
conn_shutdown_stream_write(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t app_error_code)11171 static int conn_shutdown_stream_write(ngtcp2_conn *conn, ngtcp2_strm *strm,
11172                                       uint64_t app_error_code) {
11173   if (strm->flags & NGTCP2_STRM_FLAG_SENT_RST) {
11174     return 0;
11175   }
11176 
11177   /* Set this flag so that we don't accidentally send DATA to this
11178      stream. */
11179   strm->flags |= NGTCP2_STRM_FLAG_SHUT_WR | NGTCP2_STRM_FLAG_SENT_RST;
11180   ngtcp2_strm_set_app_error_code(strm, app_error_code);
11181 
11182   ngtcp2_strm_streamfrq_clear(strm);
11183 
11184   return conn_reset_stream(conn, strm, app_error_code);
11185 }
11186 
11187 /*
11188  * conn_shutdown_stream_read closes read stream with error code
11189  * |app_error_code|.  STOP_SENDING frame is scheduled.
11190  *
11191  * This function returns 0 if it succeeds, or one of the following
11192  * negative error codes:
11193  *
11194  * NGTCP2_ERR_NOMEM
11195  *     Out of memory.
11196  */
conn_shutdown_stream_read(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t app_error_code)11197 static int conn_shutdown_stream_read(ngtcp2_conn *conn, ngtcp2_strm *strm,
11198                                      uint64_t app_error_code) {
11199   if (strm->flags & NGTCP2_STRM_FLAG_STOP_SENDING) {
11200     return 0;
11201   }
11202   if ((strm->flags & NGTCP2_STRM_FLAG_SHUT_RD) &&
11203       ngtcp2_strm_rx_offset(strm) == strm->rx.last_offset) {
11204     return 0;
11205   }
11206 
11207   /* Extend connection flow control window for the amount of data
11208      which are not passed to application. */
11209   if (!(strm->flags &
11210         (NGTCP2_STRM_FLAG_STOP_SENDING | NGTCP2_STRM_FLAG_RECV_RST))) {
11211     ngtcp2_conn_extend_max_offset(conn, strm->rx.last_offset -
11212                                             ngtcp2_strm_rx_offset(strm));
11213   }
11214 
11215   strm->flags |= NGTCP2_STRM_FLAG_STOP_SENDING;
11216   ngtcp2_strm_set_app_error_code(strm, app_error_code);
11217 
11218   return conn_stop_sending(conn, strm, app_error_code);
11219 }
11220 
ngtcp2_conn_shutdown_stream(ngtcp2_conn * conn,int64_t stream_id,uint64_t app_error_code)11221 int ngtcp2_conn_shutdown_stream(ngtcp2_conn *conn, int64_t stream_id,
11222                                 uint64_t app_error_code) {
11223   int rv;
11224   ngtcp2_strm *strm;
11225 
11226   strm = ngtcp2_conn_find_stream(conn, stream_id);
11227   if (strm == NULL) {
11228     return NGTCP2_ERR_STREAM_NOT_FOUND;
11229   }
11230 
11231   rv = conn_shutdown_stream_read(conn, strm, app_error_code);
11232   if (rv != 0) {
11233     return rv;
11234   }
11235 
11236   rv = conn_shutdown_stream_write(conn, strm, app_error_code);
11237   if (rv != 0) {
11238     return rv;
11239   }
11240 
11241   return 0;
11242 }
11243 
ngtcp2_conn_shutdown_stream_write(ngtcp2_conn * conn,int64_t stream_id,uint64_t app_error_code)11244 int ngtcp2_conn_shutdown_stream_write(ngtcp2_conn *conn, int64_t stream_id,
11245                                       uint64_t app_error_code) {
11246   ngtcp2_strm *strm;
11247 
11248   strm = ngtcp2_conn_find_stream(conn, stream_id);
11249   if (strm == NULL) {
11250     return NGTCP2_ERR_STREAM_NOT_FOUND;
11251   }
11252 
11253   return conn_shutdown_stream_write(conn, strm, app_error_code);
11254 }
11255 
ngtcp2_conn_shutdown_stream_read(ngtcp2_conn * conn,int64_t stream_id,uint64_t app_error_code)11256 int ngtcp2_conn_shutdown_stream_read(ngtcp2_conn *conn, int64_t stream_id,
11257                                      uint64_t app_error_code) {
11258   ngtcp2_strm *strm;
11259 
11260   strm = ngtcp2_conn_find_stream(conn, stream_id);
11261   if (strm == NULL) {
11262     return NGTCP2_ERR_STREAM_NOT_FOUND;
11263   }
11264 
11265   return conn_shutdown_stream_read(conn, strm, app_error_code);
11266 }
11267 
11268 /*
11269  * conn_extend_max_stream_offset extends stream level flow control
11270  * window by |datalen| of the stream denoted by |strm|.
11271  *
11272  * This function returns 0 if it succeeds, or one of the following
11273  * negative error codes:
11274  *
11275  * NGTCP2_ERR_NOMEM
11276  *     Out of memory.
11277  */
conn_extend_max_stream_offset(ngtcp2_conn * conn,ngtcp2_strm * strm,uint64_t datalen)11278 static int conn_extend_max_stream_offset(ngtcp2_conn *conn, ngtcp2_strm *strm,
11279                                          uint64_t datalen) {
11280   ngtcp2_strm *top;
11281 
11282   if (datalen > NGTCP2_MAX_VARINT ||
11283       strm->rx.unsent_max_offset > NGTCP2_MAX_VARINT - datalen) {
11284     strm->rx.unsent_max_offset = NGTCP2_MAX_VARINT;
11285   } else {
11286     strm->rx.unsent_max_offset += datalen;
11287   }
11288 
11289   if (!(strm->flags &
11290         (NGTCP2_STRM_FLAG_SHUT_RD | NGTCP2_STRM_FLAG_STOP_SENDING)) &&
11291       !ngtcp2_strm_is_tx_queued(strm) &&
11292       conn_should_send_max_stream_data(conn, strm)) {
11293     if (!ngtcp2_pq_empty(&conn->tx.strmq)) {
11294       top = ngtcp2_conn_tx_strmq_top(conn);
11295       strm->cycle = top->cycle;
11296     }
11297     strm->cycle = conn_tx_strmq_first_cycle(conn);
11298     return ngtcp2_conn_tx_strmq_push(conn, strm);
11299   }
11300 
11301   return 0;
11302 }
11303 
ngtcp2_conn_extend_max_stream_offset(ngtcp2_conn * conn,int64_t stream_id,uint64_t datalen)11304 int ngtcp2_conn_extend_max_stream_offset(ngtcp2_conn *conn, int64_t stream_id,
11305                                          uint64_t datalen) {
11306   ngtcp2_strm *strm;
11307 
11308   strm = ngtcp2_conn_find_stream(conn, stream_id);
11309   if (strm == NULL) {
11310     return NGTCP2_ERR_STREAM_NOT_FOUND;
11311   }
11312 
11313   return conn_extend_max_stream_offset(conn, strm, datalen);
11314 }
11315 
ngtcp2_conn_extend_max_offset(ngtcp2_conn * conn,uint64_t datalen)11316 void ngtcp2_conn_extend_max_offset(ngtcp2_conn *conn, uint64_t datalen) {
11317   if (NGTCP2_MAX_VARINT < datalen ||
11318       conn->rx.unsent_max_offset > NGTCP2_MAX_VARINT - datalen) {
11319     conn->rx.unsent_max_offset = NGTCP2_MAX_VARINT;
11320     return;
11321   }
11322 
11323   conn->rx.unsent_max_offset += datalen;
11324 }
11325 
ngtcp2_conn_extend_max_streams_bidi(ngtcp2_conn * conn,size_t n)11326 void ngtcp2_conn_extend_max_streams_bidi(ngtcp2_conn *conn, size_t n) {
11327   handle_max_remote_streams_extension(&conn->remote.bidi.unsent_max_streams, n);
11328 }
11329 
ngtcp2_conn_extend_max_streams_uni(ngtcp2_conn * conn,size_t n)11330 void ngtcp2_conn_extend_max_streams_uni(ngtcp2_conn *conn, size_t n) {
11331   handle_max_remote_streams_extension(&conn->remote.uni.unsent_max_streams, n);
11332 }
11333 
ngtcp2_conn_get_dcid(ngtcp2_conn * conn)11334 const ngtcp2_cid *ngtcp2_conn_get_dcid(ngtcp2_conn *conn) {
11335   return &conn->dcid.current.cid;
11336 }
11337 
ngtcp2_conn_get_client_initial_dcid(ngtcp2_conn * conn)11338 const ngtcp2_cid *ngtcp2_conn_get_client_initial_dcid(ngtcp2_conn *conn) {
11339   return &conn->rcid;
11340 }
11341 
ngtcp2_conn_get_negotiated_version(ngtcp2_conn * conn)11342 uint32_t ngtcp2_conn_get_negotiated_version(ngtcp2_conn *conn) {
11343   return conn->version;
11344 }
11345 
delete_strms_pq_each(void * data,void * ptr)11346 static int delete_strms_pq_each(void *data, void *ptr) {
11347   ngtcp2_conn *conn = ptr;
11348   ngtcp2_strm *s = data;
11349 
11350   if (ngtcp2_strm_is_tx_queued(s)) {
11351     ngtcp2_pq_remove(&conn->tx.strmq, &s->pe);
11352   }
11353 
11354   ngtcp2_strm_free(s);
11355   ngtcp2_mem_free(conn->mem, s);
11356 
11357   return 0;
11358 }
11359 
11360 /*
11361  * conn_discard_early_data_state discards any connection states which
11362  * are altered by any operations during early data transfer.
11363  */
conn_discard_early_data_state(ngtcp2_conn * conn)11364 static void conn_discard_early_data_state(ngtcp2_conn *conn) {
11365   ngtcp2_frame_chain **pfrc, *frc;
11366 
11367   ngtcp2_rtb_remove_early_data(&conn->pktns.rtb, &conn->cstat);
11368 
11369   ngtcp2_map_each_free(&conn->strms, delete_strms_pq_each, conn);
11370   ngtcp2_map_clear(&conn->strms);
11371 
11372   conn->tx.offset = 0;
11373 
11374   conn->rx.unsent_max_offset = conn->rx.max_offset =
11375       conn->local.transport_params.initial_max_data;
11376 
11377   conn->remote.bidi.unsent_max_streams = conn->remote.bidi.max_streams =
11378       conn->local.transport_params.initial_max_streams_bidi;
11379 
11380   conn->remote.uni.unsent_max_streams = conn->remote.uni.max_streams =
11381       conn->local.transport_params.initial_max_streams_uni;
11382 
11383   if (conn->server) {
11384     conn->local.bidi.next_stream_id = 1;
11385     conn->local.uni.next_stream_id = 3;
11386   } else {
11387     conn->local.bidi.next_stream_id = 0;
11388     conn->local.uni.next_stream_id = 2;
11389   }
11390 
11391   for (pfrc = &conn->pktns.tx.frq; *pfrc;) {
11392     frc = *pfrc;
11393     *pfrc = (*pfrc)->next;
11394     ngtcp2_frame_chain_del(frc, conn->mem);
11395   }
11396 }
11397 
ngtcp2_conn_early_data_rejected(ngtcp2_conn * conn)11398 int ngtcp2_conn_early_data_rejected(ngtcp2_conn *conn) {
11399   conn->flags |= NGTCP2_CONN_FLAG_EARLY_DATA_REJECTED;
11400 
11401   conn_discard_early_data_state(conn);
11402 
11403   return 0;
11404 }
11405 
ngtcp2_conn_update_rtt(ngtcp2_conn * conn,ngtcp2_duration rtt,ngtcp2_duration ack_delay,ngtcp2_tstamp ts)11406 void ngtcp2_conn_update_rtt(ngtcp2_conn *conn, ngtcp2_duration rtt,
11407                             ngtcp2_duration ack_delay, ngtcp2_tstamp ts) {
11408   ngtcp2_conn_stat *cstat = &conn->cstat;
11409   ngtcp2_duration min_rtt;
11410 
11411   cstat->latest_rtt = rtt;
11412 
11413   if (cstat->min_rtt == UINT64_MAX) {
11414     cstat->min_rtt = rtt;
11415     cstat->smoothed_rtt = rtt;
11416     cstat->rttvar = rtt / 2;
11417     cstat->first_rtt_sample_ts = ts;
11418   } else {
11419     min_rtt = ngtcp2_min(cstat->min_rtt, rtt);
11420     if (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) {
11421       ack_delay =
11422           ngtcp2_min(ack_delay, conn->remote.transport_params.max_ack_delay);
11423     } else if (ack_delay > 0 && rtt < cstat->min_rtt + ack_delay) {
11424       /* Ignore RTT sample if adjusting ack_delay causes the sample
11425          less than min_rtt before handshake confirmation. */
11426       ngtcp2_log_info(
11427           &conn->log, NGTCP2_LOG_EVENT_RCV,
11428           "ignore rtt sample because ack_delay is too large latest_rtt=%" PRIu64
11429           " min_rtt=%" PRIu64 " ack_delay=%" PRIu64,
11430           (uint64_t)(rtt / NGTCP2_MILLISECONDS),
11431           (uint64_t)(cstat->min_rtt / NGTCP2_MILLISECONDS),
11432           (uint64_t)(ack_delay / NGTCP2_MILLISECONDS));
11433       return;
11434     }
11435 
11436     if (rtt > min_rtt + ack_delay) {
11437       rtt -= ack_delay;
11438     }
11439 
11440     cstat->min_rtt = min_rtt;
11441     cstat->rttvar = (cstat->rttvar * 3 + (cstat->smoothed_rtt < rtt
11442                                               ? rtt - cstat->smoothed_rtt
11443                                               : cstat->smoothed_rtt - rtt)) /
11444                     4;
11445     cstat->smoothed_rtt = (cstat->smoothed_rtt * 7 + rtt) / 8;
11446   }
11447 
11448   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV,
11449                   "latest_rtt=%" PRIu64 " min_rtt=%" PRIu64
11450                   " smoothed_rtt=%" PRIu64 " rttvar=%" PRIu64
11451                   " ack_delay=%" PRIu64,
11452                   (uint64_t)(cstat->latest_rtt / NGTCP2_MILLISECONDS),
11453                   (uint64_t)(cstat->min_rtt / NGTCP2_MILLISECONDS),
11454                   cstat->smoothed_rtt / NGTCP2_MILLISECONDS,
11455                   cstat->rttvar / NGTCP2_MILLISECONDS,
11456                   (uint64_t)(ack_delay / NGTCP2_MILLISECONDS));
11457 }
11458 
ngtcp2_conn_get_conn_stat_versioned(ngtcp2_conn * conn,int conn_stat_version,ngtcp2_conn_stat * cstat)11459 void ngtcp2_conn_get_conn_stat_versioned(ngtcp2_conn *conn,
11460                                          int conn_stat_version,
11461                                          ngtcp2_conn_stat *cstat) {
11462   (void)conn_stat_version;
11463 
11464   *cstat = conn->cstat;
11465 }
11466 
conn_get_earliest_pktns(ngtcp2_conn * conn,ngtcp2_tstamp * pts,const ngtcp2_tstamp * times)11467 static ngtcp2_pktns *conn_get_earliest_pktns(ngtcp2_conn *conn,
11468                                              ngtcp2_tstamp *pts,
11469                                              const ngtcp2_tstamp *times) {
11470   ngtcp2_pktns *ns[] = {conn->in_pktns, conn->hs_pktns, &conn->pktns};
11471   ngtcp2_pktns *res = NULL;
11472   size_t i;
11473   ngtcp2_tstamp earliest_ts = UINT64_MAX;
11474 
11475   for (i = NGTCP2_PKTNS_ID_INITIAL; i < NGTCP2_PKTNS_ID_MAX; ++i) {
11476     if (ns[i] == NULL || ns[i]->rtb.num_retransmittable == 0 ||
11477         (times[i] == UINT64_MAX ||
11478          (earliest_ts != UINT64_MAX && times[i] >= earliest_ts) ||
11479          (i == NGTCP2_PKTNS_ID_APPLICATION &&
11480           !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
11481       continue;
11482     }
11483 
11484     earliest_ts = times[i];
11485     res = ns[i];
11486   }
11487 
11488   if (res == NULL && !conn->server) {
11489     if (conn->hs_pktns && conn->hs_pktns->crypto.tx.ckm) {
11490       res = conn->hs_pktns;
11491     } else {
11492       res = conn->in_pktns;
11493     }
11494   }
11495 
11496   if (pts) {
11497     *pts = earliest_ts;
11498   }
11499   return res;
11500 }
11501 
conn_get_earliest_pto_expiry(ngtcp2_conn * conn,const ngtcp2_tstamp * times,size_t pto_count,ngtcp2_tstamp ts)11502 static ngtcp2_tstamp conn_get_earliest_pto_expiry(ngtcp2_conn *conn,
11503                                                   const ngtcp2_tstamp *times,
11504                                                   size_t pto_count,
11505                                                   ngtcp2_tstamp ts) {
11506   ngtcp2_pktns *ns[] = {conn->in_pktns, conn->hs_pktns, &conn->pktns};
11507   size_t i;
11508   ngtcp2_tstamp earliest_ts = UINT64_MAX, t;
11509   ngtcp2_conn_stat *cstat = &conn->cstat;
11510   ngtcp2_duration duration =
11511       compute_pto(cstat->smoothed_rtt, cstat->rttvar, /* max_ack_delay = */ 0) *
11512       (1ULL << pto_count);
11513 
11514   for (i = NGTCP2_PKTNS_ID_INITIAL; i < NGTCP2_PKTNS_ID_MAX; ++i) {
11515     if (ns[i] == NULL || ns[i]->rtb.num_retransmittable == 0 ||
11516         (times[i] == UINT64_MAX ||
11517          (i == NGTCP2_PKTNS_ID_APPLICATION &&
11518           !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
11519       continue;
11520     }
11521 
11522     t = times[i] + duration;
11523 
11524     if (i == NGTCP2_PKTNS_ID_APPLICATION) {
11525       t += conn->remote.transport_params.max_ack_delay * (1ULL << pto_count);
11526     }
11527 
11528     if (t < earliest_ts) {
11529       earliest_ts = t;
11530     }
11531   }
11532 
11533   if (earliest_ts == UINT64_MAX) {
11534     return ts + duration;
11535   }
11536 
11537   return earliest_ts;
11538 }
11539 
ngtcp2_conn_set_loss_detection_timer(ngtcp2_conn * conn,ngtcp2_tstamp ts)11540 void ngtcp2_conn_set_loss_detection_timer(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11541   ngtcp2_conn_stat *cstat = &conn->cstat;
11542   ngtcp2_duration timeout;
11543   ngtcp2_pktns *in_pktns = conn->in_pktns;
11544   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
11545   ngtcp2_pktns *pktns = &conn->pktns;
11546   ngtcp2_tstamp earliest_loss_time;
11547 
11548   conn_get_earliest_pktns(conn, &earliest_loss_time, cstat->loss_time);
11549 
11550   if (earliest_loss_time != UINT64_MAX) {
11551     cstat->loss_detection_timer = earliest_loss_time;
11552 
11553     ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV,
11554                     "loss_detection_timer=%" PRIu64 " nonzero crypto loss time",
11555                     cstat->loss_detection_timer);
11556     return;
11557   }
11558 
11559   if ((!in_pktns || in_pktns->rtb.num_retransmittable == 0) &&
11560       (!hs_pktns || hs_pktns->rtb.num_retransmittable == 0) &&
11561       (pktns->rtb.num_retransmittable == 0 ||
11562        !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)) &&
11563       (conn->server ||
11564        (conn->flags & (NGTCP2_CONN_FLAG_SERVER_ADDR_VERIFIED |
11565                        NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED)))) {
11566     if (cstat->loss_detection_timer != UINT64_MAX) {
11567       ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV,
11568                       "loss detection timer canceled");
11569       cstat->loss_detection_timer = UINT64_MAX;
11570       cstat->pto_count = 0;
11571     }
11572     return;
11573   }
11574 
11575   cstat->loss_detection_timer = conn_get_earliest_pto_expiry(
11576       conn, cstat->last_tx_pkt_ts, cstat->pto_count, ts);
11577 
11578   timeout =
11579       cstat->loss_detection_timer > ts ? cstat->loss_detection_timer - ts : 0;
11580 
11581   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV,
11582                   "loss_detection_timer=%" PRIu64 " timeout=%" PRIu64,
11583                   cstat->loss_detection_timer,
11584                   (uint64_t)(timeout / NGTCP2_MILLISECONDS));
11585 }
11586 
ngtcp2_conn_on_loss_detection_timer(ngtcp2_conn * conn,ngtcp2_tstamp ts)11587 int ngtcp2_conn_on_loss_detection_timer(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
11588   ngtcp2_conn_stat *cstat = &conn->cstat;
11589   int rv;
11590   ngtcp2_pktns *in_pktns = conn->in_pktns;
11591   ngtcp2_pktns *hs_pktns = conn->hs_pktns;
11592   ngtcp2_tstamp earliest_loss_time;
11593   ngtcp2_pktns *loss_pktns =
11594       conn_get_earliest_pktns(conn, &earliest_loss_time, cstat->loss_time);
11595 
11596   conn->log.last_ts = ts;
11597   conn->qlog.last_ts = ts;
11598 
11599   switch (conn->state) {
11600   case NGTCP2_CS_CLOSING:
11601   case NGTCP2_CS_DRAINING:
11602     cstat->loss_detection_timer = UINT64_MAX;
11603     cstat->pto_count = 0;
11604     return 0;
11605   default:
11606     break;
11607   }
11608 
11609   if (cstat->loss_detection_timer == UINT64_MAX) {
11610     return 0;
11611   }
11612 
11613   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV,
11614                   "loss detection timer fired");
11615 
11616   if (earliest_loss_time != UINT64_MAX) {
11617     rv = ngtcp2_conn_detect_lost_pkt(conn, loss_pktns, cstat, ts);
11618     if (rv != 0) {
11619       return rv;
11620     }
11621     ngtcp2_conn_set_loss_detection_timer(conn, ts);
11622     return 0;
11623   }
11624 
11625   if (!conn->server && !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)) {
11626     if (hs_pktns->crypto.tx.ckm) {
11627       hs_pktns->rtb.probe_pkt_left = 1;
11628     } else {
11629       in_pktns->rtb.probe_pkt_left = 1;
11630     }
11631   } else {
11632     if (in_pktns && in_pktns->rtb.num_retransmittable) {
11633       in_pktns->rtb.probe_pkt_left = 1;
11634 
11635       assert(hs_pktns);
11636 
11637       if (conn->server && hs_pktns->rtb.num_retransmittable) {
11638         /* let server coalesce packets */
11639         hs_pktns->rtb.probe_pkt_left = 1;
11640       }
11641     } else if (hs_pktns && hs_pktns->rtb.num_retransmittable) {
11642       hs_pktns->rtb.probe_pkt_left = 1;
11643     } else {
11644       conn->pktns.rtb.probe_pkt_left = 2;
11645     }
11646   }
11647 
11648   ++cstat->pto_count;
11649 
11650   ngtcp2_log_info(&conn->log, NGTCP2_LOG_EVENT_RCV, "pto_count=%zu",
11651                   cstat->pto_count);
11652 
11653   ngtcp2_conn_set_loss_detection_timer(conn, ts);
11654 
11655   return 0;
11656 }
11657 
conn_buffer_crypto_data(ngtcp2_conn * conn,const uint8_t ** pdata,ngtcp2_pktns * pktns,const uint8_t * data,size_t datalen)11658 static int conn_buffer_crypto_data(ngtcp2_conn *conn, const uint8_t **pdata,
11659                                    ngtcp2_pktns *pktns, const uint8_t *data,
11660                                    size_t datalen) {
11661   int rv;
11662   ngtcp2_buf_chain **pbufchain = &pktns->crypto.tx.data;
11663 
11664   if (*pbufchain) {
11665     for (; (*pbufchain)->next; pbufchain = &(*pbufchain)->next)
11666       ;
11667 
11668     if (ngtcp2_buf_left(&(*pbufchain)->buf) < datalen) {
11669       pbufchain = &(*pbufchain)->next;
11670     }
11671   }
11672 
11673   if (!*pbufchain) {
11674     rv = ngtcp2_buf_chain_new(pbufchain, ngtcp2_max(1024, datalen), conn->mem);
11675     if (rv != 0) {
11676       return rv;
11677     }
11678   }
11679 
11680   *pdata = (*pbufchain)->buf.last;
11681   (*pbufchain)->buf.last = ngtcp2_cpymem((*pbufchain)->buf.last, data, datalen);
11682 
11683   return 0;
11684 }
11685 
ngtcp2_conn_submit_crypto_data(ngtcp2_conn * conn,ngtcp2_crypto_level crypto_level,const uint8_t * data,const size_t datalen)11686 int ngtcp2_conn_submit_crypto_data(ngtcp2_conn *conn,
11687                                    ngtcp2_crypto_level crypto_level,
11688                                    const uint8_t *data, const size_t datalen) {
11689   ngtcp2_pktns *pktns;
11690   ngtcp2_frame_chain *frc;
11691   ngtcp2_crypto *fr;
11692   int rv;
11693 
11694   if (datalen == 0) {
11695     return 0;
11696   }
11697 
11698   switch (crypto_level) {
11699   case NGTCP2_CRYPTO_LEVEL_INITIAL:
11700     assert(conn->in_pktns);
11701     pktns = conn->in_pktns;
11702     break;
11703   case NGTCP2_CRYPTO_LEVEL_HANDSHAKE:
11704     assert(conn->hs_pktns);
11705     pktns = conn->hs_pktns;
11706     break;
11707   case NGTCP2_CRYPTO_LEVEL_APPLICATION:
11708     pktns = &conn->pktns;
11709     break;
11710   default:
11711     return NGTCP2_ERR_INVALID_ARGUMENT;
11712   }
11713 
11714   rv = conn_buffer_crypto_data(conn, &data, pktns, data, datalen);
11715   if (rv != 0) {
11716     return rv;
11717   }
11718 
11719   rv = ngtcp2_frame_chain_new(&frc, conn->mem);
11720   if (rv != 0) {
11721     return rv;
11722   }
11723 
11724   fr = &frc->fr.crypto;
11725 
11726   fr->type = NGTCP2_FRAME_CRYPTO;
11727   fr->offset = pktns->crypto.tx.offset;
11728   fr->datacnt = 1;
11729   fr->data[0].len = datalen;
11730   fr->data[0].base = (uint8_t *)data;
11731 
11732   rv = ngtcp2_ksl_insert(&pktns->crypto.tx.frq, NULL, &fr->offset, frc);
11733   if (rv != 0) {
11734     ngtcp2_frame_chain_del(frc, conn->mem);
11735     return rv;
11736   }
11737 
11738   pktns->crypto.strm.tx.offset += datalen;
11739   pktns->crypto.tx.offset += datalen;
11740 
11741   return 0;
11742 }
11743 
ngtcp2_conn_submit_new_token(ngtcp2_conn * conn,const uint8_t * token,size_t tokenlen)11744 int ngtcp2_conn_submit_new_token(ngtcp2_conn *conn, const uint8_t *token,
11745                                  size_t tokenlen) {
11746   int rv;
11747   ngtcp2_frame_chain *nfrc;
11748   ngtcp2_vec tokenv = {(uint8_t *)token, tokenlen};
11749 
11750   assert(conn->server);
11751   assert(token);
11752   assert(tokenlen);
11753 
11754   rv = ngtcp2_frame_chain_new_token_new(&nfrc, &tokenv, conn->mem);
11755   if (rv != 0) {
11756     return rv;
11757   }
11758 
11759   nfrc->next = conn->pktns.tx.frq;
11760   conn->pktns.tx.frq = nfrc;
11761 
11762   return 0;
11763 }
11764 
ngtcp2_conn_tx_strmq_top(ngtcp2_conn * conn)11765 ngtcp2_strm *ngtcp2_conn_tx_strmq_top(ngtcp2_conn *conn) {
11766   assert(!ngtcp2_pq_empty(&conn->tx.strmq));
11767   return ngtcp2_struct_of(ngtcp2_pq_top(&conn->tx.strmq), ngtcp2_strm, pe);
11768 }
11769 
ngtcp2_conn_tx_strmq_pop(ngtcp2_conn * conn)11770 void ngtcp2_conn_tx_strmq_pop(ngtcp2_conn *conn) {
11771   ngtcp2_strm *strm = ngtcp2_conn_tx_strmq_top(conn);
11772   assert(strm);
11773   ngtcp2_pq_pop(&conn->tx.strmq);
11774   strm->pe.index = NGTCP2_PQ_BAD_INDEX;
11775 }
11776 
ngtcp2_conn_tx_strmq_push(ngtcp2_conn * conn,ngtcp2_strm * strm)11777 int ngtcp2_conn_tx_strmq_push(ngtcp2_conn *conn, ngtcp2_strm *strm) {
11778   return ngtcp2_pq_push(&conn->tx.strmq, &strm->pe);
11779 }
11780 
conn_has_uncommited_preferred_address_cid(ngtcp2_conn * conn)11781 static int conn_has_uncommited_preferred_address_cid(ngtcp2_conn *conn) {
11782   return conn->server &&
11783          !(conn->flags & NGTCP2_CONN_FLAG_LOCAL_TRANSPORT_PARAMS_COMMITTED) &&
11784          conn->oscid.datalen &&
11785          conn->local.transport_params.preferred_address_present;
11786 }
11787 
ngtcp2_conn_get_num_scid(ngtcp2_conn * conn)11788 size_t ngtcp2_conn_get_num_scid(ngtcp2_conn *conn) {
11789   return ngtcp2_ksl_len(&conn->scid.set) +
11790          (size_t)conn_has_uncommited_preferred_address_cid(conn);
11791 }
11792 
ngtcp2_conn_get_scid(ngtcp2_conn * conn,ngtcp2_cid * dest)11793 size_t ngtcp2_conn_get_scid(ngtcp2_conn *conn, ngtcp2_cid *dest) {
11794   ngtcp2_cid *origdest = dest;
11795   ngtcp2_ksl_it it;
11796   ngtcp2_scid *scid;
11797 
11798   for (it = ngtcp2_ksl_begin(&conn->scid.set); !ngtcp2_ksl_it_end(&it);
11799        ngtcp2_ksl_it_next(&it)) {
11800     scid = ngtcp2_ksl_it_get(&it);
11801     *dest++ = scid->cid;
11802   }
11803 
11804   if (conn_has_uncommited_preferred_address_cid(conn)) {
11805     *dest++ = conn->local.transport_params.preferred_address.cid;
11806   }
11807 
11808   return (size_t)(dest - origdest);
11809 }
11810 
ngtcp2_conn_get_num_active_dcid(ngtcp2_conn * conn)11811 size_t ngtcp2_conn_get_num_active_dcid(ngtcp2_conn *conn) {
11812   size_t n = 1; /* for conn->dcid.current */
11813   ngtcp2_pv *pv = conn->pv;
11814 
11815   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED)) {
11816     return 0;
11817   }
11818 
11819   if (pv) {
11820     if (pv->dcid.seq != conn->dcid.current.seq) {
11821       ++n;
11822     }
11823     if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
11824         pv->fallback_dcid.seq != conn->dcid.current.seq &&
11825         pv->fallback_dcid.seq != pv->dcid.seq) {
11826       ++n;
11827     }
11828   }
11829 
11830   n += ngtcp2_ringbuf_len(&conn->dcid.retired);
11831 
11832   return n;
11833 }
11834 
copy_dcid_to_cid_token(ngtcp2_cid_token * dest,const ngtcp2_dcid * src)11835 static void copy_dcid_to_cid_token(ngtcp2_cid_token *dest,
11836                                    const ngtcp2_dcid *src) {
11837   dest->seq = src->seq;
11838   dest->cid = src->cid;
11839   ngtcp2_path_storage_init2(&dest->ps, &src->ps.path);
11840   if ((dest->token_present =
11841            (src->flags & NGTCP2_DCID_FLAG_TOKEN_PRESENT) != 0)) {
11842     memcpy(dest->token, src->token, NGTCP2_STATELESS_RESET_TOKENLEN);
11843   }
11844 }
11845 
ngtcp2_conn_get_active_dcid(ngtcp2_conn * conn,ngtcp2_cid_token * dest)11846 size_t ngtcp2_conn_get_active_dcid(ngtcp2_conn *conn, ngtcp2_cid_token *dest) {
11847   ngtcp2_pv *pv = conn->pv;
11848   ngtcp2_cid_token *orig = dest;
11849   ngtcp2_dcid *dcid;
11850   size_t len, i;
11851 
11852   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED_HANDLED)) {
11853     return 0;
11854   }
11855 
11856   copy_dcid_to_cid_token(dest, &conn->dcid.current);
11857   ++dest;
11858 
11859   if (pv) {
11860     if (pv->dcid.seq != conn->dcid.current.seq) {
11861       copy_dcid_to_cid_token(dest, &pv->dcid);
11862       ++dest;
11863     }
11864     if ((pv->flags & NGTCP2_PV_FLAG_FALLBACK_ON_FAILURE) &&
11865         pv->fallback_dcid.seq != conn->dcid.current.seq &&
11866         pv->fallback_dcid.seq != pv->dcid.seq) {
11867       copy_dcid_to_cid_token(dest, &pv->fallback_dcid);
11868       ++dest;
11869     }
11870   }
11871 
11872   len = ngtcp2_ringbuf_len(&conn->dcid.retired);
11873   for (i = 0; i < len; ++i) {
11874     dcid = ngtcp2_ringbuf_get(&conn->dcid.retired, i);
11875     copy_dcid_to_cid_token(dest, dcid);
11876     ++dest;
11877   }
11878 
11879   return (size_t)(dest - orig);
11880 }
11881 
ngtcp2_conn_set_local_addr(ngtcp2_conn * conn,const ngtcp2_addr * addr)11882 void ngtcp2_conn_set_local_addr(ngtcp2_conn *conn, const ngtcp2_addr *addr) {
11883   ngtcp2_addr *dest = &conn->dcid.current.ps.path.local;
11884 
11885   assert(addr->addrlen <= sizeof(conn->dcid.current.ps.local_addrbuf));
11886   ngtcp2_addr_copy(dest, addr);
11887 }
11888 
ngtcp2_conn_set_path_user_data(ngtcp2_conn * conn,void * path_user_data)11889 void ngtcp2_conn_set_path_user_data(ngtcp2_conn *conn, void *path_user_data) {
11890   conn->dcid.current.ps.path.user_data = path_user_data;
11891 }
11892 
ngtcp2_conn_get_path_max_udp_payload_size(ngtcp2_conn * conn)11893 size_t ngtcp2_conn_get_path_max_udp_payload_size(ngtcp2_conn *conn) {
11894   if (conn->local.settings.no_udp_payload_size_shaping) {
11895     return conn->local.settings.max_udp_payload_size;
11896   }
11897 
11898   return ngtcp2_min(conn->local.settings.max_udp_payload_size,
11899                     conn->dcid.current.max_udp_payload_size);
11900 }
11901 
ngtcp2_conn_get_path(ngtcp2_conn * conn)11902 const ngtcp2_path *ngtcp2_conn_get_path(ngtcp2_conn *conn) {
11903   return &conn->dcid.current.ps.path;
11904 }
11905 
conn_initiate_migration_precheck(ngtcp2_conn * conn,const ngtcp2_addr * local_addr)11906 static int conn_initiate_migration_precheck(ngtcp2_conn *conn,
11907                                             const ngtcp2_addr *local_addr) {
11908   if (conn->remote.transport_params.disable_active_migration ||
11909       conn->dcid.current.cid.datalen == 0 ||
11910       !(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_CONFIRMED) ||
11911       (conn->pv && (conn->pv->flags & NGTCP2_PV_FLAG_PREFERRED_ADDR))) {
11912     return NGTCP2_ERR_INVALID_STATE;
11913   }
11914 
11915   if (ngtcp2_ringbuf_len(&conn->dcid.unused) == 0) {
11916     return NGTCP2_ERR_CONN_ID_BLOCKED;
11917   }
11918 
11919   if (ngtcp2_addr_eq(&conn->dcid.current.ps.path.local, local_addr)) {
11920     return NGTCP2_ERR_INVALID_ARGUMENT;
11921   }
11922 
11923   return 0;
11924 }
11925 
ngtcp2_conn_initiate_immediate_migration(ngtcp2_conn * conn,const ngtcp2_path * path,ngtcp2_tstamp ts)11926 int ngtcp2_conn_initiate_immediate_migration(ngtcp2_conn *conn,
11927                                              const ngtcp2_path *path,
11928                                              ngtcp2_tstamp ts) {
11929   int rv;
11930   ngtcp2_dcid *dcid;
11931 
11932   assert(!conn->server);
11933 
11934   conn->log.last_ts = ts;
11935   conn->qlog.last_ts = ts;
11936 
11937   rv = conn_initiate_migration_precheck(conn, &path->local);
11938   if (rv != 0) {
11939     return rv;
11940   }
11941 
11942   if (conn->pv) {
11943     rv = conn_abort_pv(conn, ts);
11944     if (rv != 0) {
11945       return rv;
11946     }
11947   }
11948 
11949   rv = conn_retire_dcid(conn, &conn->dcid.current, ts);
11950   if (rv != 0) {
11951     return rv;
11952   }
11953 
11954   dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
11955   ngtcp2_dcid_set_path(dcid, path);
11956 
11957   ngtcp2_dcid_copy(&conn->dcid.current, dcid);
11958   ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
11959 
11960   rv = conn_call_activate_dcid(conn, &conn->dcid.current);
11961   if (rv != 0) {
11962     return rv;
11963   }
11964 
11965   conn_reset_congestion_state(conn, ts);
11966   conn_reset_ecn_validation_state(conn);
11967 
11968   return 0;
11969 }
11970 
ngtcp2_conn_initiate_migration(ngtcp2_conn * conn,const ngtcp2_path * path,ngtcp2_tstamp ts)11971 int ngtcp2_conn_initiate_migration(ngtcp2_conn *conn, const ngtcp2_path *path,
11972                                    ngtcp2_tstamp ts) {
11973   int rv;
11974   ngtcp2_dcid *dcid;
11975   ngtcp2_duration pto, initial_pto, timeout;
11976   ngtcp2_pv *pv;
11977 
11978   assert(!conn->server);
11979 
11980   conn->log.last_ts = ts;
11981   conn->qlog.last_ts = ts;
11982 
11983   rv = conn_initiate_migration_precheck(conn, &path->local);
11984   if (rv != 0) {
11985     return rv;
11986   }
11987 
11988   if (conn->pv) {
11989     rv = conn_abort_pv(conn, ts);
11990     if (rv != 0) {
11991       return rv;
11992     }
11993   }
11994 
11995   dcid = ngtcp2_ringbuf_get(&conn->dcid.unused, 0);
11996   ngtcp2_dcid_set_path(dcid, path);
11997 
11998   pto = conn_compute_pto(conn, &conn->pktns);
11999   initial_pto = conn_compute_initial_pto(conn, &conn->pktns);
12000   timeout = 3 * ngtcp2_max(pto, initial_pto);
12001 
12002   rv = ngtcp2_pv_new(&pv, dcid, timeout, NGTCP2_PV_FLAG_NONE, &conn->log,
12003                      conn->mem);
12004   if (rv != 0) {
12005     return rv;
12006   }
12007 
12008   ngtcp2_ringbuf_pop_front(&conn->dcid.unused);
12009   conn->pv = pv;
12010 
12011   return conn_call_activate_dcid(conn, &pv->dcid);
12012 }
12013 
ngtcp2_conn_get_max_local_streams_uni(ngtcp2_conn * conn)12014 uint64_t ngtcp2_conn_get_max_local_streams_uni(ngtcp2_conn *conn) {
12015   return conn->local.uni.max_streams;
12016 }
12017 
ngtcp2_conn_get_max_data_left(ngtcp2_conn * conn)12018 uint64_t ngtcp2_conn_get_max_data_left(ngtcp2_conn *conn) {
12019   return conn->tx.max_offset - conn->tx.offset;
12020 }
12021 
ngtcp2_conn_get_streams_bidi_left(ngtcp2_conn * conn)12022 uint64_t ngtcp2_conn_get_streams_bidi_left(ngtcp2_conn *conn) {
12023   uint64_t n = ngtcp2_ord_stream_id(conn->local.bidi.next_stream_id);
12024 
12025   return n > conn->local.bidi.max_streams
12026              ? 0
12027              : conn->local.bidi.max_streams - n + 1;
12028 }
12029 
ngtcp2_conn_get_streams_uni_left(ngtcp2_conn * conn)12030 uint64_t ngtcp2_conn_get_streams_uni_left(ngtcp2_conn *conn) {
12031   uint64_t n = ngtcp2_ord_stream_id(conn->local.uni.next_stream_id);
12032 
12033   return n > conn->local.uni.max_streams ? 0
12034                                          : conn->local.uni.max_streams - n + 1;
12035 }
12036 
ngtcp2_conn_get_idle_expiry(ngtcp2_conn * conn)12037 ngtcp2_tstamp ngtcp2_conn_get_idle_expiry(ngtcp2_conn *conn) {
12038   ngtcp2_duration trpto;
12039   ngtcp2_duration idle_timeout;
12040 
12041   /* TODO Remote max_idle_timeout becomes effective after handshake
12042      completion. */
12043 
12044   if (!(conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED) ||
12045       conn->remote.transport_params.max_idle_timeout == 0 ||
12046       (conn->local.transport_params.max_idle_timeout &&
12047        conn->local.transport_params.max_idle_timeout <
12048            conn->remote.transport_params.max_idle_timeout)) {
12049     idle_timeout = conn->local.transport_params.max_idle_timeout;
12050   } else {
12051     idle_timeout = conn->remote.transport_params.max_idle_timeout;
12052   }
12053 
12054   if (idle_timeout == 0) {
12055     return UINT64_MAX;
12056   }
12057 
12058   trpto = 3 * conn_compute_pto(
12059                   conn, (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)
12060                             ? &conn->pktns
12061                             : conn->hs_pktns);
12062 
12063   return conn->idle_ts + ngtcp2_max(idle_timeout, trpto);
12064 }
12065 
ngtcp2_conn_get_pto(ngtcp2_conn * conn)12066 ngtcp2_duration ngtcp2_conn_get_pto(ngtcp2_conn *conn) {
12067   return conn_compute_pto(conn,
12068                           (conn->flags & NGTCP2_CONN_FLAG_HANDSHAKE_COMPLETED)
12069                               ? &conn->pktns
12070                               : conn->hs_pktns);
12071 }
12072 
ngtcp2_conn_set_initial_crypto_ctx(ngtcp2_conn * conn,const ngtcp2_crypto_ctx * ctx)12073 void ngtcp2_conn_set_initial_crypto_ctx(ngtcp2_conn *conn,
12074                                         const ngtcp2_crypto_ctx *ctx) {
12075   assert(conn->in_pktns);
12076   conn->in_pktns->crypto.ctx = *ctx;
12077 }
12078 
ngtcp2_conn_get_initial_crypto_ctx(ngtcp2_conn * conn)12079 const ngtcp2_crypto_ctx *ngtcp2_conn_get_initial_crypto_ctx(ngtcp2_conn *conn) {
12080   assert(conn->in_pktns);
12081   return &conn->in_pktns->crypto.ctx;
12082 }
12083 
ngtcp2_conn_set_retry_aead(ngtcp2_conn * conn,const ngtcp2_crypto_aead * aead,const ngtcp2_crypto_aead_ctx * aead_ctx)12084 void ngtcp2_conn_set_retry_aead(ngtcp2_conn *conn,
12085                                 const ngtcp2_crypto_aead *aead,
12086                                 const ngtcp2_crypto_aead_ctx *aead_ctx) {
12087   assert(!conn->crypto.retry_aead_ctx.native_handle);
12088 
12089   conn->crypto.retry_aead = *aead;
12090   conn->crypto.retry_aead_ctx = *aead_ctx;
12091 }
12092 
ngtcp2_conn_set_crypto_ctx(ngtcp2_conn * conn,const ngtcp2_crypto_ctx * ctx)12093 void ngtcp2_conn_set_crypto_ctx(ngtcp2_conn *conn,
12094                                 const ngtcp2_crypto_ctx *ctx) {
12095   assert(conn->hs_pktns);
12096   conn->hs_pktns->crypto.ctx = *ctx;
12097   conn->pktns.crypto.ctx = *ctx;
12098 }
12099 
ngtcp2_conn_get_crypto_ctx(ngtcp2_conn * conn)12100 const ngtcp2_crypto_ctx *ngtcp2_conn_get_crypto_ctx(ngtcp2_conn *conn) {
12101   return &conn->pktns.crypto.ctx;
12102 }
12103 
ngtcp2_conn_set_early_crypto_ctx(ngtcp2_conn * conn,const ngtcp2_crypto_ctx * ctx)12104 void ngtcp2_conn_set_early_crypto_ctx(ngtcp2_conn *conn,
12105                                       const ngtcp2_crypto_ctx *ctx) {
12106   conn->early.ctx = *ctx;
12107 }
12108 
ngtcp2_conn_get_early_crypto_ctx(ngtcp2_conn * conn)12109 const ngtcp2_crypto_ctx *ngtcp2_conn_get_early_crypto_ctx(ngtcp2_conn *conn) {
12110   return &conn->early.ctx;
12111 }
12112 
ngtcp2_conn_get_tls_native_handle(ngtcp2_conn * conn)12113 void *ngtcp2_conn_get_tls_native_handle(ngtcp2_conn *conn) {
12114   return conn->crypto.tls_native_handle;
12115 }
12116 
ngtcp2_conn_set_tls_native_handle(ngtcp2_conn * conn,void * tls_native_handle)12117 void ngtcp2_conn_set_tls_native_handle(ngtcp2_conn *conn,
12118                                        void *tls_native_handle) {
12119   conn->crypto.tls_native_handle = tls_native_handle;
12120 }
12121 
ngtcp2_conn_get_connection_close_error_code(ngtcp2_conn * conn,ngtcp2_connection_close_error_code * ccec)12122 void ngtcp2_conn_get_connection_close_error_code(
12123     ngtcp2_conn *conn, ngtcp2_connection_close_error_code *ccec) {
12124   *ccec = conn->rx.ccec;
12125 }
12126 
ngtcp2_conn_set_tls_error(ngtcp2_conn * conn,int liberr)12127 void ngtcp2_conn_set_tls_error(ngtcp2_conn *conn, int liberr) {
12128   conn->crypto.tls_error = liberr;
12129 }
12130 
ngtcp2_conn_get_tls_error(ngtcp2_conn * conn)12131 int ngtcp2_conn_get_tls_error(ngtcp2_conn *conn) {
12132   return conn->crypto.tls_error;
12133 }
12134 
ngtcp2_conn_is_local_stream(ngtcp2_conn * conn,int64_t stream_id)12135 int ngtcp2_conn_is_local_stream(ngtcp2_conn *conn, int64_t stream_id) {
12136   return conn_local_stream(conn, stream_id);
12137 }
12138 
ngtcp2_conn_is_server(ngtcp2_conn * conn)12139 int ngtcp2_conn_is_server(ngtcp2_conn *conn) { return conn->server; }
12140 
ngtcp2_conn_after_retry(ngtcp2_conn * conn)12141 int ngtcp2_conn_after_retry(ngtcp2_conn *conn) {
12142   return (conn->flags & NGTCP2_CONN_FLAG_RECV_RETRY) != 0;
12143 }
12144 
ngtcp2_conn_set_stream_user_data(ngtcp2_conn * conn,int64_t stream_id,void * stream_user_data)12145 int ngtcp2_conn_set_stream_user_data(ngtcp2_conn *conn, int64_t stream_id,
12146                                      void *stream_user_data) {
12147   ngtcp2_strm *strm = ngtcp2_conn_find_stream(conn, stream_id);
12148 
12149   if (strm == NULL) {
12150     return NGTCP2_ERR_STREAM_NOT_FOUND;
12151   }
12152 
12153   strm->stream_user_data = stream_user_data;
12154 
12155   return 0;
12156 }
12157 
ngtcp2_conn_update_pkt_tx_time(ngtcp2_conn * conn,ngtcp2_tstamp ts)12158 void ngtcp2_conn_update_pkt_tx_time(ngtcp2_conn *conn, ngtcp2_tstamp ts) {
12159   if (!(conn->cstat.pacing_rate > 0) || conn->tx.pacing.pktlen == 0) {
12160     return;
12161   }
12162 
12163   conn->tx.pacing.next_ts =
12164       ts + (ngtcp2_duration)((double)conn->tx.pacing.pktlen /
12165                              conn->cstat.pacing_rate);
12166   conn->tx.pacing.pktlen = 0;
12167 }
12168 
ngtcp2_conn_get_send_quantum(ngtcp2_conn * conn)12169 size_t ngtcp2_conn_get_send_quantum(ngtcp2_conn *conn) {
12170   return conn->cstat.send_quantum;
12171 }
12172 
ngtcp2_path_challenge_entry_init(ngtcp2_path_challenge_entry * pcent,const ngtcp2_path * path,const uint8_t * data)12173 void ngtcp2_path_challenge_entry_init(ngtcp2_path_challenge_entry *pcent,
12174                                       const ngtcp2_path *path,
12175                                       const uint8_t *data) {
12176   ngtcp2_path_storage_init2(&pcent->ps, path);
12177   memcpy(pcent->data, data, sizeof(pcent->data));
12178 }
12179 
ngtcp2_settings_default_versioned(int settings_version,ngtcp2_settings * settings)12180 void ngtcp2_settings_default_versioned(int settings_version,
12181                                        ngtcp2_settings *settings) {
12182   (void)settings_version;
12183 
12184   memset(settings, 0, sizeof(*settings));
12185   settings->cc_algo = NGTCP2_CC_ALGO_CUBIC;
12186   settings->initial_rtt = NGTCP2_DEFAULT_INITIAL_RTT;
12187   settings->ack_thresh = 2;
12188   settings->max_udp_payload_size = NGTCP2_MAX_UDP_PAYLOAD_SIZE;
12189 }
12190 
ngtcp2_transport_params_default_versioned(int transport_params_version,ngtcp2_transport_params * params)12191 void ngtcp2_transport_params_default_versioned(
12192     int transport_params_version, ngtcp2_transport_params *params) {
12193   (void)transport_params_version;
12194 
12195   memset(params, 0, sizeof(*params));
12196   params->max_udp_payload_size = NGTCP2_DEFAULT_MAX_RECV_UDP_PAYLOAD_SIZE;
12197   params->ack_delay_exponent = NGTCP2_DEFAULT_ACK_DELAY_EXPONENT;
12198   params->max_ack_delay = NGTCP2_DEFAULT_MAX_ACK_DELAY;
12199   params->active_connection_id_limit =
12200       NGTCP2_DEFAULT_ACTIVE_CONNECTION_ID_LIMIT;
12201 }
12202 
12203 /* The functions prefixed with ngtcp2_pkt_ are usually put inside
12204    ngtcp2_pkt.c.  This function uses encryption construct and uses
12205    test data defined only in ngtcp2_conn_test.c, so it is written
12206    here. */
ngtcp2_pkt_write_connection_close(uint8_t * dest,size_t destlen,uint32_t version,const ngtcp2_cid * dcid,const ngtcp2_cid * scid,uint64_t error_code,ngtcp2_encrypt encrypt,const ngtcp2_crypto_aead * aead,const ngtcp2_crypto_aead_ctx * aead_ctx,const uint8_t * iv,ngtcp2_hp_mask hp_mask,const ngtcp2_crypto_cipher * hp,const ngtcp2_crypto_cipher_ctx * hp_ctx)12207 ngtcp2_ssize ngtcp2_pkt_write_connection_close(
12208     uint8_t *dest, size_t destlen, uint32_t version, const ngtcp2_cid *dcid,
12209     const ngtcp2_cid *scid, uint64_t error_code, ngtcp2_encrypt encrypt,
12210     const ngtcp2_crypto_aead *aead, const ngtcp2_crypto_aead_ctx *aead_ctx,
12211     const uint8_t *iv, ngtcp2_hp_mask hp_mask, const ngtcp2_crypto_cipher *hp,
12212     const ngtcp2_crypto_cipher_ctx *hp_ctx) {
12213   ngtcp2_pkt_hd hd;
12214   ngtcp2_crypto_km ckm;
12215   ngtcp2_crypto_cc cc;
12216   ngtcp2_ppe ppe;
12217   ngtcp2_frame fr = {0};
12218   int rv;
12219 
12220   ngtcp2_pkt_hd_init(&hd, NGTCP2_PKT_FLAG_LONG_FORM, NGTCP2_PKT_INITIAL, dcid,
12221                      scid, /* pkt_num = */ 0, /* pkt_numlen = */ 1, version,
12222                      /* len = */ 0);
12223 
12224   ngtcp2_vec_init(&ckm.secret, NULL, 0);
12225   ngtcp2_vec_init(&ckm.iv, iv, 12);
12226   ckm.aead_ctx = *aead_ctx;
12227   ckm.pkt_num = 0;
12228   ckm.flags = NGTCP2_CRYPTO_KM_FLAG_NONE;
12229 
12230   cc.aead = *aead;
12231   cc.hp = *hp;
12232   cc.ckm = &ckm;
12233   cc.hp_ctx = *hp_ctx;
12234   cc.encrypt = encrypt;
12235   cc.hp_mask = hp_mask;
12236 
12237   ngtcp2_ppe_init(&ppe, dest, destlen, &cc);
12238 
12239   rv = ngtcp2_ppe_encode_hd(&ppe, &hd);
12240   if (rv != 0) {
12241     assert(NGTCP2_ERR_NOBUF == rv);
12242     return rv;
12243   }
12244 
12245   if (!ngtcp2_ppe_ensure_hp_sample(&ppe)) {
12246     return NGTCP2_ERR_NOBUF;
12247   }
12248 
12249   fr.type = NGTCP2_FRAME_CONNECTION_CLOSE;
12250   fr.connection_close.error_code = error_code;
12251 
12252   rv = ngtcp2_ppe_encode_frame(&ppe, &fr);
12253   if (rv != 0) {
12254     assert(NGTCP2_ERR_NOBUF == rv);
12255     return rv;
12256   }
12257 
12258   return ngtcp2_ppe_final(&ppe, NULL);
12259 }
12260 
ngtcp2_is_bidi_stream(int64_t stream_id)12261 int ngtcp2_is_bidi_stream(int64_t stream_id) { return bidi_stream(stream_id); }
12262