lsquic_full_conn.c revision 2a5cd80e
1/* Copyright (c) 2017 - 2018 LiteSpeed Technologies Inc. See LICENSE. */ 2/* 3 * lsquic_full_conn.c -- A "full" connection object has full functionality 4 */ 5 6#include <assert.h> 7#include <errno.h> 8#include <inttypes.h> 9#include <stdarg.h> 10#include <stdlib.h> 11#include <string.h> 12#ifndef WIN32 13#include <netinet/in.h> 14#include <sys/socket.h> 15#include <sys/time.h> 16#endif 17#include <sys/queue.h> 18 19#include "lsquic_types.h" 20#include "lsquic.h" 21#include "lsquic_alarmset.h" 22#include "lsquic_packet_common.h" 23#include "lsquic_parse.h" 24#include "lsquic_packet_in.h" 25#include "lsquic_packet_out.h" 26#include "lsquic_rechist.h" 27#include "lsquic_util.h" 28#include "lsquic_conn_flow.h" 29#include "lsquic_sfcw.h" 30#include "lsquic_stream.h" 31#include "lsquic_senhist.h" 32#include "lsquic_rtt.h" 33#include "lsquic_cubic.h" 34#include "lsquic_pacer.h" 35#include "lsquic_send_ctl.h" 36#include "lsquic_set.h" 37#include "lsquic_malo.h" 38#include "lsquic_chsk_stream.h" 39#include "lsquic_str.h" 40#include "lsquic_qtags.h" 41#include "lsquic_handshake.h" 42#include "lsquic_headers_stream.h" 43#include "lsquic_frame_common.h" 44#include "lsquic_frame_reader.h" 45#include "lsquic_mm.h" 46#include "lsquic_engine_public.h" 47#include "lsquic_spi.h" 48#include "lsquic_ev_log.h" 49#include "lsquic_version.h" 50#include "lsquic_hash.h" 51 52#include "lsquic_conn.h" 53#include "lsquic_conn_public.h" 54#include "lsquic_ver_neg.h" 55#include "lsquic_full_conn.h" 56 57#define LSQUIC_LOGGER_MODULE LSQLM_CONN 58#define LSQUIC_LOG_CONN_ID conn->fc_conn.cn_cid 59#include "lsquic_logger.h" 60 61enum { STREAM_IF_STD, STREAM_IF_HSK, STREAM_IF_HDR, N_STREAM_IFS }; 62 63#define MAX_ANY_PACKETS_SINCE_LAST_ACK 20 64#define MAX_RETR_PACKETS_SINCE_LAST_ACK 2 65#define ACK_TIMEOUT 25000 66#define TIME_BETWEEN_PINGS 15000000 67#define IDLE_TIMEOUT 30000000 68 69/* IMPORTANT: Keep values of FC_SERVER and FC_HTTP same as LSENG_SERVER 70 * and LSENG_HTTP. 71 */ 72enum full_conn_flags { 73 FC_SERVER = LSENG_SERVER, /* Server mode */ 74 FC_HTTP = LSENG_HTTP, /* HTTP mode */ 75 FC_TIMED_OUT = (1 << 2), 76#define FC_BIT_ERROR 3 77 FC_ERROR = (1 << FC_BIT_ERROR), 78 FC_ABORTED = (1 << 4), 79 FC_CLOSING = (1 << 5), /* Closing */ 80 FC_SEND_PING = (1 << 6), /* PING frame scheduled */ 81 FC_NSTP = (1 << 7), /* NSTP mode */ 82 FC_SEND_GOAWAY = (1 << 8), 83 FC_SEND_WUF = (1 << 9), 84 FC_SEND_STOP_WAITING 85 = (1 <<10), 86 FC_ACK_QUEUED = (1 <<11), 87 FC_ACK_HAD_MISS = (1 <<12), /* Last ACK frame had missing packets. */ 88 FC_CREATED_OK = (1 <<13), 89 FC_RECV_CLOSE = (1 <<14), /* Received CONNECTION_CLOSE frame */ 90 FC_GOING_AWAY = (1 <<15), /* Do not accept or create new streams */ 91 FC_GOAWAY_SENT = (1 <<16), /* Only send GOAWAY once */ 92 FC_SUPPORT_PUSH = (1 <<17), 93 FC_GOT_PRST = (1 <<18), /* Received public reset packet */ 94 FC_FIRST_TICK = (1 <<19), 95 FC_TICK_CLOSE = (1 <<20), /* We returned TICK_CLOSE */ 96 FC_HSK_FAILED = (1 <<21), 97 FC_HAVE_SAVED_ACK = (1 <<22), 98}; 99 100#define FC_IMMEDIATE_CLOSE_FLAGS \ 101 (FC_TIMED_OUT|FC_ERROR|FC_ABORTED|FC_HSK_FAILED) 102 103#if LSQUIC_KEEP_STREAM_HISTORY 104#define KEEP_CLOSED_STREAM_HISTORY 0 105#endif 106 107#if KEEP_CLOSED_STREAM_HISTORY 108struct stream_history 109{ 110 uint32_t shist_stream_id; 111 enum stream_flags shist_stream_flags; 112 unsigned char shist_hist_buf[1 << SM_HIST_BITS]; 113}; 114#define SHIST_BITS 5 115#define SHIST_MASK ((1 << SHIST_BITS) - 1) 116#endif 117 118#ifndef KEEP_PACKET_HISTORY 119#ifdef NDEBUG 120#define KEEP_PACKET_HISTORY 0 121#else 122#define KEEP_PACKET_HISTORY 16 123#endif 124#endif 125 126#if KEEP_PACKET_HISTORY 127struct packet_el 128{ 129 lsquic_time_t time; 130 enum quic_ft_bit frame_types; 131}; 132 133struct recent_packets 134{ 135 struct packet_el els[KEEP_PACKET_HISTORY]; 136 unsigned idx; 137}; 138#endif 139 140struct stream_id_to_reset 141{ 142 STAILQ_ENTRY(stream_id_to_reset) sitr_next; 143 uint32_t sitr_stream_id; 144}; 145 146 147struct full_conn 148{ 149 struct lsquic_conn fc_conn; 150 struct lsquic_rechist fc_rechist; 151 struct { 152 const struct lsquic_stream_if *stream_if; 153 void *stream_if_ctx; 154 } fc_stream_ifs[N_STREAM_IFS]; 155 lsquic_conn_ctx_t *fc_conn_ctx; 156 struct lsquic_send_ctl fc_send_ctl; 157 struct lsquic_conn_public fc_pub; 158 lsquic_alarmset_t fc_alset; 159 lsquic_set32_t fc_closed_stream_ids[2]; 160 const struct lsquic_engine_settings 161 *fc_settings; 162 struct lsquic_engine_public *fc_enpub; 163 lsquic_packno_t fc_max_ack_packno; 164 lsquic_packno_t fc_max_swf_packno; 165 lsquic_time_t fc_mem_logged_last; 166 struct { 167 unsigned max_streams_in; 168 unsigned max_streams_out; 169 unsigned max_conn_send; 170 unsigned max_stream_send; 171 } fc_cfg; 172 enum full_conn_flags fc_flags; 173 /* Number of packets received since last ACK sent: */ 174 unsigned fc_n_slack_all; 175 /* Number ackable packets received since last ACK was sent: */ 176 unsigned fc_n_slack_akbl; 177 unsigned fc_n_delayed_streams; 178 unsigned fc_n_cons_unretx; 179 uint32_t fc_last_stream_id; 180 uint32_t fc_max_peer_stream_id; 181 uint32_t fc_goaway_stream_id; 182 struct ver_neg fc_ver_neg; 183 union { 184 struct client_hsk_ctx client; 185 } fc_hsk_ctx; 186#if FULL_CONN_STATS 187 struct { 188 unsigned n_all_packets_in, 189 n_packets_out, 190 n_undec_packets, 191 n_dup_packets, 192 n_err_packets; 193 unsigned long stream_data_sz; 194 unsigned long n_ticks; 195 unsigned n_acks_in, 196 n_acks_proc, 197 n_acks_merged[2]; 198 } fc_stats; 199#endif 200#if KEEP_CLOSED_STREAM_HISTORY 201 /* Rolling log of histories of closed streams. Older entries are 202 * overwritten. 203 */ 204 struct stream_history fc_stream_histories[1 << SHIST_BITS]; 205 unsigned fc_stream_hist_idx; 206#endif 207 char *fc_errmsg; 208#if KEEP_PACKET_HISTORY 209 struct recent_packets fc_recent_packets[2]; /* 0: in; 1: out */ 210#endif 211 STAILQ_HEAD(, stream_id_to_reset) 212 fc_stream_ids_to_reset; 213 struct short_ack_info fc_saved_ack_info; 214 lsquic_time_t fc_saved_ack_received; 215}; 216 217 218#define MAX_ERRMSG 256 219 220#define SET_ERRMSG(conn, ...) do { \ 221 if (!(conn)->fc_errmsg) \ 222 (conn)->fc_errmsg = malloc(MAX_ERRMSG); \ 223 if ((conn)->fc_errmsg) \ 224 snprintf((conn)->fc_errmsg, MAX_ERRMSG, __VA_ARGS__); \ 225} while (0) 226 227#define ABORT_WITH_FLAG(conn, flag, ...) do { \ 228 SET_ERRMSG(conn, __VA_ARGS__); \ 229 (conn)->fc_flags |= flag; \ 230 LSQ_ERROR("Abort connection: " __VA_ARGS__); \ 231} while (0) 232 233#define ABORT_ERROR(...) ABORT_WITH_FLAG(conn, FC_ERROR, __VA_ARGS__) 234 235#define ABORT_TIMEOUT(...) ABORT_WITH_FLAG(conn, FC_TIMED_OUT, __VA_ARGS__) 236 237static void 238idle_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now); 239 240static void 241ping_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now); 242 243static void 244handshake_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now); 245 246static void 247ack_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now); 248 249static lsquic_stream_t * 250new_stream (struct full_conn *conn, uint32_t stream_id, enum stream_ctor_flags); 251 252static void 253reset_ack_state (struct full_conn *conn); 254 255static int 256write_is_possible (struct full_conn *); 257 258static const struct headers_stream_callbacks *headers_callbacks_ptr; 259 260#if KEEP_CLOSED_STREAM_HISTORY 261 262static void 263save_stream_history (struct full_conn *conn, const lsquic_stream_t *stream) 264{ 265 sm_hist_idx_t idx; 266 struct stream_history *const shist = 267 &conn->fc_stream_histories[ conn->fc_stream_hist_idx++ & SHIST_MASK ]; 268 269 shist->shist_stream_id = stream->id; 270 shist->shist_stream_flags = stream->stream_flags; 271 272 idx = stream->sm_hist_idx & SM_HIST_IDX_MASK; 273 if ('\0' == stream->sm_hist_buf[ idx ]) 274 memcpy(shist->shist_hist_buf, stream->sm_hist_buf, idx + 1); 275 else 276 { 277 memcpy(shist->shist_hist_buf, 278 stream->sm_hist_buf + idx, sizeof(stream->sm_hist_buf) - idx); 279 memcpy(shist->shist_hist_buf + sizeof(shist->shist_hist_buf) - idx, 280 stream->sm_hist_buf, idx); 281 } 282} 283 284 285static const struct stream_history * 286find_stream_history (const struct full_conn *conn, uint32_t stream_id) 287{ 288 const struct stream_history *shist; 289 const struct stream_history *const shist_end = 290 conn->fc_stream_histories + (1 << SHIST_BITS); 291 for (shist = conn->fc_stream_histories; shist < shist_end; ++shist) 292 if (shist->shist_stream_id == stream_id) 293 return shist; 294 return NULL; 295} 296 297 298# define SAVE_STREAM_HISTORY(conn, stream) save_stream_history(conn, stream) 299#else 300# define SAVE_STREAM_HISTORY(conn, stream) 301#endif 302 303#if KEEP_PACKET_HISTORY 304static void 305recent_packet_hist_new (struct full_conn *conn, unsigned out, 306 lsquic_time_t time) 307{ 308 unsigned idx; 309 idx = conn->fc_recent_packets[out].idx++ % KEEP_PACKET_HISTORY; 310 conn->fc_recent_packets[out].els[idx].time = time; 311} 312 313 314static void 315recent_packet_hist_frames (struct full_conn *conn, unsigned out, 316 enum quic_ft_bit frame_types) 317{ 318 unsigned idx; 319 idx = (conn->fc_recent_packets[out].idx - 1) % KEEP_PACKET_HISTORY; 320 conn->fc_recent_packets[out].els[idx].frame_types |= frame_types; 321} 322 323 324#else 325#define recent_packet_hist_new(conn, out, time) 326#define recent_packet_hist_frames(conn, out, frames) 327#endif 328 329static unsigned 330highest_bit_set (unsigned sz) 331{ 332#if __GNUC__ 333 unsigned clz = __builtin_clz(sz); 334 return 31 - clz; 335#else 336 unsigned n, y; 337 n = 32; 338 y = sz >> 16; if (y) { n -= 16; sz = y; } 339 y = sz >> 8; if (y) { n -= 8; sz = y; } 340 y = sz >> 4; if (y) { n -= 4; sz = y; } 341 y = sz >> 2; if (y) { n -= 2; sz = y; } 342 y = sz >> 1; if (y) return 31 - n + 2; 343 return 31 - n + sz; 344#endif 345} 346 347 348static size_t 349calc_mem_used (const struct full_conn *conn) 350{ 351 const lsquic_stream_t *stream; 352 const struct lsquic_hash_elem *el; 353 size_t size; 354 355 size = sizeof(*conn); 356 size -= sizeof(conn->fc_send_ctl); 357 size += lsquic_send_ctl_mem_used(&conn->fc_send_ctl); 358 size += lsquic_hash_mem_used(conn->fc_pub.all_streams); 359 size += lsquic_malo_mem_used(conn->fc_pub.packet_out_malo); 360 if (conn->fc_pub.hs) 361 size += lsquic_headers_stream_mem_used(conn->fc_pub.hs); 362 363 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 364 el = lsquic_hash_next(conn->fc_pub.all_streams)) 365 { 366 stream = lsquic_hashelem_getdata(el); 367 size += lsquic_stream_mem_used(stream); 368 } 369 size += conn->fc_conn.cn_esf->esf_mem_used(conn->fc_conn.cn_enc_session); 370 371 return size; 372} 373 374 375static void 376set_versions (struct full_conn *conn, unsigned versions) 377{ 378 conn->fc_ver_neg.vn_supp = versions; 379 conn->fc_ver_neg.vn_ver = highest_bit_set(versions); 380 conn->fc_ver_neg.vn_buf = lsquic_ver2tag(conn->fc_ver_neg.vn_ver); 381 conn->fc_conn.cn_version = conn->fc_ver_neg.vn_ver; 382 LSQ_DEBUG("negotiating version %s", 383 lsquic_ver2str[conn->fc_ver_neg.vn_ver]); 384} 385 386 387static void 388init_ver_neg (struct full_conn *conn, unsigned versions) 389{ 390 set_versions(conn, versions); 391 conn->fc_ver_neg.vn_tag = &conn->fc_ver_neg.vn_buf; 392 conn->fc_ver_neg.vn_state = VN_START; 393} 394 395 396/* If peer supplies odd values, we abort the connection immediately rather 397 * that wait for it to finish "naturally" due to inability to send things. 398 */ 399static void 400conn_on_peer_config (struct full_conn *conn, unsigned peer_cfcw, 401 unsigned peer_sfcw, unsigned max_streams_out) 402{ 403 lsquic_stream_t *stream; 404 struct lsquic_hash_elem *el; 405 406 LSQ_INFO("Applying peer config: cfcw: %u; sfcw: %u; # streams: %u", 407 peer_cfcw, peer_sfcw, max_streams_out); 408 409 if (peer_cfcw < conn->fc_pub.conn_cap.cc_sent) 410 { 411 ABORT_ERROR("peer specified CFCW=%u bytes, which is smaller than " 412 "the amount of data already sent on this connection (%"PRIu64 413 " bytes)", peer_cfcw, conn->fc_pub.conn_cap.cc_sent); 414 return; 415 } 416 417 conn->fc_cfg.max_streams_out = max_streams_out; 418 conn->fc_pub.conn_cap.cc_max = peer_cfcw; 419 420 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 421 el = lsquic_hash_next(conn->fc_pub.all_streams)) 422 { 423 stream = lsquic_hashelem_getdata(el); 424 if (0 != lsquic_stream_set_max_send_off(stream, peer_sfcw)) 425 { 426 ABORT_ERROR("cannot set peer-supplied SFCW=%u on stream %u", 427 peer_sfcw, stream->id); 428 return; 429 } 430 } 431 432 conn->fc_cfg.max_stream_send = peer_sfcw; 433} 434 435 436static int 437send_smhl (const struct full_conn *conn) 438{ 439 uint32_t smhl; 440 return conn->fc_conn.cn_enc_session 441 && (conn->fc_conn.cn_flags & LSCONN_HANDSHAKE_DONE) 442 && 0 == conn->fc_conn.cn_esf->esf_get_peer_setting( 443 conn->fc_conn.cn_enc_session, QTAG_SMHL, &smhl) 444 && 1 == smhl; 445} 446 447 448/* Once handshake has been completed, send settings to peer if appropriate. 449 */ 450static void 451maybe_send_settings (struct full_conn *conn) 452{ 453 struct lsquic_http2_setting settings[2]; 454 unsigned n_settings = 0; 455 456 if (conn->fc_settings->es_max_header_list_size && send_smhl(conn)) 457 { 458 settings[n_settings].id = SETTINGS_MAX_HEADER_LIST_SIZE; 459 settings[n_settings].value = conn->fc_settings->es_max_header_list_size; 460 LSQ_DEBUG("sending settings SETTINGS_MAX_HEADER_LIST_SIZE=%u", 461 settings[n_settings].value); 462 ++n_settings; 463 } 464 if (!(conn->fc_flags & FC_SERVER) && !conn->fc_settings->es_support_push) 465 { 466 settings[n_settings].id = SETTINGS_ENABLE_PUSH; 467 settings[n_settings].value = 0; 468 LSQ_DEBUG("sending settings SETTINGS_ENABLE_PUSH=%u", 469 settings[n_settings].value); 470 ++n_settings; 471 } 472 473 if (n_settings) 474 { 475 if (0 != lsquic_headers_stream_send_settings(conn->fc_pub.hs, 476 settings, n_settings)) 477 ABORT_ERROR("could not send settings"); 478 } 479 else 480 LSQ_DEBUG("not sending any settings"); 481} 482 483 484static int 485apply_peer_settings (struct full_conn *conn) 486{ 487 uint32_t cfcw, sfcw, mids; 488 unsigned n; 489 const struct { 490 uint32_t tag; 491 uint32_t *val; 492 const char *tag_str; 493 } tags[] = { 494 { QTAG_CFCW, &cfcw, "CFCW", }, 495 { QTAG_SFCW, &sfcw, "SFCW", }, 496 { QTAG_MIDS, &mids, "MIDS", }, 497 }; 498 499#ifndef NDEBUG 500 if (getenv("LSQUIC_TEST_ENGINE_DTOR")) 501 return 0; 502#endif 503 504 for (n = 0; n < sizeof(tags) / sizeof(tags[0]); ++n) 505 if (0 != conn->fc_conn.cn_esf->esf_get_peer_setting( 506 conn->fc_conn.cn_enc_session, tags[n].tag, tags[n].val)) 507 { 508 LSQ_INFO("peer did not supply value for %s", tags[n].tag_str); 509 return -1; 510 } 511 512 LSQ_DEBUG("peer settings: CFCW: %u; SFCW: %u; MIDS: %u", 513 cfcw, sfcw, mids); 514 conn_on_peer_config(conn, cfcw, sfcw, mids); 515 if (conn->fc_flags & FC_HTTP) 516 maybe_send_settings(conn); 517 return 0; 518} 519 520 521static const struct conn_iface *full_conn_iface_ptr; 522 523static struct full_conn * 524new_conn_common (lsquic_cid_t cid, struct lsquic_engine_public *enpub, 525 const struct lsquic_stream_if *stream_if, 526 void *stream_if_ctx, unsigned flags, 527 unsigned short max_packet_size) 528{ 529 struct full_conn *conn; 530 lsquic_stream_t *headers_stream; 531 int saved_errno; 532 533 assert(0 == (flags & ~(FC_SERVER|FC_HTTP))); 534 535 conn = calloc(1, sizeof(*conn)); 536 if (!conn) 537 return NULL; 538 headers_stream = NULL; 539 conn->fc_conn.cn_cid = cid; 540 conn->fc_conn.cn_pack_size = max_packet_size; 541 conn->fc_flags = flags; 542 conn->fc_enpub = enpub; 543 conn->fc_pub.enpub = enpub; 544 conn->fc_pub.mm = &enpub->enp_mm; 545 conn->fc_pub.lconn = &conn->fc_conn; 546 conn->fc_pub.send_ctl = &conn->fc_send_ctl; 547 conn->fc_pub.packet_out_malo = 548 lsquic_malo_create(sizeof(struct lsquic_packet_out)); 549 conn->fc_stream_ifs[STREAM_IF_STD].stream_if = stream_if; 550 conn->fc_stream_ifs[STREAM_IF_STD].stream_if_ctx = stream_if_ctx; 551 conn->fc_settings = &enpub->enp_settings; 552 /* Calculate maximum number of incoming streams using the same mechanism 553 * and parameters as found in Chrome: 554 */ 555 conn->fc_cfg.max_streams_in = 556 (unsigned) ((float) enpub->enp_settings.es_max_streams_in * 1.1f); 557 if (conn->fc_cfg.max_streams_in < 558 enpub->enp_settings.es_max_streams_in + 10) 559 conn->fc_cfg.max_streams_in = 560 enpub->enp_settings.es_max_streams_in + 10; 561 /* `max_streams_out' gets reset when handshake is complete and we 562 * learn of peer settings. 100 seems like a sane default value 563 * because it is what other implementations use. In server mode, 564 * we do not open any streams until the handshake is complete; in 565 * client mode, we are limited to 98 outgoing requests alongside 566 * handshake and headers streams. 567 */ 568 conn->fc_cfg.max_streams_out = 100; 569 TAILQ_INIT(&conn->fc_pub.sending_streams); 570 TAILQ_INIT(&conn->fc_pub.read_streams); 571 TAILQ_INIT(&conn->fc_pub.write_streams); 572 TAILQ_INIT(&conn->fc_pub.service_streams); 573 STAILQ_INIT(&conn->fc_stream_ids_to_reset); 574 lsquic_conn_cap_init(&conn->fc_pub.conn_cap, LSQUIC_MIN_FCW); 575 lsquic_alarmset_init(&conn->fc_alset, cid); 576 lsquic_alarmset_init_alarm(&conn->fc_alset, AL_IDLE, idle_alarm_expired, conn); 577 lsquic_alarmset_init_alarm(&conn->fc_alset, AL_ACK, ack_alarm_expired, conn); 578 lsquic_alarmset_init_alarm(&conn->fc_alset, AL_PING, ping_alarm_expired, conn); 579 lsquic_alarmset_init_alarm(&conn->fc_alset, AL_HANDSHAKE, handshake_alarm_expired, conn); 580 lsquic_set32_init(&conn->fc_closed_stream_ids[0]); 581 lsquic_set32_init(&conn->fc_closed_stream_ids[1]); 582 lsquic_cfcw_init(&conn->fc_pub.cfcw, &conn->fc_pub, conn->fc_settings->es_cfcw); 583 lsquic_send_ctl_init(&conn->fc_send_ctl, &conn->fc_alset, conn->fc_enpub, 584 &conn->fc_ver_neg, &conn->fc_pub, conn->fc_conn.cn_pack_size); 585 586 conn->fc_pub.all_streams = lsquic_hash_create(); 587 if (!conn->fc_pub.all_streams) 588 goto cleanup_on_error; 589 lsquic_rechist_init(&conn->fc_rechist, cid); 590 if (conn->fc_flags & FC_HTTP) 591 { 592 conn->fc_pub.hs = lsquic_headers_stream_new( 593 !!(conn->fc_flags & FC_SERVER), conn->fc_pub.mm, conn->fc_settings, 594 headers_callbacks_ptr, conn); 595 if (!conn->fc_pub.hs) 596 goto cleanup_on_error; 597 conn->fc_stream_ifs[STREAM_IF_HDR].stream_if = lsquic_headers_stream_if; 598 conn->fc_stream_ifs[STREAM_IF_HDR].stream_if_ctx = conn->fc_pub.hs; 599 headers_stream = new_stream(conn, LSQUIC_STREAM_HEADERS, 600 SCF_CALL_ON_NEW); 601 if (!headers_stream) 602 goto cleanup_on_error; 603 } 604 else 605 { 606 conn->fc_stream_ifs[STREAM_IF_HDR].stream_if = stream_if; 607 conn->fc_stream_ifs[STREAM_IF_HDR].stream_if_ctx = stream_if_ctx; 608 } 609 if (conn->fc_settings->es_support_push) 610 conn->fc_flags |= FC_SUPPORT_PUSH; 611 conn->fc_conn.cn_if = full_conn_iface_ptr; 612 return conn; 613 614 cleanup_on_error: 615 saved_errno = errno; 616 617 if (conn->fc_pub.all_streams) 618 lsquic_hash_destroy(conn->fc_pub.all_streams); 619 lsquic_rechist_cleanup(&conn->fc_rechist); 620 if (conn->fc_flags & FC_HTTP) 621 { 622 if (conn->fc_pub.hs) 623 lsquic_headers_stream_destroy(conn->fc_pub.hs); 624 if (headers_stream) 625 lsquic_stream_destroy(headers_stream); 626 } 627 memset(conn, 0, sizeof(*conn)); 628 free(conn); 629 630 errno = saved_errno; 631 return NULL; 632} 633 634 635struct lsquic_conn * 636full_conn_client_new (struct lsquic_engine_public *enpub, 637 const struct lsquic_stream_if *stream_if, 638 void *stream_if_ctx, unsigned flags, 639 const char *hostname, unsigned short max_packet_size) 640{ 641 struct full_conn *conn; 642 enum lsquic_version version; 643 lsquic_cid_t cid; 644 const struct enc_session_funcs *esf; 645 646 version = highest_bit_set(enpub->enp_settings.es_versions); 647 esf = select_esf_by_ver(version); 648 cid = esf->esf_generate_cid(); 649 conn = new_conn_common(cid, enpub, stream_if, stream_if_ctx, flags, 650 max_packet_size); 651 if (!conn) 652 return NULL; 653 conn->fc_conn.cn_esf = esf; 654 conn->fc_conn.cn_enc_session = 655 conn->fc_conn.cn_esf->esf_create_client(hostname, cid, conn->fc_enpub); 656 if (!conn->fc_conn.cn_enc_session) 657 { 658 LSQ_WARN("could not create enc session: %s", strerror(errno)); 659 conn->fc_conn.cn_if->ci_destroy(&conn->fc_conn); 660 return NULL; 661 } 662 663 if (conn->fc_flags & FC_HTTP) 664 conn->fc_last_stream_id = LSQUIC_STREAM_HEADERS; /* Client goes 5, 7, 9.... */ 665 else 666 conn->fc_last_stream_id = LSQUIC_STREAM_HANDSHAKE; 667 conn->fc_hsk_ctx.client.lconn = &conn->fc_conn; 668 conn->fc_hsk_ctx.client.mm = &enpub->enp_mm; 669 conn->fc_hsk_ctx.client.ver_neg = &conn->fc_ver_neg; 670 conn->fc_stream_ifs[STREAM_IF_HSK] 671 .stream_if = &lsquic_client_hsk_stream_if; 672 conn->fc_stream_ifs[STREAM_IF_HSK].stream_if_ctx = &conn->fc_hsk_ctx.client; 673 init_ver_neg(conn, conn->fc_settings->es_versions); 674 conn->fc_conn.cn_pf = select_pf_by_ver(conn->fc_ver_neg.vn_ver); 675 if (conn->fc_settings->es_handshake_to) 676 lsquic_alarmset_set(&conn->fc_alset, AL_HANDSHAKE, 677 lsquic_time_now() + conn->fc_settings->es_handshake_to); 678 if (!new_stream(conn, LSQUIC_STREAM_HANDSHAKE, SCF_CALL_ON_NEW)) 679 { 680 LSQ_WARN("could not create handshake stream: %s", strerror(errno)); 681 conn->fc_conn.cn_if->ci_destroy(&conn->fc_conn); 682 return NULL; 683 } 684 conn->fc_flags |= FC_CREATED_OK; 685 LSQ_INFO("Created new client connection"); 686 EV_LOG_CONN_EVENT(cid, "created full connection"); 687 return &conn->fc_conn; 688} 689 690 691void 692full_conn_client_call_on_new (struct lsquic_conn *lconn) 693{ 694 struct full_conn *const conn = (struct full_conn *) lconn; 695 assert(conn->fc_flags & FC_CREATED_OK); 696 conn->fc_conn_ctx = conn->fc_stream_ifs[STREAM_IF_STD].stream_if 697 ->on_new_conn(conn->fc_stream_ifs[STREAM_IF_STD].stream_if_ctx, lconn); 698} 699 700 701static int 702is_our_stream (const struct full_conn *conn, const lsquic_stream_t *stream) 703{ 704 int is_server = !!(conn->fc_flags & FC_SERVER); 705 return (1 & stream->id) ^ is_server; 706} 707 708 709static unsigned 710count_streams (const struct full_conn *conn, int peer) 711{ 712 const lsquic_stream_t *stream; 713 unsigned count; 714 int ours; 715 int is_server; 716 struct lsquic_hash_elem *el; 717 718 peer = !!peer; 719 is_server = !!(conn->fc_flags & FC_SERVER); 720 count = 0; 721 722 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 723 el = lsquic_hash_next(conn->fc_pub.all_streams)) 724 { 725 stream = lsquic_hashelem_getdata(el); 726 ours = (1 & stream->id) ^ is_server; 727 if (ours ^ peer) 728 count += !lsquic_stream_is_closed(stream); 729 } 730 731 return count; 732} 733 734 735static void 736full_conn_ci_destroy (lsquic_conn_t *lconn) 737{ 738 struct full_conn *conn = (struct full_conn *) lconn; 739 struct lsquic_hash_elem *el; 740 struct lsquic_stream *stream; 741 struct stream_id_to_reset *sitr; 742 743 LSQ_DEBUG("destroy connection"); 744 conn->fc_flags |= FC_CLOSING; 745 lsquic_set32_cleanup(&conn->fc_closed_stream_ids[0]); 746 lsquic_set32_cleanup(&conn->fc_closed_stream_ids[1]); 747 while ((el = lsquic_hash_first(conn->fc_pub.all_streams))) 748 { 749 stream = lsquic_hashelem_getdata(el); 750 lsquic_hash_erase(conn->fc_pub.all_streams, el); 751 lsquic_stream_destroy(stream); 752 } 753 lsquic_hash_destroy(conn->fc_pub.all_streams); 754 if (conn->fc_flags & FC_CREATED_OK) 755 conn->fc_stream_ifs[STREAM_IF_STD].stream_if 756 ->on_conn_closed(&conn->fc_conn); 757 if (conn->fc_pub.hs) 758 lsquic_headers_stream_destroy(conn->fc_pub.hs); 759 760 lsquic_send_ctl_cleanup(&conn->fc_send_ctl); 761 lsquic_rechist_cleanup(&conn->fc_rechist); 762 if (conn->fc_conn.cn_enc_session) 763 conn->fc_conn.cn_esf->esf_destroy(conn->fc_conn.cn_enc_session); 764 lsquic_malo_destroy(conn->fc_pub.packet_out_malo); 765#if FULL_CONN_STATS 766 LSQ_NOTICE("# ticks: %lu", conn->fc_stats.n_ticks); 767 LSQ_NOTICE("received %u packets, of which %u were not decryptable, %u were " 768 "dups and %u were errors; sent %u packets, avg stream data per outgoing" 769 " packet is %lu bytes", 770 conn->fc_stats.n_all_packets_in, conn->fc_stats.n_undec_packets, 771 conn->fc_stats.n_dup_packets, conn->fc_stats.n_err_packets, 772 conn->fc_stats.n_packets_out, 773 conn->fc_stats.stream_data_sz / conn->fc_stats.n_packets_out); 774 LSQ_NOTICE("ACKs: in: %u; processed: %u; merged to: new %u, old %u", 775 conn->fc_stats.n_acks_in, conn->fc_stats.n_acks_proc, 776 conn->fc_stats.n_acks_merged[0], conn->fc_stats.n_acks_merged[1]); 777#endif 778 while ((sitr = STAILQ_FIRST(&conn->fc_stream_ids_to_reset))) 779 { 780 STAILQ_REMOVE_HEAD(&conn->fc_stream_ids_to_reset, sitr_next); 781 free(sitr); 782 } 783 EV_LOG_CONN_EVENT(LSQUIC_LOG_CONN_ID, "full connection destroyed"); 784 free(conn->fc_errmsg); 785 free(conn); 786} 787 788 789static void 790conn_mark_stream_closed (struct full_conn *conn, uint32_t stream_id) 791{ /* Because stream IDs are distributed unevenly -- there is a set of odd 792 * stream IDs and a set of even stream IDs -- it is more efficient to 793 * maintain two sets of closed stream IDs. 794 */ 795 int idx = stream_id & 1; 796 stream_id >>= 1; 797 if (0 != lsquic_set32_add(&conn->fc_closed_stream_ids[idx], stream_id)) 798 ABORT_ERROR("could not add element to set: %s", strerror(errno)); 799} 800 801 802static int 803conn_is_stream_closed (struct full_conn *conn, uint32_t stream_id) 804{ 805 int idx = stream_id & 1; 806 stream_id >>= 1; 807 return lsquic_set32_has(&conn->fc_closed_stream_ids[idx], stream_id); 808} 809 810 811static void 812set_ack_timer (struct full_conn *conn, lsquic_time_t now) 813{ 814 lsquic_alarmset_set(&conn->fc_alset, AL_ACK, now + ACK_TIMEOUT); 815 LSQ_DEBUG("ACK alarm set to %"PRIu64, now + ACK_TIMEOUT); 816} 817 818 819static void 820ack_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now) 821{ 822 struct full_conn *conn = ctx; 823 LSQ_DEBUG("ACK timer expired (%"PRIu64" < %"PRIu64"): ACK queued", 824 expiry, now); 825 conn->fc_flags |= FC_ACK_QUEUED; 826} 827 828 829static void 830try_queueing_ack (struct full_conn *conn, int was_missing, lsquic_time_t now) 831{ 832 if (conn->fc_n_slack_akbl >= MAX_RETR_PACKETS_SINCE_LAST_ACK || 833 (conn->fc_conn.cn_version < LSQVER_039 /* Since Q039 do not ack ACKs */ 834 && conn->fc_n_slack_all >= MAX_ANY_PACKETS_SINCE_LAST_ACK) || 835 ((conn->fc_flags & FC_ACK_HAD_MISS) && was_missing) || 836 lsquic_send_ctl_n_stop_waiting(&conn->fc_send_ctl) > 1) 837 { 838 lsquic_alarmset_unset(&conn->fc_alset, AL_ACK); 839 lsquic_send_ctl_sanity_check(&conn->fc_send_ctl); 840 conn->fc_flags |= FC_ACK_QUEUED; 841 LSQ_DEBUG("ACK queued: ackable: %u; all: %u; had_miss: %d; " 842 "was_missing: %d; n_stop_waiting: %u", 843 conn->fc_n_slack_akbl, conn->fc_n_slack_all, 844 !!(conn->fc_flags & FC_ACK_HAD_MISS), was_missing, 845 lsquic_send_ctl_n_stop_waiting(&conn->fc_send_ctl)); 846 } 847 else if (conn->fc_n_slack_akbl > 0) 848 set_ack_timer(conn, now); 849} 850 851 852static void 853reset_ack_state (struct full_conn *conn) 854{ 855 conn->fc_n_slack_all = 0; 856 conn->fc_n_slack_akbl = 0; 857 lsquic_send_ctl_n_stop_waiting_reset(&conn->fc_send_ctl); 858 conn->fc_flags &= ~FC_ACK_QUEUED; 859 lsquic_alarmset_unset(&conn->fc_alset, AL_ACK); 860 lsquic_send_ctl_sanity_check(&conn->fc_send_ctl); 861 LSQ_DEBUG("ACK state reset"); 862} 863 864 865static lsquic_stream_t * 866new_stream_ext (struct full_conn *conn, uint32_t stream_id, int if_idx, 867 enum stream_ctor_flags stream_ctor_flags) 868{ 869 struct lsquic_stream *stream; 870 871 if (conn->fc_conn.cn_version >= LSQVER_042) 872 stream_ctor_flags |= SCF_ALLOW_OVERLAP; 873 874 stream = lsquic_stream_new_ext(stream_id, &conn->fc_pub, 875 conn->fc_stream_ifs[if_idx].stream_if, 876 conn->fc_stream_ifs[if_idx].stream_if_ctx, conn->fc_settings->es_sfcw, 877 conn->fc_cfg.max_stream_send, stream_ctor_flags); 878 if (stream) 879 lsquic_hash_insert(conn->fc_pub.all_streams, &stream->id, sizeof(stream->id), 880 stream); 881 return stream; 882} 883 884 885static lsquic_stream_t * 886new_stream (struct full_conn *conn, uint32_t stream_id, 887 enum stream_ctor_flags flags) 888{ 889 int idx; 890 switch (stream_id) 891 { 892 case LSQUIC_STREAM_HANDSHAKE: 893 idx = STREAM_IF_HSK; 894 flags |= SCF_DI_AUTOSWITCH; 895 break; 896 case LSQUIC_STREAM_HEADERS: 897 idx = STREAM_IF_HDR; 898 flags |= SCF_DI_AUTOSWITCH; 899 if (!(conn->fc_flags & FC_HTTP) && 900 conn->fc_enpub->enp_settings.es_rw_once) 901 flags |= SCF_DISP_RW_ONCE; 902 break; 903 default: 904 idx = STREAM_IF_STD; 905 flags |= SCF_DI_AUTOSWITCH; 906 if (conn->fc_enpub->enp_settings.es_rw_once) 907 flags |= SCF_DISP_RW_ONCE; 908 break; 909 } 910 return new_stream_ext(conn, stream_id, idx, flags); 911} 912 913 914static uint32_t 915generate_stream_id (struct full_conn *conn) 916{ 917 conn->fc_last_stream_id += 2; 918 return conn->fc_last_stream_id; 919} 920 921 922unsigned 923lsquic_conn_n_pending_streams (const lsquic_conn_t *lconn) 924{ 925 struct full_conn *conn = (struct full_conn *) lconn; 926 return conn->fc_n_delayed_streams; 927} 928 929 930unsigned 931lsquic_conn_cancel_pending_streams (lsquic_conn_t *lconn, unsigned n) 932{ 933 struct full_conn *conn = (struct full_conn *) lconn; 934 if (n > conn->fc_n_delayed_streams) 935 conn->fc_n_delayed_streams = 0; 936 else 937 conn->fc_n_delayed_streams -= n; 938 return conn->fc_n_delayed_streams; 939} 940 941 942static int 943either_side_going_away (const struct full_conn *conn) 944{ 945 return (conn->fc_flags & FC_GOING_AWAY) 946 || (conn->fc_conn.cn_flags & LSCONN_PEER_GOING_AWAY); 947} 948 949 950void 951lsquic_conn_make_stream (lsquic_conn_t *lconn) 952{ 953 struct full_conn *conn = (struct full_conn *) lconn; 954 unsigned stream_count = count_streams(conn, 0); 955 if (stream_count < conn->fc_cfg.max_streams_out) 956 { 957 if (!new_stream(conn, generate_stream_id(conn), SCF_CALL_ON_NEW)) 958 ABORT_ERROR("could not create new stream: %s", strerror(errno)); 959 } 960 else if (either_side_going_away(conn)) 961 (void) conn->fc_stream_ifs[STREAM_IF_STD].stream_if->on_new_stream( 962 conn->fc_stream_ifs[STREAM_IF_STD].stream_if_ctx, NULL); 963 else 964 { 965 ++conn->fc_n_delayed_streams; 966 LSQ_DEBUG("delayed stream creation. Backlog size: %u", 967 conn->fc_n_delayed_streams); 968 } 969} 970 971 972static lsquic_stream_t * 973find_stream_by_id (struct full_conn *conn, uint32_t stream_id) 974{ 975 struct lsquic_hash_elem *el; 976 el = lsquic_hash_find(conn->fc_pub.all_streams, &stream_id, sizeof(stream_id)); 977 if (el) 978 return lsquic_hashelem_getdata(el); 979 else 980 return NULL; 981} 982 983 984lsquic_stream_t * 985lsquic_conn_get_stream_by_id (lsquic_conn_t *lconn, uint32_t stream_id) 986{ 987 struct full_conn *conn = (struct full_conn *) lconn; 988 return find_stream_by_id(conn, stream_id); 989} 990 991 992lsquic_engine_t * 993lsquic_conn_get_engine (lsquic_conn_t *lconn) 994{ 995 struct full_conn *conn = (struct full_conn *) lconn; 996 return conn->fc_enpub->enp_engine; 997} 998 999 1000static ptrdiff_t 1001count_zero_bytes (const unsigned char *p, size_t len) 1002{ 1003 const unsigned char *const end = p + len; 1004 while (p < end && 0 == *p) 1005 ++p; 1006 return len - (end - p); 1007} 1008 1009 1010static unsigned 1011process_padding_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1012 const unsigned char *p, size_t len) 1013{ 1014 if (conn->fc_conn.cn_version >= LSQVER_038) 1015 return (unsigned) count_zero_bytes(p, len); 1016 if (lsquic_is_zero(p, len)) 1017 { 1018 EV_LOG_PADDING_FRAME_IN(LSQUIC_LOG_CONN_ID, len); 1019 return (unsigned) len; 1020 } 1021 else 1022 return 0; 1023} 1024 1025 1026static unsigned 1027process_ping_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1028 const unsigned char *p, size_t len) 1029{ /* This frame causes ACK frame to be queued, but nothing to do here; 1030 * return the length of this frame. 1031 */ 1032 EV_LOG_PING_FRAME_IN(LSQUIC_LOG_CONN_ID); 1033 LSQ_DEBUG("received PING"); 1034 return 1; 1035} 1036 1037 1038static int 1039is_peer_initiated (const struct full_conn *conn, uint32_t stream_id) 1040{ 1041 unsigned is_server = !!(conn->fc_flags & FC_SERVER); 1042 int peer_initiated = (stream_id & 1) == is_server; 1043 return peer_initiated; 1044} 1045 1046 1047static void 1048maybe_schedule_reset_for_stream (struct full_conn *conn, uint32_t stream_id) 1049{ 1050 struct stream_id_to_reset *sitr; 1051 1052 if (conn_is_stream_closed(conn, stream_id)) 1053 return; 1054 1055 sitr = malloc(sizeof(*sitr)); 1056 if (!sitr) 1057 return; 1058 1059 sitr->sitr_stream_id = stream_id; 1060 STAILQ_INSERT_TAIL(&conn->fc_stream_ids_to_reset, sitr, sitr_next); 1061 conn_mark_stream_closed(conn, stream_id); 1062} 1063 1064 1065static unsigned 1066process_stream_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1067 const unsigned char *p, size_t len) 1068{ 1069 stream_frame_t *stream_frame; 1070 lsquic_stream_t *stream; 1071 enum enc_level enc_level; 1072 int parsed_len; 1073 1074 stream_frame = lsquic_malo_get(conn->fc_pub.mm->malo.stream_frame); 1075 if (!stream_frame) 1076 { 1077 LSQ_WARN("could not allocate stream frame: %s", strerror(errno)); 1078 return 0; 1079 } 1080 1081 parsed_len = conn->fc_conn.cn_pf->pf_parse_stream_frame(p, len, 1082 stream_frame); 1083 if (parsed_len < 0) { 1084 lsquic_malo_put(stream_frame); 1085 return 0; 1086 } 1087 EV_LOG_STREAM_FRAME_IN(LSQUIC_LOG_CONN_ID, stream_frame); 1088 LSQ_DEBUG("Got stream frame for stream #%u", stream_frame->stream_id); 1089 1090 enc_level = lsquic_packet_in_enc_level(packet_in); 1091 if (stream_frame->stream_id != LSQUIC_STREAM_HANDSHAKE 1092 && enc_level != ENC_LEV_FORW 1093 && enc_level != ENC_LEV_INIT) 1094 { 1095 lsquic_malo_put(stream_frame); 1096 ABORT_ERROR("received unencrypted data for stream %u", 1097 stream_frame->stream_id); 1098 return 0; 1099 } 1100 1101 if (conn->fc_flags & FC_CLOSING) 1102 { 1103 LSQ_DEBUG("Connection closing: ignore frame"); 1104 lsquic_malo_put(stream_frame); 1105 return parsed_len; 1106 } 1107 1108 stream = find_stream_by_id(conn, stream_frame->stream_id); 1109 if (!stream) 1110 { 1111 if (conn_is_stream_closed(conn, stream_frame->stream_id)) 1112 { 1113 LSQ_DEBUG("drop frame for closed stream %u", stream_frame->stream_id); 1114 lsquic_malo_put(stream_frame); 1115 return parsed_len; 1116 } 1117 if (is_peer_initiated(conn, stream_frame->stream_id)) 1118 { 1119 unsigned in_count = count_streams(conn, 1); 1120 LSQ_DEBUG("number of peer-initiated streams: %u", in_count); 1121 if (in_count >= conn->fc_cfg.max_streams_in) 1122 { 1123 ABORT_ERROR("incoming stream would exceed limit: %u", 1124 conn->fc_cfg.max_streams_in); 1125 lsquic_malo_put(stream_frame); 1126 return 0; 1127 } 1128 if ((conn->fc_flags & FC_GOING_AWAY) && 1129 stream_frame->stream_id > conn->fc_max_peer_stream_id) 1130 { 1131 LSQ_DEBUG("going away: reset new incoming stream %"PRIu32, 1132 stream_frame->stream_id); 1133 maybe_schedule_reset_for_stream(conn, stream_frame->stream_id); 1134 lsquic_malo_put(stream_frame); 1135 return parsed_len; 1136 } 1137 } 1138 else 1139 { 1140 ABORT_ERROR("frame for never-initiated stream"); 1141 lsquic_malo_put(stream_frame); 1142 return 0; 1143 } 1144 stream = new_stream(conn, stream_frame->stream_id, SCF_CALL_ON_NEW); 1145 if (!stream) 1146 { 1147 ABORT_ERROR("cannot create new stream: %s", strerror(errno)); 1148 lsquic_malo_put(stream_frame); 1149 return 0; 1150 } 1151 if (stream_frame->stream_id > conn->fc_max_peer_stream_id) 1152 conn->fc_max_peer_stream_id = stream_frame->stream_id; 1153 } 1154 1155 stream_frame->packet_in = lsquic_packet_in_get(packet_in); 1156 if (0 != lsquic_stream_frame_in(stream, stream_frame)) 1157 { 1158 ABORT_ERROR("cannot insert stream frame"); 1159 return 0; 1160 } 1161 1162 if (stream->id == LSQUIC_STREAM_HANDSHAKE 1163 && !(conn->fc_flags & FC_SERVER) 1164 && !(conn->fc_conn.cn_flags & LSCONN_HANDSHAKE_DONE)) 1165 { /* To enable decryption, process handshake stream as soon as its 1166 * data frames are received. 1167 * 1168 * TODO: this does not work when packets are reordered. A more 1169 * flexible solution would defer packet decryption if handshake 1170 * has not been completed yet. Nevertheless, this is good enough 1171 * for now. 1172 */ 1173 lsquic_stream_dispatch_read_events(stream); 1174 } 1175 1176 return parsed_len; 1177} 1178 1179 1180static unsigned 1181process_invalid_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1182 const unsigned char *p, size_t len) 1183{ 1184 ABORT_ERROR("invalid frame"); 1185 return 0; 1186} 1187 1188 1189/* Reset locally-initiated streams whose IDs is larger than the stream ID 1190 * specified in received GOAWAY frame. 1191 */ 1192static void 1193reset_local_streams_over_goaway (struct full_conn *conn) 1194{ 1195 const unsigned is_server = !!(conn->fc_flags & FC_SERVER); 1196 lsquic_stream_t *stream; 1197 struct lsquic_hash_elem *el; 1198 1199 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 1200 el = lsquic_hash_next(conn->fc_pub.all_streams)) 1201 { 1202 stream = lsquic_hashelem_getdata(el); 1203 if (stream->id > conn->fc_goaway_stream_id && 1204 ((stream->id & 1) ^ is_server /* Locally initiated? */)) 1205 { 1206 lsquic_stream_received_goaway(stream); 1207 } 1208 } 1209} 1210 1211 1212static unsigned 1213process_goaway_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1214 const unsigned char *p, size_t len) 1215{ 1216 uint32_t error_code, stream_id; 1217 uint16_t reason_length; 1218 const char *reason; 1219 const int parsed_len = conn->fc_conn.cn_pf->pf_parse_goaway_frame(p, len, 1220 &error_code, &stream_id, &reason_length, &reason); 1221 if (parsed_len < 0) 1222 return 0; 1223 EV_LOG_GOAWAY_FRAME_IN(LSQUIC_LOG_CONN_ID, error_code, stream_id, 1224 reason_length, reason); 1225 LSQ_DEBUG("received GOAWAY frame, last good stream ID: %u, error code: 0x%X," 1226 " reason: `%.*s'", stream_id, error_code, reason_length, reason); 1227 if (0 == (conn->fc_conn.cn_flags & LSCONN_PEER_GOING_AWAY)) 1228 { 1229 conn->fc_conn.cn_flags |= LSCONN_PEER_GOING_AWAY; 1230 conn->fc_goaway_stream_id = stream_id; 1231 if (conn->fc_stream_ifs[STREAM_IF_STD].stream_if->on_goaway_received) 1232 { 1233 LSQ_DEBUG("calling on_goaway_received"); 1234 conn->fc_stream_ifs[STREAM_IF_STD].stream_if->on_goaway_received( 1235 &conn->fc_conn); 1236 } 1237 else 1238 LSQ_DEBUG("on_goaway_received not registered"); 1239 reset_local_streams_over_goaway(conn); 1240 } 1241 else 1242 LSQ_DEBUG("ignore duplicate GOAWAY frame"); 1243 return parsed_len; 1244} 1245 1246 1247static void 1248log_invalid_ack_frame (struct full_conn *conn, const unsigned char *p, 1249 int parsed_len, const struct ack_info *acki) 1250{ 1251 char *buf; 1252 size_t sz; 1253 1254 buf = malloc(0x1000); 1255 if (buf) 1256 { 1257 lsquic_senhist_tostr(&conn->fc_send_ctl.sc_senhist, buf, 0x1000); 1258 LSQ_WARN("send history: %s", buf); 1259 hexdump(p, parsed_len, buf, 0x1000); 1260 LSQ_WARN("raw ACK frame:\n%s", buf); 1261 free(buf); 1262 } 1263 else 1264 LSQ_WARN("malloc failed"); 1265 1266 buf = acki2str(acki, &sz); 1267 if (buf) 1268 { 1269 LSQ_WARN("parsed ACK frame: %.*s", (int) sz, buf); 1270 free(buf); 1271 } 1272 else 1273 LSQ_WARN("malloc failed"); 1274} 1275 1276 1277static int 1278process_ack (struct full_conn *conn, struct ack_info *acki, 1279 lsquic_time_t received) 1280{ 1281#if FULL_CONN_STATS 1282 ++conn->fc_stats.n_acks_proc; 1283#endif 1284 LSQ_DEBUG("Processing ACK"); 1285 if (0 == lsquic_send_ctl_got_ack(&conn->fc_send_ctl, acki, received)) 1286 { 1287 if (lsquic_send_ctl_largest_ack2ed(&conn->fc_send_ctl)) 1288 lsquic_rechist_stop_wait(&conn->fc_rechist, 1289 lsquic_send_ctl_largest_ack2ed(&conn->fc_send_ctl) + 1); 1290 return 0; 1291 } 1292 else 1293 { 1294 ABORT_ERROR("Received invalid ACK"); 1295 return -1; 1296 } 1297} 1298 1299 1300static int 1301process_saved_ack (struct full_conn *conn, int restore_parsed_ack) 1302{ 1303 struct ack_info *const acki = conn->fc_pub.mm->acki; 1304 struct lsquic_packno_range range; 1305 unsigned n_ranges, n_timestamps; 1306 lsquic_time_t lack_delta; 1307 int retval; 1308 1309#ifdef WIN32 1310 /* Useless initialization to mollify MSVC: */ 1311 memset(&range, 0, sizeof(range)); 1312 n_ranges = 0; 1313 n_timestamps = 0; 1314 lack_delta = 0; 1315#endif 1316 1317 if (restore_parsed_ack) 1318 { 1319 n_ranges = acki->n_ranges; 1320 n_timestamps = acki->n_timestamps; 1321 lack_delta = acki->lack_delta; 1322 range = acki->ranges[0]; 1323 } 1324 1325 acki->n_ranges = 1; 1326 acki->n_timestamps = conn->fc_saved_ack_info.sai_n_timestamps; 1327 acki->lack_delta = conn->fc_saved_ack_info.sai_lack_delta; 1328 acki->ranges[0] = conn->fc_saved_ack_info.sai_range; 1329 1330 retval = process_ack(conn, acki, conn->fc_saved_ack_received); 1331 1332 if (restore_parsed_ack) 1333 { 1334 acki->n_ranges = n_ranges; 1335 acki->n_timestamps = n_timestamps; 1336 acki->lack_delta = lack_delta; 1337 acki->ranges[0] = range; 1338 } 1339 1340 return retval; 1341} 1342 1343 1344static int 1345new_ack_is_superset (const struct short_ack_info *old, const struct ack_info *new) 1346{ 1347 const struct lsquic_packno_range *new_range; 1348 1349 new_range = &new->ranges[ new->n_ranges - 1 ]; 1350 return new_range->low <= old->sai_range.low 1351 && new_range->high >= old->sai_range.high; 1352} 1353 1354 1355static int 1356merge_saved_to_new (const struct short_ack_info *old, struct ack_info *new) 1357{ 1358 struct lsquic_packno_range *smallest_range; 1359 1360 assert(new->n_ranges > 1); 1361 smallest_range = &new->ranges[ new->n_ranges - 1 ]; 1362 if (old->sai_range.high <= smallest_range->high 1363 && old->sai_range.high >= smallest_range->low 1364 && old->sai_range.low < smallest_range->low) 1365 { 1366 smallest_range->low = old->sai_range.low; 1367 return 1; 1368 } 1369 else 1370 return 0; 1371} 1372 1373 1374static int 1375merge_new_to_saved (struct short_ack_info *old, const struct ack_info *new) 1376{ 1377 const struct lsquic_packno_range *new_range; 1378 1379 assert(new->n_ranges == 1); 1380 new_range = &new->ranges[0]; 1381 /* Only merge if new is higher, for simplicity. This is also the 1382 * expected case. 1383 */ 1384 if (new_range->high > old->sai_range.high 1385 && new_range->low > old->sai_range.low) 1386 { 1387 old->sai_range.high = new_range->high; 1388 return 1; 1389 } 1390 else 1391 return 0; 1392} 1393 1394 1395static unsigned 1396process_ack_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1397 const unsigned char *p, size_t len) 1398{ 1399 struct ack_info *const new_acki = conn->fc_pub.mm->acki; 1400 int parsed_len; 1401 1402#if FULL_CONN_STATS 1403 ++conn->fc_stats.n_acks_in; 1404#endif 1405 1406 parsed_len = conn->fc_conn.cn_pf->pf_parse_ack_frame(p, len, new_acki); 1407 if (parsed_len < 0) 1408 goto err; 1409 1410 if (packet_in->pi_packno <= conn->fc_max_ack_packno) 1411 { 1412 LSQ_DEBUG("Ignore old ack (max %"PRIu64")", conn->fc_max_ack_packno); 1413 return parsed_len; 1414 } 1415 1416 EV_LOG_ACK_FRAME_IN(LSQUIC_LOG_CONN_ID, new_acki); 1417 conn->fc_max_ack_packno = packet_in->pi_packno; 1418 1419 if (conn->fc_flags & FC_HAVE_SAVED_ACK) 1420 { 1421 LSQ_DEBUG("old ack [%"PRIu64"-%"PRIu64"]", 1422 conn->fc_saved_ack_info.sai_range.high, 1423 conn->fc_saved_ack_info.sai_range.low); 1424 const int is_superset = new_ack_is_superset(&conn->fc_saved_ack_info, 1425 new_acki); 1426 const int is_1range = new_acki->n_ranges == 1; 1427 switch ( 1428 (is_superset << 1) 1429 | (is_1range << 0)) 1430 /* | | 1431 | | 1432 V V */ { 1433 case (0 << 1) | (0 << 0): 1434 if (merge_saved_to_new(&conn->fc_saved_ack_info, new_acki)) 1435 { 1436#if FULL_CONN_STATS 1437 ++conn->fc_stats.n_acks_merged[0] 1438#endif 1439 ; 1440 } 1441 else 1442 process_saved_ack(conn, 1); 1443 conn->fc_flags &= ~FC_HAVE_SAVED_ACK; 1444 if (0 != process_ack(conn, new_acki, packet_in->pi_received)) 1445 goto err; 1446 break; 1447 case (0 << 1) | (1 << 0): 1448 if (merge_new_to_saved(&conn->fc_saved_ack_info, new_acki)) 1449 { 1450#if FULL_CONN_STATS 1451 ++conn->fc_stats.n_acks_merged[1] 1452#endif 1453 ; 1454 } 1455 else 1456 { 1457 process_saved_ack(conn, 1); 1458 conn->fc_saved_ack_info.sai_n_timestamps = new_acki->n_timestamps; 1459 conn->fc_saved_ack_info.sai_range = new_acki->ranges[0]; 1460 } 1461 conn->fc_saved_ack_info.sai_lack_delta = new_acki->lack_delta; 1462 conn->fc_saved_ack_received = packet_in->pi_received; 1463 break; 1464 case (1 << 1) | (0 << 0): 1465 conn->fc_flags &= ~FC_HAVE_SAVED_ACK; 1466 if (0 != process_ack(conn, new_acki, packet_in->pi_received)) 1467 goto err; 1468 break; 1469 case (1 << 1) | (1 << 0): 1470 conn->fc_saved_ack_info.sai_n_timestamps = new_acki->n_timestamps; 1471 conn->fc_saved_ack_info.sai_lack_delta = new_acki->lack_delta; 1472 conn->fc_saved_ack_info.sai_range = new_acki->ranges[0]; 1473 conn->fc_saved_ack_received = packet_in->pi_received; 1474 break; 1475 } 1476 } 1477 else if (new_acki->n_ranges == 1) 1478 { 1479 conn->fc_saved_ack_info.sai_n_timestamps = new_acki->n_timestamps; 1480 conn->fc_saved_ack_info.sai_lack_delta = new_acki->lack_delta; 1481 conn->fc_saved_ack_info.sai_range = new_acki->ranges[0]; 1482 conn->fc_saved_ack_received = packet_in->pi_received; 1483 conn->fc_flags |= FC_HAVE_SAVED_ACK; 1484 } 1485 else if (0 != process_ack(conn, new_acki, packet_in->pi_received)) 1486 goto err; 1487 1488 return parsed_len; 1489 1490 err: 1491 log_invalid_ack_frame(conn, p, parsed_len, new_acki); 1492 return 0; 1493} 1494 1495 1496static unsigned 1497process_stop_waiting_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1498 const unsigned char *p, size_t len) 1499{ 1500 lsquic_packno_t least, cutoff; 1501 enum lsquic_packno_bits bits; 1502 int parsed_len; 1503 1504 bits = lsquic_packet_in_packno_bits(packet_in); 1505 1506 if (conn->fc_flags & FC_NSTP) 1507 { 1508 LSQ_DEBUG("NSTP on: ignore STOP_WAITING frame"); 1509 parsed_len = conn->fc_conn.cn_pf->pf_skip_stop_waiting_frame(len, bits); 1510 if (parsed_len > 0) 1511 return (unsigned) parsed_len; 1512 else 1513 return 0; 1514 } 1515 1516 parsed_len = conn->fc_conn.cn_pf->pf_parse_stop_waiting_frame(p, len, 1517 packet_in->pi_packno, bits, &least); 1518 if (parsed_len < 0) 1519 return 0; 1520 1521 if (packet_in->pi_packno <= conn->fc_max_swf_packno) 1522 { 1523 LSQ_DEBUG("ignore old STOP_WAITING frame"); 1524 return parsed_len; 1525 } 1526 1527 LSQ_DEBUG("Got STOP_WAITING frame, least unacked: %"PRIu64, least); 1528 EV_LOG_STOP_WAITING_FRAME_IN(LSQUIC_LOG_CONN_ID, least); 1529 1530 if (least > packet_in->pi_packno) 1531 { 1532 ABORT_ERROR("received invalid STOP_WAITING: %"PRIu64" is larger " 1533 "than the packet number%"PRIu64, least, packet_in->pi_packno); 1534 return 0; 1535 } 1536 1537 cutoff = lsquic_rechist_cutoff(&conn->fc_rechist); 1538 if (cutoff && least < cutoff) 1539 { 1540 ABORT_ERROR("received invalid STOP_WAITING: %"PRIu64" is smaller " 1541 "than the cutoff %"PRIu64, least, cutoff); 1542 return 0; 1543 } 1544 1545 conn->fc_max_swf_packno = packet_in->pi_packno; 1546 lsquic_rechist_stop_wait(&conn->fc_rechist, least); 1547 return parsed_len; 1548} 1549 1550 1551static unsigned 1552process_blocked_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1553 const unsigned char *p, size_t len) 1554{ 1555 uint32_t stream_id; 1556 const int parsed_len = conn->fc_conn.cn_pf->pf_parse_blocked_frame(p, len, 1557 &stream_id); 1558 if (parsed_len < 0) 1559 return 0; 1560 EV_LOG_BLOCKED_FRAME_IN(LSQUIC_LOG_CONN_ID, stream_id); 1561 LSQ_DEBUG("Peer reports stream %u as blocked", stream_id); 1562 return parsed_len; 1563} 1564 1565 1566static unsigned 1567process_connection_close_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1568 const unsigned char *p, size_t len) 1569{ 1570 lsquic_stream_t *stream; 1571 struct lsquic_hash_elem *el; 1572 uint32_t error_code; 1573 uint16_t reason_len; 1574 uint8_t reason_off; 1575 int parsed_len; 1576 1577 parsed_len = conn->fc_conn.cn_pf->pf_parse_connect_close_frame(p, len, 1578 &error_code, &reason_len, &reason_off); 1579 if (parsed_len < 0) 1580 return 0; 1581 EV_LOG_CONNECTION_CLOSE_FRAME_IN(LSQUIC_LOG_CONN_ID, error_code, 1582 (int) reason_len, (const char *) p + reason_off); 1583 LSQ_INFO("Received CONNECTION_CLOSE frame (code: %u; reason: %.*s)", 1584 error_code, (int) reason_len, (const char *) p + reason_off); 1585 conn->fc_flags |= FC_RECV_CLOSE; 1586 if (!(conn->fc_flags & FC_CLOSING)) 1587 { 1588 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 1589 el = lsquic_hash_next(conn->fc_pub.all_streams)) 1590 { 1591 stream = lsquic_hashelem_getdata(el); 1592 lsquic_stream_shutdown_internal(stream); 1593 } 1594 conn->fc_flags |= FC_CLOSING; 1595 } 1596 return parsed_len; 1597} 1598 1599 1600static unsigned 1601process_rst_stream_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1602 const unsigned char *p, size_t len) 1603{ 1604 uint32_t stream_id, error_code; 1605 uint64_t offset; 1606 lsquic_stream_t *stream; 1607 const int parsed_len = conn->fc_conn.cn_pf->pf_parse_rst_frame(p, len, 1608 &stream_id, &offset, &error_code); 1609 if (parsed_len < 0) 1610 return 0; 1611 1612 EV_LOG_RST_STREAM_FRAME_IN(LSQUIC_LOG_CONN_ID, stream_id, offset, 1613 error_code); 1614 LSQ_DEBUG("Got RST_STREAM; stream: %u; offset: 0x%"PRIX64, stream_id, 1615 offset); 1616 if (0 == stream_id) 1617 { /* Follow reference implementation and ignore this apparently 1618 * invalid frame. 1619 */ 1620 return parsed_len; 1621 } 1622 1623 if (LSQUIC_STREAM_HANDSHAKE == stream_id || 1624 ((conn->fc_flags & FC_HTTP) && LSQUIC_STREAM_HEADERS == stream_id)) 1625 { 1626 ABORT_ERROR("received reset on static stream %u", stream_id); 1627 return 0; 1628 } 1629 1630 stream = find_stream_by_id(conn, stream_id); 1631 if (!stream) 1632 { 1633 if (conn_is_stream_closed(conn, stream_id)) 1634 { 1635 LSQ_DEBUG("got reset frame for closed stream %u", stream_id); 1636 return parsed_len; 1637 } 1638 if (!is_peer_initiated(conn, stream_id)) 1639 { 1640 ABORT_ERROR("received reset for never-initiated stream %u", 1641 stream_id); 1642 return 0; 1643 } 1644 stream = new_stream(conn, stream_id, SCF_CALL_ON_NEW); 1645 if (!stream) 1646 { 1647 ABORT_ERROR("cannot create new stream: %s", strerror(errno)); 1648 return 0; 1649 } 1650 if (stream_id > conn->fc_max_peer_stream_id) 1651 conn->fc_max_peer_stream_id = stream_id; 1652 } 1653 1654 if (0 != lsquic_stream_rst_in(stream, offset, error_code)) 1655 { 1656 ABORT_ERROR("received invalid RST_STREAM"); 1657 return 0; 1658 } 1659 return parsed_len; 1660} 1661 1662 1663static unsigned 1664process_window_update_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1665 const unsigned char *p, size_t len) 1666{ 1667 uint32_t stream_id; 1668 uint64_t offset; 1669 const int parsed_len = 1670 conn->fc_conn.cn_pf->pf_parse_window_update_frame(p, len, 1671 &stream_id, &offset); 1672 if (parsed_len < 0) 1673 return 0; 1674 EV_LOG_WINDOW_UPDATE_FRAME_IN(LSQUIC_LOG_CONN_ID, stream_id, offset); 1675 if (stream_id) 1676 { 1677 lsquic_stream_t *stream = find_stream_by_id(conn, stream_id); 1678 if (stream) 1679 { 1680 LSQ_DEBUG("Got window update frame, stream: %u; offset: 0x%"PRIX64, 1681 stream_id, offset); 1682 lsquic_stream_window_update(stream, offset); 1683 } 1684 else /* Perhaps a result of lost packets? */ 1685 LSQ_DEBUG("Got window update frame for non-existing stream %u " 1686 "(offset: 0x%"PRIX64")", stream_id, offset); 1687 } 1688 else if (offset > conn->fc_pub.conn_cap.cc_max) 1689 { 1690 conn->fc_pub.conn_cap.cc_max = offset; 1691 assert(conn->fc_pub.conn_cap.cc_max >= conn->fc_pub.conn_cap.cc_sent); 1692 LSQ_DEBUG("Connection WUF, new offset 0x%"PRIX64, offset); 1693 } 1694 else 1695 LSQ_DEBUG("Throw ouw duplicate connection WUF"); 1696 return parsed_len; 1697} 1698 1699 1700typedef unsigned (*process_frame_f)( 1701 struct full_conn *, lsquic_packet_in_t *, const unsigned char *p, size_t); 1702 1703static process_frame_f const process_frames[N_QUIC_FRAMES] = 1704{ 1705 [QUIC_FRAME_ACK] = process_ack_frame, 1706 [QUIC_FRAME_BLOCKED] = process_blocked_frame, 1707 [QUIC_FRAME_CONNECTION_CLOSE] = process_connection_close_frame, 1708 [QUIC_FRAME_GOAWAY] = process_goaway_frame, 1709 [QUIC_FRAME_INVALID] = process_invalid_frame, 1710 [QUIC_FRAME_PADDING] = process_padding_frame, 1711 [QUIC_FRAME_PING] = process_ping_frame, 1712 [QUIC_FRAME_RST_STREAM] = process_rst_stream_frame, 1713 [QUIC_FRAME_STOP_WAITING] = process_stop_waiting_frame, 1714 [QUIC_FRAME_STREAM] = process_stream_frame, 1715 [QUIC_FRAME_WINDOW_UPDATE] = process_window_update_frame, 1716}; 1717 1718static unsigned 1719process_packet_frame (struct full_conn *conn, lsquic_packet_in_t *packet_in, 1720 const unsigned char *p, size_t len) 1721{ 1722 enum QUIC_FRAME_TYPE type = conn->fc_conn.cn_pf->pf_parse_frame_type(p[0]); 1723 packet_in->pi_frame_types |= 1 << type; 1724 recent_packet_hist_frames(conn, 0, 1 << type); 1725 return process_frames[type](conn, packet_in, p, len); 1726} 1727 1728 1729static void 1730process_ver_neg_packet (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1731{ 1732 int s; 1733 struct ver_iter vi; 1734 lsquic_ver_tag_t ver_tag; 1735 enum lsquic_version version; 1736 unsigned versions = 0; 1737 1738 LSQ_DEBUG("Processing version-negotiation packet"); 1739 1740 if (conn->fc_ver_neg.vn_state != VN_START) 1741 { 1742 LSQ_DEBUG("ignore a likely duplicate version negotiation packet"); 1743 return; 1744 } 1745 1746 for (s = packet_in_ver_first(packet_in, &vi, &ver_tag); s; 1747 s = packet_in_ver_next(&vi, &ver_tag)) 1748 { 1749 version = lsquic_tag2ver(ver_tag); 1750 if (version < N_LSQVER) 1751 { 1752 versions |= 1 << version; 1753 LSQ_DEBUG("server supports version %s", lsquic_ver2str[version]); 1754 } 1755 } 1756 1757 if (versions & (1 << conn->fc_ver_neg.vn_ver)) 1758 { 1759 ABORT_ERROR("server replied with version we support: %s", 1760 lsquic_ver2str[conn->fc_ver_neg.vn_ver]); 1761 return; 1762 } 1763 1764 versions &= conn->fc_ver_neg.vn_supp; 1765 if (0 == versions) 1766 { 1767 ABORT_ERROR("client does not support any of the server-specified " 1768 "versions"); 1769 return; 1770 } 1771 1772 set_versions(conn, versions); 1773 conn->fc_ver_neg.vn_state = VN_IN_PROGRESS; 1774 lsquic_send_ctl_expire_all(&conn->fc_send_ctl); 1775} 1776 1777 1778static void 1779reconstruct_packet_number (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1780{ 1781 lsquic_packno_t cur_packno, max_packno; 1782 enum lsquic_packno_bits bits; 1783 1784 cur_packno = packet_in->pi_packno; 1785 max_packno = lsquic_rechist_largest_packno(&conn->fc_rechist); 1786 bits = lsquic_packet_in_packno_bits(packet_in); 1787 packet_in->pi_packno = restore_packno(cur_packno, bits, max_packno); 1788 LSQ_DEBUG("reconstructed (bits: %u, packno: %"PRIu64", max: %"PRIu64") " 1789 "to %"PRIu64"", bits, cur_packno, max_packno, packet_in->pi_packno); 1790} 1791 1792 1793static int 1794conn_decrypt_packet (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1795{ 1796 return lsquic_conn_decrypt_packet(&conn->fc_conn, conn->fc_enpub, 1797 packet_in); 1798} 1799 1800 1801static void 1802parse_regular_packet (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1803{ 1804 const unsigned char *p, *pend; 1805 unsigned len; 1806 1807 p = packet_in->pi_data + packet_in->pi_header_sz; 1808 pend = packet_in->pi_data + packet_in->pi_data_sz; 1809 1810 while (p < pend) 1811 { 1812 len = process_packet_frame(conn, packet_in, p, pend - p); 1813 if (len > 0) 1814 p += len; 1815 else 1816 { 1817 ABORT_ERROR("Error parsing frame"); 1818 break; 1819 } 1820 } 1821} 1822 1823 1824static int 1825process_regular_packet (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1826{ 1827 enum received_st st; 1828 enum quic_ft_bit frame_types; 1829 int was_missing; 1830 1831 reconstruct_packet_number(conn, packet_in); 1832 EV_LOG_PACKET_IN(LSQUIC_LOG_CONN_ID, packet_in); 1833 1834#if FULL_CONN_STATS 1835 ++conn->fc_stats.n_all_packets_in; 1836#endif 1837 1838 /* The packet is decrypted before receive history is updated. This is 1839 * done to make sure that a bad packet won't occupy a slot in receive 1840 * history and subsequent good packet won't be marked as a duplicate. 1841 */ 1842 if (0 == (packet_in->pi_flags & PI_DECRYPTED) && 1843 0 != conn_decrypt_packet(conn, packet_in)) 1844 { 1845 LSQ_INFO("could not decrypt packet"); 1846#if FULL_CONN_STATS 1847 ++conn->fc_stats.n_undec_packets; 1848#endif 1849 return 0; 1850 } 1851 1852 st = lsquic_rechist_received(&conn->fc_rechist, packet_in->pi_packno, 1853 packet_in->pi_received); 1854 switch (st) { 1855 case REC_ST_OK: 1856 parse_regular_packet(conn, packet_in); 1857 if (0 == (conn->fc_flags & FC_ACK_QUEUED)) 1858 { 1859 frame_types = packet_in->pi_frame_types; 1860 was_missing = packet_in->pi_packno != 1861 lsquic_rechist_largest_packno(&conn->fc_rechist); 1862 conn->fc_n_slack_all += 1; 1863 conn->fc_n_slack_akbl += !!(frame_types & QFRAME_ACKABLE_MASK); 1864 try_queueing_ack(conn, was_missing, packet_in->pi_received); 1865 } 1866 return 0; 1867 case REC_ST_DUP: 1868#if FULL_CONN_STATS 1869 ++conn->fc_stats.n_dup_packets; 1870#endif 1871 LSQ_INFO("packet %"PRIu64" is a duplicate", packet_in->pi_packno); 1872 return 0; 1873 default: 1874 assert(0); 1875 /* Fall through */ 1876 case REC_ST_ERR: 1877#if FULL_CONN_STATS 1878 ++conn->fc_stats.n_err_packets; 1879#endif 1880 LSQ_INFO("error processing packet %"PRIu64, packet_in->pi_packno); 1881 return -1; 1882 } 1883} 1884 1885 1886static int 1887process_incoming_packet (struct full_conn *conn, lsquic_packet_in_t *packet_in) 1888{ 1889 recent_packet_hist_new(conn, 0, packet_in->pi_received); 1890 LSQ_DEBUG("Processing packet %"PRIu64, packet_in->pi_packno); 1891 /* See flowchart in Section 4.1 of [draft-ietf-quic-transport-00]. We test 1892 * for the common case first. 1893 */ 1894 const unsigned flags = lsquic_packet_in_public_flags(packet_in); 1895 if (0 == (flags & (PACKET_PUBLIC_FLAGS_RST|PACKET_PUBLIC_FLAGS_VERSION))) 1896 { 1897 if (conn->fc_ver_neg.vn_tag) 1898 { 1899 assert(conn->fc_ver_neg.vn_state != VN_END); 1900 conn->fc_ver_neg.vn_state = VN_END; 1901 conn->fc_ver_neg.vn_tag = NULL; 1902 conn->fc_conn.cn_version = conn->fc_ver_neg.vn_ver; 1903 conn->fc_conn.cn_flags |= LSCONN_VER_SET; 1904 if (conn->fc_conn.cn_version >= LSQVER_037) 1905 { 1906 assert(!(conn->fc_flags & FC_NSTP)); /* This bit off at start */ 1907 if (conn->fc_settings->es_support_nstp) 1908 { 1909 conn->fc_flags |= FC_NSTP; 1910 lsquic_send_ctl_turn_nstp_on(&conn->fc_send_ctl); 1911 } 1912 } 1913 LSQ_DEBUG("end of version negotiation: agreed upon %s", 1914 lsquic_ver2str[conn->fc_ver_neg.vn_ver]); 1915 } 1916 return process_regular_packet(conn, packet_in); 1917 } 1918 else if (flags & PACKET_PUBLIC_FLAGS_RST) 1919 { 1920 LSQ_INFO("received public reset packet: aborting connection"); 1921 conn->fc_flags |= FC_GOT_PRST; 1922 return -1; 1923 } 1924 else 1925 { 1926 if (conn->fc_flags & FC_SERVER) 1927 return process_regular_packet(conn, packet_in); 1928 else if (conn->fc_ver_neg.vn_tag) 1929 { 1930 process_ver_neg_packet(conn, packet_in); 1931 return 0; 1932 } 1933 else 1934 { 1935 LSQ_DEBUG("unexpected version negotiation packet: ignore it"); 1936 return 0; 1937 } 1938 } 1939} 1940 1941 1942static void 1943idle_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now) 1944{ 1945 struct full_conn *conn = ctx; 1946 LSQ_DEBUG("connection timed out"); 1947 conn->fc_flags |= FC_TIMED_OUT; 1948} 1949 1950 1951static void 1952handshake_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now) 1953{ 1954 struct full_conn *conn = ctx; 1955 LSQ_DEBUG("connection timed out: handshake timed out"); 1956 conn->fc_flags |= FC_TIMED_OUT; 1957} 1958 1959 1960static void 1961ping_alarm_expired (void *ctx, lsquic_time_t expiry, lsquic_time_t now) 1962{ 1963 struct full_conn *conn = ctx; 1964 LSQ_DEBUG("Ping alarm rang: schedule PING frame to be generated"); 1965 conn->fc_flags |= FC_SEND_PING; 1966} 1967 1968 1969static lsquic_packet_out_t * 1970get_writeable_packet (struct full_conn *conn, unsigned need_at_least) 1971{ 1972 lsquic_packet_out_t *packet_out; 1973 int is_err; 1974 1975 assert(need_at_least <= QUIC_MAX_PAYLOAD_SZ); 1976 packet_out = lsquic_send_ctl_get_writeable_packet(&conn->fc_send_ctl, 1977 need_at_least, &is_err); 1978 if (!packet_out && is_err) 1979 ABORT_ERROR("cannot allocate packet: %s", strerror(errno)); 1980 return packet_out; 1981} 1982 1983 1984static int 1985generate_wuf_stream (struct full_conn *conn, lsquic_stream_t *stream) 1986{ 1987 lsquic_packet_out_t *packet_out = get_writeable_packet(conn, QUIC_WUF_SZ); 1988 if (!packet_out) 1989 return 0; 1990 const uint64_t recv_off = lsquic_stream_fc_recv_off(stream); 1991 int sz = conn->fc_conn.cn_pf->pf_gen_window_update_frame( 1992 packet_out->po_data + packet_out->po_data_sz, 1993 lsquic_packet_out_avail(packet_out), stream->id, recv_off); 1994 if (sz < 0) { 1995 ABORT_ERROR("gen_window_update_frame failed"); 1996 return 0; 1997 } 1998 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 1999 packet_out->po_frame_types |= 1 << QUIC_FRAME_WINDOW_UPDATE; 2000 LSQ_DEBUG("wrote WUF: stream %u; offset 0x%"PRIX64, stream->id, recv_off); 2001 return 1; 2002} 2003 2004 2005static void 2006generate_wuf_conn (struct full_conn *conn) 2007{ 2008 assert(conn->fc_flags & FC_SEND_WUF); 2009 lsquic_packet_out_t *packet_out = get_writeable_packet(conn, QUIC_WUF_SZ); 2010 if (!packet_out) 2011 return; 2012 const uint64_t recv_off = lsquic_cfcw_get_fc_recv_off(&conn->fc_pub.cfcw); 2013 int sz = conn->fc_conn.cn_pf->pf_gen_window_update_frame( 2014 packet_out->po_data + packet_out->po_data_sz, 2015 lsquic_packet_out_avail(packet_out), 0, recv_off); 2016 if (sz < 0) { 2017 ABORT_ERROR("gen_window_update_frame failed"); 2018 return; 2019 } 2020 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2021 packet_out->po_frame_types |= 1 << QUIC_FRAME_WINDOW_UPDATE; 2022 conn->fc_flags &= ~FC_SEND_WUF; 2023 LSQ_DEBUG("wrote connection WUF: offset 0x%"PRIX64, recv_off); 2024} 2025 2026 2027static void 2028generate_goaway_frame (struct full_conn *conn) 2029{ 2030 int reason_len = 0; 2031 lsquic_packet_out_t *packet_out = 2032 get_writeable_packet(conn, QUIC_GOAWAY_FRAME_SZ + reason_len); 2033 if (!packet_out) 2034 return; 2035 int sz = conn->fc_conn.cn_pf->pf_gen_goaway_frame( 2036 packet_out->po_data + packet_out->po_data_sz, 2037 lsquic_packet_out_avail(packet_out), 0, conn->fc_max_peer_stream_id, 2038 NULL, reason_len); 2039 if (sz < 0) { 2040 ABORT_ERROR("gen_goaway_frame failed"); 2041 return; 2042 } 2043 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2044 packet_out->po_frame_types |= 1 << QUIC_FRAME_GOAWAY; 2045 conn->fc_flags &= ~FC_SEND_GOAWAY; 2046 conn->fc_flags |= FC_GOAWAY_SENT; 2047 LSQ_DEBUG("wrote GOAWAY frame: stream id: %u", conn->fc_max_peer_stream_id); 2048} 2049 2050 2051static void 2052generate_connection_close_packet (struct full_conn *conn) 2053{ 2054 lsquic_packet_out_t *packet_out; 2055 2056 packet_out = lsquic_send_ctl_new_packet_out(&conn->fc_send_ctl, 0); 2057 if (!packet_out) 2058 { 2059 ABORT_ERROR("cannot allocate packet: %s", strerror(errno)); 2060 return; 2061 } 2062 2063 lsquic_send_ctl_scheduled_one(&conn->fc_send_ctl, packet_out); 2064 int sz = conn->fc_conn.cn_pf->pf_gen_connect_close_frame(packet_out->po_data + packet_out->po_data_sz, 2065 lsquic_packet_out_avail(packet_out), 16 /* PEER_GOING_AWAY */, 2066 NULL, 0); 2067 if (sz < 0) { 2068 ABORT_ERROR("generate_connection_close_packet failed"); 2069 return; 2070 } 2071 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2072 packet_out->po_frame_types |= 1 << QUIC_FRAME_CONNECTION_CLOSE; 2073 LSQ_DEBUG("generated CONNECTION_CLOSE frame in its own packet"); 2074} 2075 2076 2077static int 2078generate_blocked_frame (struct full_conn *conn, uint32_t stream_id) 2079{ 2080 lsquic_packet_out_t *packet_out = 2081 get_writeable_packet(conn, QUIC_BLOCKED_FRAME_SZ); 2082 if (!packet_out) 2083 return 0; 2084 int sz = conn->fc_conn.cn_pf->pf_gen_blocked_frame( 2085 packet_out->po_data + packet_out->po_data_sz, 2086 lsquic_packet_out_avail(packet_out), stream_id); 2087 if (sz < 0) { 2088 ABORT_ERROR("gen_blocked_frame failed"); 2089 return 0; 2090 } 2091 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2092 packet_out->po_frame_types |= 1 << QUIC_FRAME_BLOCKED; 2093 LSQ_DEBUG("wrote blocked frame: stream %u", stream_id); 2094 return 1; 2095} 2096 2097 2098static int 2099generate_stream_blocked_frame (struct full_conn *conn, lsquic_stream_t *stream) 2100{ 2101 if (generate_blocked_frame(conn, stream->id)) 2102 { 2103 lsquic_stream_blocked_frame_sent(stream); 2104 return 1; 2105 } 2106 else 2107 return 0; 2108} 2109 2110 2111static int 2112generate_rst_stream_frame (struct full_conn *conn, lsquic_stream_t *stream) 2113{ 2114 lsquic_packet_out_t *packet_out; 2115 int sz, s; 2116 2117 packet_out = get_writeable_packet(conn, QUIC_RST_STREAM_SZ); 2118 if (!packet_out) 2119 return 0; 2120 /* TODO Possible optimization: instead of using stream->tosend_off as the 2121 * offset, keep track of the offset that was actually sent: include it 2122 * into stream_rec and update a new per-stream "maximum offset actually 2123 * sent" field. Then, if a stream is reset, the connection cap can be 2124 * increased. 2125 */ 2126 sz = conn->fc_conn.cn_pf->pf_gen_rst_frame( 2127 packet_out->po_data + packet_out->po_data_sz, 2128 lsquic_packet_out_avail(packet_out), stream->id, 2129 stream->tosend_off, stream->error_code); 2130 if (sz < 0) { 2131 ABORT_ERROR("gen_rst_frame failed"); 2132 return 0; 2133 } 2134 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2135 packet_out->po_frame_types |= 1 << QUIC_FRAME_RST_STREAM; 2136 s = lsquic_packet_out_add_stream(packet_out, conn->fc_pub.mm, stream, 2137 QUIC_FRAME_RST_STREAM, 0, 0); 2138 if (s != 0) 2139 { 2140 ABORT_ERROR("adding stream to packet failed: %s", strerror(errno)); 2141 return 0; 2142 } 2143 lsquic_stream_rst_frame_sent(stream); 2144 LSQ_DEBUG("wrote RST: stream %u; offset 0x%"PRIX64"; error code 0x%X", 2145 stream->id, stream->tosend_off, stream->error_code); 2146 return 1; 2147} 2148 2149 2150static void 2151generate_ping_frame (struct full_conn *conn) 2152{ 2153 lsquic_packet_out_t *packet_out = get_writeable_packet(conn, 1); 2154 if (!packet_out) 2155 { 2156 LSQ_DEBUG("cannot get writeable packet for PING frame"); 2157 return; 2158 } 2159 int sz = conn->fc_conn.cn_pf->pf_gen_ping_frame( 2160 packet_out->po_data + packet_out->po_data_sz, 2161 lsquic_packet_out_avail(packet_out)); 2162 if (sz < 0) { 2163 ABORT_ERROR("gen_blocked_frame failed"); 2164 return; 2165 } 2166 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2167 packet_out->po_frame_types |= 1 << QUIC_FRAME_PING; 2168 LSQ_DEBUG("wrote PING frame"); 2169} 2170 2171 2172static void 2173generate_stop_waiting_frame (struct full_conn *conn) 2174{ 2175 assert(conn->fc_flags & FC_SEND_STOP_WAITING); 2176 2177 int sz; 2178 unsigned packnum_len; 2179 lsquic_packno_t least_unacked; 2180 lsquic_packet_out_t *packet_out; 2181 2182 /* Get packet that has room for the minimum size STOP_WAITING frame: */ 2183 packet_out = get_writeable_packet(conn, 1 + packno_bits2len(PACKNO_LEN_1)); 2184 if (!packet_out) 2185 return; 2186 2187 /* Now calculate number of bytes we really need. If there is not enough 2188 * room in the current packet, get a new one. 2189 */ 2190 packnum_len = packno_bits2len(lsquic_packet_out_packno_bits(packet_out)); 2191 if ((unsigned) lsquic_packet_out_avail(packet_out) < 1 + packnum_len) 2192 { 2193 packet_out = get_writeable_packet(conn, 1 + packnum_len); 2194 if (!packet_out) 2195 return; 2196 /* Here, a new packet has been allocated, The number of bytes needed 2197 * to represent packet number in the STOP_WAITING frame may have 2198 * increased. However, this does not matter, because the newly 2199 * allocated packet must have room for a STOP_WAITING frame of any 2200 * size. 2201 */ 2202 } 2203 2204 least_unacked = lsquic_send_ctl_smallest_unacked(&conn->fc_send_ctl); 2205 sz = conn->fc_conn.cn_pf->pf_gen_stop_waiting_frame( 2206 packet_out->po_data + packet_out->po_data_sz, 2207 lsquic_packet_out_avail(packet_out), packet_out->po_packno, 2208 lsquic_packet_out_packno_bits(packet_out), least_unacked); 2209 if (sz < 0) { 2210 ABORT_ERROR("gen_stop_waiting_frame failed"); 2211 return; 2212 } 2213 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2214 packet_out->po_regen_sz += sz; 2215 packet_out->po_frame_types |= 1 << QUIC_FRAME_STOP_WAITING; 2216 conn->fc_flags &= ~FC_SEND_STOP_WAITING; 2217 LSQ_DEBUG("wrote STOP_WAITING frame: least unacked: %"PRIu64, 2218 least_unacked); 2219 EV_LOG_GENERATED_STOP_WAITING_FRAME(LSQUIC_LOG_CONN_ID, least_unacked); 2220} 2221 2222 2223static int 2224process_stream_ready_to_send (struct full_conn *conn, lsquic_stream_t *stream) 2225{ 2226 int r = 1; 2227 if (stream->stream_flags & STREAM_SEND_WUF) 2228 r &= generate_wuf_stream(conn, stream); 2229 if (stream->stream_flags & STREAM_SEND_BLOCKED) 2230 r &= generate_stream_blocked_frame(conn, stream); 2231 if (stream->stream_flags & STREAM_SEND_RST) 2232 r &= generate_rst_stream_frame(conn, stream); 2233 return r; 2234} 2235 2236 2237static void 2238process_streams_ready_to_send (struct full_conn *conn) 2239{ 2240 lsquic_stream_t *stream; 2241 struct stream_prio_iter spi; 2242 2243 assert(!TAILQ_EMPTY(&conn->fc_pub.sending_streams)); 2244 2245 lsquic_spi_init(&spi, TAILQ_FIRST(&conn->fc_pub.sending_streams), 2246 TAILQ_LAST(&conn->fc_pub.sending_streams, lsquic_streams_tailq), 2247 (uintptr_t) &TAILQ_NEXT((lsquic_stream_t *) NULL, next_send_stream), 2248 STREAM_SENDING_FLAGS, conn->fc_conn.cn_cid, "send"); 2249 2250 for (stream = lsquic_spi_first(&spi); stream; 2251 stream = lsquic_spi_next(&spi)) 2252 if (!process_stream_ready_to_send(conn, stream)) 2253 break; 2254} 2255 2256 2257/* Return true if packetized, false otherwise */ 2258static int 2259packetize_standalone_stream_reset (struct full_conn *conn, uint32_t stream_id) 2260{ 2261 lsquic_packet_out_t *packet_out; 2262 int sz; 2263 2264 packet_out = get_writeable_packet(conn, QUIC_RST_STREAM_SZ); 2265 if (!packet_out) 2266 return 0; 2267 2268 sz = conn->fc_conn.cn_pf->pf_gen_rst_frame( 2269 packet_out->po_data + packet_out->po_data_sz, 2270 lsquic_packet_out_avail(packet_out), stream_id, 2271 0, 0x10 /* QUIC_PEER_GOING_AWAY */); 2272 if (sz < 0) { 2273 ABORT_ERROR("gen_rst_frame failed"); 2274 return 0; 2275 } 2276 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2277 packet_out->po_frame_types |= 1 << QUIC_FRAME_RST_STREAM; 2278 LSQ_DEBUG("generated standaloen RST_STREAM frame for stream %"PRIu32, 2279 stream_id); 2280 return 1; 2281} 2282 2283 2284static void 2285packetize_standalone_stream_resets (struct full_conn *conn) 2286{ 2287 struct stream_id_to_reset *sitr; 2288 2289 while ((sitr = STAILQ_FIRST(&conn->fc_stream_ids_to_reset))) 2290 if (packetize_standalone_stream_reset(conn, sitr->sitr_stream_id)) 2291 { 2292 STAILQ_REMOVE_HEAD(&conn->fc_stream_ids_to_reset, sitr_next); 2293 free(sitr); 2294 } 2295 else 2296 break; 2297} 2298 2299 2300static void 2301service_streams (struct full_conn *conn) 2302{ 2303 struct lsquic_hash_elem *el; 2304 lsquic_stream_t *stream, *next; 2305 int n_our_destroyed = 0; 2306 2307 for (stream = TAILQ_FIRST(&conn->fc_pub.service_streams); stream; stream = next) 2308 { 2309 next = TAILQ_NEXT(stream, next_service_stream); 2310 if (stream->stream_flags & STREAM_ABORT_CONN) 2311 /* No need to unset this flag or remove this stream: the connection 2312 * is about to be aborted. 2313 */ 2314 ABORT_ERROR("aborted due to error in stream %"PRIu32, stream->id); 2315 if (stream->stream_flags & STREAM_CALL_ONCLOSE) 2316 lsquic_stream_call_on_close(stream); 2317 if (stream->stream_flags & STREAM_FREE_STREAM) 2318 { 2319 n_our_destroyed += is_our_stream(conn, stream); 2320 TAILQ_REMOVE(&conn->fc_pub.service_streams, stream, next_service_stream); 2321 el = lsquic_hash_find(conn->fc_pub.all_streams, &stream->id, sizeof(stream->id)); 2322 if (el) 2323 lsquic_hash_erase(conn->fc_pub.all_streams, el); 2324 conn_mark_stream_closed(conn, stream->id); 2325 SAVE_STREAM_HISTORY(conn, stream); 2326 lsquic_stream_destroy(stream); 2327 } 2328 } 2329 2330 if (either_side_going_away(conn)) 2331 while (conn->fc_n_delayed_streams) 2332 { 2333 --conn->fc_n_delayed_streams; 2334 LSQ_DEBUG("goaway mode: delayed stream results in null ctor"); 2335 (void) conn->fc_stream_ifs[STREAM_IF_STD].stream_if->on_new_stream( 2336 conn->fc_stream_ifs[STREAM_IF_STD].stream_if_ctx, NULL); 2337 } 2338 else 2339 while (n_our_destroyed && conn->fc_n_delayed_streams) 2340 { 2341 --n_our_destroyed; 2342 --conn->fc_n_delayed_streams; 2343 LSQ_DEBUG("creating delayed stream"); 2344 if (!new_stream(conn, generate_stream_id(conn), SCF_CALL_ON_NEW)) 2345 { 2346 ABORT_ERROR("%s: cannot create new stream: %s", __func__, 2347 strerror(errno)); 2348 break; 2349 } 2350 assert(count_streams(conn, 0) <= conn->fc_cfg.max_streams_out); 2351 } 2352} 2353 2354 2355static void 2356process_streams_read_events (struct full_conn *conn) 2357{ 2358 lsquic_stream_t *stream; 2359 struct stream_prio_iter spi; 2360 2361 if (TAILQ_EMPTY(&conn->fc_pub.read_streams)) 2362 return; 2363 2364 lsquic_spi_init(&spi, TAILQ_FIRST(&conn->fc_pub.read_streams), 2365 TAILQ_LAST(&conn->fc_pub.read_streams, lsquic_streams_tailq), 2366 (uintptr_t) &TAILQ_NEXT((lsquic_stream_t *) NULL, next_read_stream), 2367 STREAM_WANT_READ, conn->fc_conn.cn_cid, "read"); 2368 2369 for (stream = lsquic_spi_first(&spi); stream; 2370 stream = lsquic_spi_next(&spi)) 2371 lsquic_stream_dispatch_read_events(stream); 2372} 2373 2374 2375static void 2376maybe_conn_flush_headers_stream (struct full_conn *conn) 2377{ 2378 lsquic_stream_t *stream; 2379 2380 if (conn->fc_flags & FC_HTTP) 2381 { 2382 stream = lsquic_headers_stream_get_stream(conn->fc_pub.hs); 2383 if (lsquic_stream_has_data_to_flush(stream)) 2384 (void) lsquic_stream_flush(stream); 2385 } 2386} 2387 2388 2389static void 2390process_streams_write_events (struct full_conn *conn, int high_prio) 2391{ 2392 lsquic_stream_t *stream; 2393 struct stream_prio_iter spi; 2394 2395 lsquic_spi_init(&spi, TAILQ_FIRST(&conn->fc_pub.write_streams), 2396 TAILQ_LAST(&conn->fc_pub.write_streams, lsquic_streams_tailq), 2397 (uintptr_t) &TAILQ_NEXT((lsquic_stream_t *) NULL, next_write_stream), 2398 STREAM_WANT_WRITE|STREAM_WANT_FLUSH, conn->fc_conn.cn_cid, 2399 high_prio ? "write-high" : "write-low"); 2400 2401 if (high_prio) 2402 lsquic_spi_drop_non_high(&spi); 2403 else 2404 lsquic_spi_drop_high(&spi); 2405 2406 for (stream = lsquic_spi_first(&spi); stream && write_is_possible(conn); 2407 stream = lsquic_spi_next(&spi)) 2408 lsquic_stream_dispatch_write_events(stream); 2409 2410 maybe_conn_flush_headers_stream(conn); 2411} 2412 2413 2414static void 2415process_hsk_stream_read_events (struct full_conn *conn) 2416{ 2417 lsquic_stream_t *stream; 2418 TAILQ_FOREACH(stream, &conn->fc_pub.read_streams, next_read_stream) 2419 if (LSQUIC_STREAM_HANDSHAKE == stream->id) 2420 { 2421 lsquic_stream_dispatch_read_events(stream); 2422 break; 2423 } 2424} 2425 2426 2427static void 2428process_hsk_stream_write_events (struct full_conn *conn) 2429{ 2430 lsquic_stream_t *stream; 2431 TAILQ_FOREACH(stream, &conn->fc_pub.write_streams, next_write_stream) 2432 if (LSQUIC_STREAM_HANDSHAKE == stream->id) 2433 { 2434 lsquic_stream_dispatch_write_events(stream); 2435 break; 2436 } 2437} 2438 2439 2440#if 1 2441# define verify_ack_frame(a, b, c) 2442#else 2443static void 2444verify_ack_frame (struct full_conn *conn, const unsigned char *buf, int bufsz) 2445{ 2446 unsigned i; 2447 int parsed_len; 2448 struct ack_info *ack_info; 2449 const struct lsquic_packno_range *range; 2450 char ack_buf[512]; 2451 unsigned buf_off = 0; 2452 int nw; 2453 2454 ack_info = conn->fc_pub.mm->acki; 2455 parsed_len = parse_ack_frame(buf, bufsz, ack_info); 2456 assert(parsed_len == bufsz); 2457 2458 for (range = lsquic_rechist_first(&conn->fc_rechist), i = 0; range; 2459 range = lsquic_rechist_next(&conn->fc_rechist), ++i) 2460 { 2461 assert(i < ack_info->n_ranges); 2462 assert(range->high == ack_info->ranges[i].high); 2463 assert(range->low == ack_info->ranges[i].low); 2464 if (LSQ_LOG_ENABLED(LSQ_LOG_DEBUG)) 2465 { 2466 nw = snprintf(ack_buf + buf_off, sizeof(ack_buf) - buf_off, 2467 "[%"PRIu64"-%"PRIu64"]", range->high, range->low); 2468 assert(nw >= 0); 2469 buf_off += nw; 2470 } 2471 } 2472 assert(i == ack_info->n_ranges); 2473 LSQ_DEBUG("Sent ACK frame %s", ack_buf); 2474} 2475 2476 2477#endif 2478 2479 2480static void 2481generate_ack_frame (struct full_conn *conn) 2482{ 2483 lsquic_packet_out_t *packet_out; 2484 lsquic_time_t now; 2485 int has_missing, w; 2486 2487 packet_out = lsquic_send_ctl_new_packet_out(&conn->fc_send_ctl, 0); 2488 if (!packet_out) 2489 { 2490 ABORT_ERROR("cannot allocate packet: %s", strerror(errno)); 2491 return; 2492 } 2493 2494 lsquic_send_ctl_scheduled_one(&conn->fc_send_ctl, packet_out); 2495 now = lsquic_time_now(); 2496 w = conn->fc_conn.cn_pf->pf_gen_ack_frame( 2497 packet_out->po_data + packet_out->po_data_sz, 2498 lsquic_packet_out_avail(packet_out), 2499 (gaf_rechist_first_f) lsquic_rechist_first, 2500 (gaf_rechist_next_f) lsquic_rechist_next, 2501 (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 2502 &conn->fc_rechist, now, &has_missing, &packet_out->po_ack2ed); 2503 if (w < 0) { 2504 ABORT_ERROR("generating ACK frame failed: %d", errno); 2505 return; 2506 } 2507 EV_LOG_GENERATED_ACK_FRAME(LSQUIC_LOG_CONN_ID, conn->fc_conn.cn_pf, 2508 packet_out->po_data + packet_out->po_data_sz, w); 2509 verify_ack_frame(conn, packet_out->po_data + packet_out->po_data_sz, w); 2510 lsquic_send_ctl_scheduled_ack(&conn->fc_send_ctl); 2511 packet_out->po_frame_types |= 1 << QUIC_FRAME_ACK; 2512 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, w); 2513 packet_out->po_regen_sz += w; 2514 if (has_missing) 2515 conn->fc_flags |= FC_ACK_HAD_MISS; 2516 else 2517 conn->fc_flags &= ~FC_ACK_HAD_MISS; 2518 LSQ_DEBUG("Put %d bytes of ACK frame into packet on outgoing queue", w); 2519 if (conn->fc_conn.cn_version >= LSQVER_039 && 2520 conn->fc_n_cons_unretx >= 20 && 2521 !lsquic_send_ctl_have_outgoing_retx_frames(&conn->fc_send_ctl)) 2522 { 2523 LSQ_DEBUG("schedule WINDOW_UPDATE frame after %u non-retx " 2524 "packets sent", conn->fc_n_cons_unretx); 2525 conn->fc_flags |= FC_SEND_WUF; 2526 } 2527} 2528 2529 2530static int 2531conn_ok_to_close (const struct full_conn *conn) 2532{ 2533 assert(conn->fc_flags & FC_CLOSING); 2534 return !(conn->fc_flags & FC_SERVER) 2535 || (conn->fc_flags & FC_RECV_CLOSE) 2536 || ( 2537 !lsquic_send_ctl_have_outgoing_stream_frames(&conn->fc_send_ctl) 2538 && lsquic_hash_count(conn->fc_pub.all_streams) == 0 2539 && lsquic_send_ctl_have_unacked_stream_frames(&conn->fc_send_ctl) == 0); 2540} 2541 2542 2543static enum tick_st 2544immediate_close (struct full_conn *conn) 2545{ 2546 lsquic_packet_out_t *packet_out; 2547 const char *error_reason; 2548 unsigned error_code; 2549 int sz; 2550 2551 if (conn->fc_flags & (FC_TICK_CLOSE|FC_GOT_PRST)) 2552 return TICK_CLOSE; 2553 2554 conn->fc_flags |= FC_TICK_CLOSE; 2555 2556 /* No reason to send anything that's been scheduled if connection is 2557 * being closed immedately. This also ensures that packet numbers 2558 * sequence is always increasing. 2559 */ 2560 lsquic_send_ctl_drop_scheduled(&conn->fc_send_ctl); 2561 2562 if ((conn->fc_flags & FC_TIMED_OUT) && conn->fc_settings->es_silent_close) 2563 return TICK_CLOSE; 2564 2565 packet_out = lsquic_send_ctl_new_packet_out(&conn->fc_send_ctl, 0); 2566 if (!packet_out) 2567 { 2568 LSQ_WARN("cannot allocate packet: %s", strerror(errno)); 2569 return TICK_CLOSE; 2570 } 2571 2572 assert(conn->fc_flags & (FC_ERROR|FC_ABORTED|FC_TIMED_OUT)); 2573 if (conn->fc_flags & FC_ERROR) 2574 { 2575 error_code = 0x01; /* QUIC_INTERNAL_ERROR */ 2576 error_reason = "connection error"; 2577 } 2578 else if (conn->fc_flags & FC_ABORTED) 2579 { 2580 error_code = 0x10; /* QUIC_PEER_GOING_AWAY */ 2581 error_reason = "user aborted connection"; 2582 } 2583 else if (conn->fc_flags & FC_TIMED_OUT) 2584 { 2585 error_code = 0x19; /* QUIC_NETWORK_IDLE_TIMEOUT */ 2586 error_reason = "connection timed out"; 2587 } 2588 else 2589 { 2590 error_code = 0x10; /* QUIC_PEER_GOING_AWAY */ 2591 error_reason = NULL; 2592 } 2593 2594 lsquic_send_ctl_scheduled_one(&conn->fc_send_ctl, packet_out); 2595 sz = conn->fc_conn.cn_pf->pf_gen_connect_close_frame( 2596 packet_out->po_data + packet_out->po_data_sz, 2597 lsquic_packet_out_avail(packet_out), error_code, 2598 error_reason, error_reason ? strlen(error_reason) : 0); 2599 if (sz < 0) { 2600 LSQ_WARN("%s failed", __func__); 2601 return TICK_CLOSE; 2602 } 2603 lsquic_send_ctl_incr_pack_sz(&conn->fc_send_ctl, packet_out, sz); 2604 packet_out->po_frame_types |= 1 << QUIC_FRAME_CONNECTION_CLOSE; 2605 LSQ_DEBUG("generated CONNECTION_CLOSE frame in its own packet"); 2606 return TICK_SEND|TICK_CLOSE; 2607} 2608 2609 2610static int 2611write_is_possible (struct full_conn *conn) 2612{ 2613 const lsquic_packet_out_t *packet_out; 2614 2615 packet_out = lsquic_send_ctl_last_scheduled(&conn->fc_send_ctl); 2616 return (packet_out && lsquic_packet_out_avail(packet_out) > 10) 2617 || lsquic_send_ctl_can_send(&conn->fc_send_ctl); 2618} 2619 2620 2621static int 2622should_generate_ack (const struct full_conn *conn) 2623{ 2624 return (conn->fc_flags & FC_ACK_QUEUED) 2625 || lsquic_send_ctl_lost_ack(&conn->fc_send_ctl); 2626} 2627 2628 2629static enum tick_st 2630full_conn_ci_tick (lsquic_conn_t *lconn, lsquic_time_t now) 2631{ 2632 struct full_conn *conn = (struct full_conn *) lconn; 2633 int have_delayed_packets; 2634 unsigned n; 2635 int s; 2636 enum tick_st tick = 0; 2637 2638#define CLOSE_IF_NECESSARY() do { \ 2639 if (conn->fc_flags & FC_IMMEDIATE_CLOSE_FLAGS) \ 2640 { \ 2641 tick |= immediate_close(conn); \ 2642 goto close_end; \ 2643 } \ 2644} while (0) 2645 2646#define RETURN_IF_OUT_OF_PACKETS() do { \ 2647 if (!lsquic_send_ctl_can_send(&conn->fc_send_ctl)) \ 2648 { \ 2649 if (0 == lsquic_send_ctl_n_scheduled(&conn->fc_send_ctl)) \ 2650 { \ 2651 LSQ_DEBUG("used up packet allowance, quiet now (line %d)", \ 2652 __LINE__); \ 2653 tick |= TICK_QUIET; \ 2654 } \ 2655 else \ 2656 { \ 2657 LSQ_DEBUG("used up packet allowance, sending now (line %d)",\ 2658 __LINE__); \ 2659 tick |= TICK_SEND; \ 2660 } \ 2661 goto end; \ 2662 } \ 2663} while (0) 2664 2665#if FULL_CONN_STATS 2666 ++conn->fc_stats.n_ticks; 2667#endif 2668 2669 if (LSQ_LOG_ENABLED(LSQ_LOG_DEBUG) 2670 && conn->fc_mem_logged_last + 1000000 <= now) 2671 { 2672 conn->fc_mem_logged_last = now; 2673 LSQ_DEBUG("memory used: %zd bytes", calc_mem_used(conn)); 2674 } 2675 2676 if (conn->fc_flags & FC_HAVE_SAVED_ACK) 2677 { 2678 (void) /* If there is an error, we'll fail shortly */ 2679 process_saved_ack(conn, 0); 2680 conn->fc_flags &= ~FC_HAVE_SAVED_ACK; 2681 } 2682 2683 lsquic_send_ctl_tick(&conn->fc_send_ctl, now); 2684 lsquic_send_ctl_set_buffer_stream_packets(&conn->fc_send_ctl, 1); 2685 CLOSE_IF_NECESSARY(); 2686 2687 if (!(conn->fc_flags & FC_SERVER)) 2688 { 2689 lsquic_alarmset_unset(&conn->fc_alset, AL_PING); 2690 lsquic_send_ctl_sanity_check(&conn->fc_send_ctl); 2691 } 2692 2693 lsquic_alarmset_ring_expired(&conn->fc_alset, now); 2694 CLOSE_IF_NECESSARY(); 2695 2696 /* To make things simple, only stream 1 is active until the handshake 2697 * has been completed. This will be adjusted in the future: the client 2698 * does not want to wait if it has the server information. 2699 */ 2700 if (conn->fc_conn.cn_flags & LSCONN_HANDSHAKE_DONE) 2701 process_streams_read_events(conn); 2702 else 2703 process_hsk_stream_read_events(conn); 2704 CLOSE_IF_NECESSARY(); 2705 2706 if (lsquic_send_ctl_pacer_blocked(&conn->fc_send_ctl)) 2707 goto skip_write; 2708 2709 if (conn->fc_flags & FC_FIRST_TICK) 2710 { 2711 conn->fc_flags &= ~FC_FIRST_TICK; 2712 have_delayed_packets = 0; 2713 } 2714 else 2715 /* If there are any scheduled packets at this point, it means that 2716 * they were not sent during previous tick; in other words, they 2717 * are delayed. When there are delayed packets, the only packet 2718 * we sometimes add is a packet with an ACK frame, and we add it 2719 * to the *front* of the queue. 2720 */ 2721 have_delayed_packets = lsquic_send_ctl_maybe_squeeze_sched( 2722 &conn->fc_send_ctl); 2723 2724 if (should_generate_ack(conn)) 2725 { 2726 if (have_delayed_packets) 2727 lsquic_send_ctl_reset_packnos(&conn->fc_send_ctl); 2728 2729 /* ACK frame generation fails with an error if it does not fit into 2730 * a single packet (it always should fit). 2731 */ 2732 generate_ack_frame(conn); 2733 CLOSE_IF_NECESSARY(); 2734 reset_ack_state(conn); 2735 2736 /* Try to send STOP_WAITING frame at the same time we send an ACK 2737 * This follows reference implementation. 2738 */ 2739 if (!(conn->fc_flags & FC_NSTP)) 2740 conn->fc_flags |= FC_SEND_STOP_WAITING; 2741 2742 if (have_delayed_packets) 2743 { 2744 if (conn->fc_flags & FC_SEND_STOP_WAITING) 2745 { 2746 /* TODO: ensure that STOP_WAITING frame is in the same packet 2747 * as the ACK frame in delayed packet mode. 2748 */ 2749 generate_stop_waiting_frame(conn); 2750 CLOSE_IF_NECESSARY(); 2751 } 2752 lsquic_send_ctl_ack_to_front(&conn->fc_send_ctl); 2753 } 2754 } 2755 2756 if (have_delayed_packets) 2757 { 2758 /* The reason for not adding STOP_WAITING and other frames below 2759 * to the packet carrying ACK frame generated when there are delayed 2760 * packets is so that if the ACK packet itself is delayed, it can be 2761 * dropped and replaced by new ACK packet. This way, we are never 2762 * more than 1 packet over CWND. 2763 */ 2764 tick |= TICK_SEND; 2765 goto end; 2766 } 2767 2768 /* Try to fit any of the following three frames -- STOP_WAITING, 2769 * WINDOW_UPDATE, and GOAWAY -- before checking if we have run 2770 * out of packets. If either of them does not fit, it will be 2771 * tried next time around. 2772 */ 2773 if (conn->fc_flags & FC_SEND_STOP_WAITING) 2774 { 2775 generate_stop_waiting_frame(conn); 2776 CLOSE_IF_NECESSARY(); 2777 } 2778 2779 if (lsquic_cfcw_fc_offsets_changed(&conn->fc_pub.cfcw) || 2780 (conn->fc_flags & FC_SEND_WUF)) 2781 { 2782 conn->fc_flags |= FC_SEND_WUF; 2783 generate_wuf_conn(conn); 2784 CLOSE_IF_NECESSARY(); 2785 } 2786 2787 if (conn->fc_flags & FC_SEND_GOAWAY) 2788 { 2789 generate_goaway_frame(conn); 2790 CLOSE_IF_NECESSARY(); 2791 } 2792 2793 n = lsquic_send_ctl_reschedule_packets(&conn->fc_send_ctl); 2794 if (n > 0) 2795 CLOSE_IF_NECESSARY(); 2796 2797 RETURN_IF_OUT_OF_PACKETS(); 2798 2799 if (conn->fc_conn.cn_flags & LSCONN_SEND_BLOCKED) 2800 { 2801 if (generate_blocked_frame(conn, 0)) 2802 conn->fc_conn.cn_flags &= ~LSCONN_SEND_BLOCKED; 2803 else 2804 RETURN_IF_OUT_OF_PACKETS(); 2805 } 2806 2807 if (!STAILQ_EMPTY(&conn->fc_stream_ids_to_reset)) 2808 { 2809 packetize_standalone_stream_resets(conn); 2810 CLOSE_IF_NECESSARY(); 2811 } 2812 2813 if (!TAILQ_EMPTY(&conn->fc_pub.sending_streams)) 2814 { 2815 process_streams_ready_to_send(conn); 2816 CLOSE_IF_NECESSARY(); 2817 } 2818 2819 lsquic_send_ctl_set_buffer_stream_packets(&conn->fc_send_ctl, 0); 2820 if (!(conn->fc_conn.cn_flags & LSCONN_HANDSHAKE_DONE)) 2821 { 2822 process_hsk_stream_write_events(conn); 2823 goto end_write; 2824 } 2825 2826 maybe_conn_flush_headers_stream(conn); 2827 2828 s = lsquic_send_ctl_schedule_buffered(&conn->fc_send_ctl, BPT_HIGHEST_PRIO); 2829 conn->fc_flags |= (s < 0) << FC_BIT_ERROR; 2830 if (!write_is_possible(conn)) 2831 goto end_write; 2832 2833 if (!TAILQ_EMPTY(&conn->fc_pub.write_streams)) 2834 { 2835 process_streams_write_events(conn, 1); 2836 if (!write_is_possible(conn)) 2837 goto end_write; 2838 } 2839 2840 s = lsquic_send_ctl_schedule_buffered(&conn->fc_send_ctl, BPT_OTHER_PRIO); 2841 conn->fc_flags |= (s < 0) << FC_BIT_ERROR; 2842 if (!write_is_possible(conn)) 2843 goto end_write; 2844 2845 if (!TAILQ_EMPTY(&conn->fc_pub.write_streams)) 2846 process_streams_write_events(conn, 0); 2847 2848 end_write: 2849 2850 skip_write: 2851 RETURN_IF_OUT_OF_PACKETS(); 2852 2853 if ((conn->fc_flags & FC_CLOSING) && conn_ok_to_close(conn)) 2854 { 2855 LSQ_DEBUG("connection is OK to close"); 2856 /* This is normal termination sequence. 2857 * 2858 * Generate CONNECTION_CLOSE frame if we are responding to one, have 2859 * packets scheduled to send, or silent close flag is not set. 2860 */ 2861 conn->fc_flags |= FC_TICK_CLOSE; 2862 if ((conn->fc_flags & FC_RECV_CLOSE) || 2863 0 != lsquic_send_ctl_n_scheduled(&conn->fc_send_ctl) || 2864 !conn->fc_settings->es_silent_close) 2865 { 2866 generate_connection_close_packet(conn); 2867 tick |= TICK_SEND|TICK_CLOSE; 2868 } 2869 else 2870 tick |= TICK_CLOSE; 2871 goto end; 2872 } 2873 2874 if (0 == lsquic_send_ctl_n_scheduled(&conn->fc_send_ctl)) 2875 { 2876 if (conn->fc_flags & FC_SEND_PING) 2877 { 2878 conn->fc_flags &= ~FC_SEND_PING; 2879 generate_ping_frame(conn); 2880 CLOSE_IF_NECESSARY(); 2881 assert(lsquic_send_ctl_n_scheduled(&conn->fc_send_ctl) != 0); 2882 } 2883 else 2884 { 2885 tick |= TICK_QUIET; 2886 goto end; 2887 } 2888 } 2889 else if (!(conn->fc_flags & FC_SERVER)) 2890 { 2891 lsquic_alarmset_unset(&conn->fc_alset, AL_PING); 2892 lsquic_send_ctl_sanity_check(&conn->fc_send_ctl); 2893 conn->fc_flags &= ~FC_SEND_PING; /* It may have rung */ 2894 } 2895 2896 now = lsquic_time_now(); 2897 lsquic_alarmset_set(&conn->fc_alset, AL_IDLE, 2898 now + conn->fc_settings->es_idle_conn_to); 2899 2900 /* From the spec: 2901 * " The PING frame should be used to keep a connection alive when 2902 * " a stream is open. 2903 */ 2904 if (0 == (conn->fc_flags & FC_SERVER) && 2905 lsquic_hash_count(conn->fc_pub.all_streams) > 0) 2906 lsquic_alarmset_set(&conn->fc_alset, AL_PING, now + TIME_BETWEEN_PINGS); 2907 2908 tick |= TICK_SEND; 2909 2910 end: 2911 service_streams(conn); 2912 CLOSE_IF_NECESSARY(); 2913 2914 close_end: 2915 lsquic_send_ctl_set_buffer_stream_packets(&conn->fc_send_ctl, 1); 2916 return tick; 2917} 2918 2919 2920static void 2921full_conn_ci_packet_in (lsquic_conn_t *lconn, lsquic_packet_in_t *packet_in) 2922{ 2923 struct full_conn *conn = (struct full_conn *) lconn; 2924 2925 lsquic_alarmset_set(&conn->fc_alset, AL_IDLE, 2926 packet_in->pi_received + conn->fc_settings->es_idle_conn_to); 2927 if (0 == (conn->fc_flags & FC_ERROR)) 2928 if (0 != process_incoming_packet(conn, packet_in)) 2929 conn->fc_flags |= FC_ERROR; 2930} 2931 2932 2933static lsquic_packet_out_t * 2934full_conn_ci_next_packet_to_send (lsquic_conn_t *lconn) 2935{ 2936 struct full_conn *conn = (struct full_conn *) lconn; 2937 return lsquic_send_ctl_next_packet_to_send(&conn->fc_send_ctl); 2938} 2939 2940 2941static void 2942full_conn_ci_packet_sent (lsquic_conn_t *lconn, lsquic_packet_out_t *packet_out) 2943{ 2944 struct full_conn *conn = (struct full_conn *) lconn; 2945 int s; 2946 2947 recent_packet_hist_new(conn, 1, packet_out->po_sent); 2948 recent_packet_hist_frames(conn, 1, packet_out->po_frame_types); 2949 2950 if (packet_out->po_frame_types & QFRAME_RETRANSMITTABLE_MASK) 2951 { 2952 conn->fc_n_cons_unretx = 0; 2953 lsquic_alarmset_set(&conn->fc_alset, AL_IDLE, 2954 packet_out->po_sent + conn->fc_settings->es_idle_conn_to); 2955 } 2956 else 2957 ++conn->fc_n_cons_unretx; 2958 s = lsquic_send_ctl_sent_packet(&conn->fc_send_ctl, packet_out, 1); 2959 if (s != 0) 2960 ABORT_ERROR("sent packet failed: %s", strerror(errno)); 2961#if FULL_CONN_STATS 2962 ++conn->fc_stats.n_packets_out; 2963#endif 2964} 2965 2966 2967static void 2968full_conn_ci_packet_not_sent (lsquic_conn_t *lconn, lsquic_packet_out_t *packet_out) 2969{ 2970 struct full_conn *conn = (struct full_conn *) lconn; 2971 lsquic_send_ctl_delayed_one(&conn->fc_send_ctl, packet_out); 2972} 2973 2974 2975static void 2976full_conn_ci_handshake_ok (lsquic_conn_t *lconn) 2977{ 2978 struct full_conn *conn = (struct full_conn *) lconn; 2979 LSQ_DEBUG("handshake reportedly done"); 2980 lsquic_alarmset_unset(&conn->fc_alset, AL_HANDSHAKE); 2981 if (0 == apply_peer_settings(conn)) 2982 lconn->cn_flags |= LSCONN_HANDSHAKE_DONE; 2983 else 2984 conn->fc_flags |= FC_ERROR; 2985} 2986 2987 2988static void 2989full_conn_ci_handshake_failed (lsquic_conn_t *lconn) 2990{ 2991 struct full_conn *conn = (struct full_conn *) lconn; 2992 LSQ_DEBUG("handshake failed"); 2993 lsquic_alarmset_unset(&conn->fc_alset, AL_HANDSHAKE); 2994 conn->fc_flags |= FC_HSK_FAILED; 2995} 2996 2997 2998void 2999lsquic_conn_abort (lsquic_conn_t *lconn) 3000{ 3001 struct full_conn *conn = (struct full_conn *) lconn; 3002 LSQ_INFO("User aborted connection"); 3003 conn->fc_flags |= FC_ABORTED; 3004} 3005 3006 3007void 3008lsquic_conn_close (lsquic_conn_t *lconn) 3009{ 3010 struct full_conn *conn = (struct full_conn *) lconn; 3011 lsquic_stream_t *stream; 3012 struct lsquic_hash_elem *el; 3013 3014 if (!(conn->fc_flags & FC_CLOSING)) 3015 { 3016 for (el = lsquic_hash_first(conn->fc_pub.all_streams); el; 3017 el = lsquic_hash_next(conn->fc_pub.all_streams)) 3018 { 3019 stream = lsquic_hashelem_getdata(el); 3020 lsquic_stream_shutdown_internal(stream); 3021 } 3022 conn->fc_flags |= FC_CLOSING; 3023 if (!(conn->fc_flags & FC_GOAWAY_SENT)) 3024 conn->fc_flags |= FC_SEND_GOAWAY; 3025 } 3026} 3027 3028 3029void 3030lsquic_conn_going_away (lsquic_conn_t *lconn) 3031{ 3032 struct full_conn *conn = (struct full_conn *) lconn; 3033 if (!(conn->fc_flags & (FC_CLOSING|FC_GOING_AWAY))) 3034 { 3035 LSQ_INFO("connection marked as going away"); 3036 assert(!(conn->fc_flags & FC_SEND_GOAWAY)); 3037 conn->fc_flags |= FC_GOING_AWAY; 3038 if (!(conn->fc_flags & FC_GOAWAY_SENT)) 3039 conn->fc_flags |= FC_SEND_GOAWAY; 3040 } 3041} 3042 3043 3044/* Find stream when stream ID is read from something other than a STREAM 3045 * frame. If the stream cannot be found or created, the connection is 3046 * aborted. 3047 */ 3048#if __GNUC__ 3049__attribute__((nonnull(4))) 3050#endif 3051static lsquic_stream_t * 3052find_stream_on_non_stream_frame (struct full_conn *conn, uint32_t stream_id, 3053 enum stream_ctor_flags stream_ctor_flags, 3054 const char *what) 3055{ 3056 lsquic_stream_t *stream; 3057 unsigned in_count; 3058 3059 stream = find_stream_by_id(conn, stream_id); 3060 if (stream) 3061 return stream; 3062 3063 if (conn_is_stream_closed(conn, stream_id)) 3064 { 3065 LSQ_DEBUG("drop incoming %s for closed stream %u", what, stream_id); 3066 return NULL; 3067 } 3068 3069 /* XXX It seems that if we receive a priority frame for a stream, the 3070 * stream should exist or have existed at some point. Thus, if 3071 * it does not exist, we should return an error here. 3072 */ 3073 3074 if (!is_peer_initiated(conn, stream_id)) 3075 { 3076 ABORT_ERROR("frame for never-initiated stream (push promise?)"); 3077 return NULL; 3078 } 3079 3080 in_count = count_streams(conn, 1); 3081 LSQ_DEBUG("number of peer-initiated streams: %u", in_count); 3082 if (in_count >= conn->fc_cfg.max_streams_in) 3083 { 3084 ABORT_ERROR("incoming %s for stream %u would exceed " 3085 "limit: %u", what, stream_id, conn->fc_cfg.max_streams_in); 3086 return NULL; 3087 } 3088 if ((conn->fc_flags & FC_GOING_AWAY) && 3089 stream_id > conn->fc_max_peer_stream_id) 3090 { 3091 maybe_schedule_reset_for_stream(conn, stream_id); 3092 LSQ_DEBUG("going away: reset new incoming stream %u", stream_id); 3093 return NULL; 3094 } 3095 3096 stream = new_stream(conn, stream_id, stream_ctor_flags); 3097 if (!stream) 3098 { 3099 ABORT_ERROR("cannot create new stream: %s", strerror(errno)); 3100 return NULL; 3101 } 3102 if (stream_id > conn->fc_max_peer_stream_id) 3103 conn->fc_max_peer_stream_id = stream_id; 3104 3105 return stream; 3106} 3107 3108 3109static void 3110headers_stream_on_conn_error (void *ctx) 3111{ 3112 struct full_conn *conn = ctx; 3113 ABORT_ERROR("connection error reported by HEADERS stream"); 3114} 3115 3116 3117static void 3118headers_stream_on_stream_error (void *ctx, uint32_t stream_id) 3119{ 3120 struct full_conn *conn = ctx; 3121 lsquic_stream_t *stream; 3122 3123 stream = find_stream_on_non_stream_frame(conn, stream_id, SCF_CALL_ON_NEW, 3124 "error"); 3125 if (stream) 3126 { 3127 LSQ_DEBUG("resetting stream %u due to error", stream_id); 3128 /* We use code 1, which is QUIC_INTERNAL_ERROR (see 3129 * [draft-hamilton-quic-transport-protocol-01], Section 10), for all 3130 * errors. There does not seem to be a good reason to figure out 3131 * and send more specific error codes. 3132 */ 3133 lsquic_stream_reset_ext(stream, 1, 0); 3134 } 3135} 3136 3137 3138static void 3139headers_stream_on_enable_push (void *ctx, int enable_push) 3140{ 3141 struct full_conn *conn = ctx; 3142 if (0 == enable_push) 3143 { 3144 LSQ_DEBUG("server push %d -> 0", !!(conn->fc_flags & FC_SUPPORT_PUSH)); 3145 conn->fc_flags &= ~FC_SUPPORT_PUSH; 3146 } 3147 else if (conn->fc_settings->es_support_push) 3148 { 3149 LSQ_DEBUG("server push %d -> 1", !!(conn->fc_flags & FC_SUPPORT_PUSH)); 3150 conn->fc_flags |= FC_SUPPORT_PUSH; 3151 } 3152 else 3153 LSQ_INFO("not enabling server push that's disabled in engine settings"); 3154} 3155 3156 3157static void 3158headers_stream_on_incoming_headers (void *ctx, struct uncompressed_headers *uh) 3159{ 3160 struct full_conn *conn = ctx; 3161 lsquic_stream_t *stream; 3162 3163 LSQ_DEBUG("incoming headers for stream %u", uh->uh_stream_id); 3164 3165 stream = find_stream_on_non_stream_frame(conn, uh->uh_stream_id, 0, 3166 "headers"); 3167 if (!stream) 3168 { 3169 free(uh); 3170 return; 3171 } 3172 3173 if (0 != lsquic_stream_uh_in(stream, uh)) 3174 { 3175 ABORT_ERROR("stream %u refused incoming headers", uh->uh_stream_id); 3176 free(uh); 3177 } 3178 3179 if (!(stream->stream_flags & STREAM_ONNEW_DONE)) 3180 lsquic_stream_call_on_new(stream); 3181} 3182 3183 3184static void 3185headers_stream_on_push_promise (void *ctx, struct uncompressed_headers *uh) 3186{ 3187 struct full_conn *conn = ctx; 3188 lsquic_stream_t *stream; 3189 3190 assert(!(conn->fc_flags & FC_SERVER)); 3191 3192 LSQ_DEBUG("push promise for stream %u in response to %u", 3193 uh->uh_oth_stream_id, uh->uh_stream_id); 3194 3195 if (0 == (uh->uh_stream_id & 1) || 3196 0 != (uh->uh_oth_stream_id & 1)) 3197 { 3198 ABORT_ERROR("invalid push promise stream IDs: %u, %u", 3199 uh->uh_oth_stream_id, uh->uh_stream_id); 3200 free(uh); 3201 return; 3202 } 3203 3204 if (!(conn_is_stream_closed(conn, uh->uh_stream_id) || 3205 find_stream_by_id(conn, uh->uh_stream_id))) 3206 { 3207 ABORT_ERROR("invalid push promise original stream ID %u never " 3208 "initiated", uh->uh_stream_id); 3209 free(uh); 3210 return; 3211 } 3212 3213 if (conn_is_stream_closed(conn, uh->uh_oth_stream_id) || 3214 find_stream_by_id(conn, uh->uh_oth_stream_id)) 3215 { 3216 ABORT_ERROR("invalid promised stream ID %u already used", 3217 uh->uh_oth_stream_id); 3218 free(uh); 3219 return; 3220 } 3221 3222 stream = new_stream_ext(conn, uh->uh_oth_stream_id, STREAM_IF_STD, 3223 SCF_DI_AUTOSWITCH|(conn->fc_enpub->enp_settings.es_rw_once ? 3224 SCF_DISP_RW_ONCE : 0)); 3225 if (!stream) 3226 { 3227 ABORT_ERROR("cannot create stream: %s", strerror(errno)); 3228 free(uh); 3229 return; 3230 } 3231 lsquic_stream_push_req(stream, uh); 3232 lsquic_stream_call_on_new(stream); 3233 return; 3234} 3235 3236 3237static void 3238headers_stream_on_priority (void *ctx, uint32_t stream_id, int exclusive, 3239 uint32_t dep_stream_id, unsigned weight) 3240{ 3241 struct full_conn *conn = ctx; 3242 lsquic_stream_t *stream; 3243 LSQ_DEBUG("got priority frame for stream %u: (ex: %d; dep stream: %u; " 3244 "weight: %u)", stream_id, exclusive, dep_stream_id, weight); 3245 stream = find_stream_on_non_stream_frame(conn, stream_id, SCF_CALL_ON_NEW, 3246 "priority"); 3247 if (stream) 3248 lsquic_stream_set_priority_internal(stream, weight); 3249} 3250 3251 3252int lsquic_conn_is_push_enabled(lsquic_conn_t *c) 3253{ 3254 return ((struct full_conn *)c)->fc_flags & FC_SUPPORT_PUSH; 3255} 3256 3257 3258lsquic_conn_ctx_t * 3259lsquic_conn_get_ctx (const lsquic_conn_t *lconn) 3260{ 3261 struct full_conn *const conn = (struct full_conn *) lconn; 3262 return conn->fc_conn_ctx; 3263} 3264 3265 3266void lsquic_conn_set_ctx (lsquic_conn_t *lconn, lsquic_conn_ctx_t *ctx) 3267{ 3268 struct full_conn *const conn = (struct full_conn *) lconn; 3269 conn->fc_conn_ctx = ctx; 3270} 3271 3272 3273enum LSQUIC_CONN_STATUS 3274lsquic_conn_status (lsquic_conn_t *lconn, char *errbuf, size_t bufsz) 3275{ 3276 struct full_conn *const conn = (struct full_conn *) lconn; 3277 size_t n; 3278 3279 /* Test the common case first: */ 3280 if (!(conn->fc_flags & (FC_ERROR 3281 |FC_TIMED_OUT 3282 |FC_ABORTED 3283 |FC_GOT_PRST 3284 |FC_HSK_FAILED 3285 |FC_CLOSING 3286 |FC_GOING_AWAY))) 3287 { 3288 if (lconn->cn_flags & LSCONN_HANDSHAKE_DONE) 3289 return LSCONN_ST_CONNECTED; 3290 else 3291 return LSCONN_ST_HSK_IN_PROGRESS; 3292 } 3293 3294 if (errbuf && bufsz) 3295 { 3296 if (conn->fc_errmsg) 3297 { 3298 n = bufsz < MAX_ERRMSG ? bufsz : MAX_ERRMSG; 3299 strncpy(errbuf, conn->fc_errmsg, n); 3300 errbuf[n - 1] = '\0'; 3301 } 3302 else 3303 errbuf[0] = '\0'; 3304 } 3305 3306 if (conn->fc_flags & FC_ERROR) 3307 return LSCONN_ST_ERROR; 3308 if (conn->fc_flags & FC_TIMED_OUT) 3309 return LSCONN_ST_TIMED_OUT; 3310 if (conn->fc_flags & FC_ABORTED) 3311 return LSCONN_ST_USER_ABORTED; 3312 if (conn->fc_flags & FC_GOT_PRST) 3313 return LSCONN_ST_RESET; 3314 if (conn->fc_flags & FC_HSK_FAILED) 3315 return LSCONN_ST_HSK_FAILURE; 3316 if (conn->fc_flags & FC_CLOSING) 3317 return LSCONN_ST_CLOSED; 3318 assert(conn->fc_flags & FC_GOING_AWAY); 3319 return LSCONN_ST_GOING_AWAY; 3320} 3321 3322 3323static int 3324full_conn_ci_is_tickable (lsquic_conn_t *lconn) 3325{ 3326 struct full_conn *conn = (struct full_conn *) lconn; 3327 const struct lsquic_stream *stream; 3328 3329 if (!TAILQ_EMPTY(&conn->fc_pub.service_streams)) 3330 return 1; 3331 3332 if (lsquic_send_ctl_can_send(&conn->fc_send_ctl) 3333 && (should_generate_ack(conn) || 3334 !lsquic_send_ctl_sched_is_blocked(&conn->fc_send_ctl))) 3335 { 3336 if (conn->fc_flags & (FC_SEND_GOAWAY|FC_SEND_STOP_WAITING 3337 |FC_SEND_PING|FC_SEND_WUF)) 3338 return 1; 3339 if (lsquic_send_ctl_has_buffered(&conn->fc_send_ctl)) 3340 return 1; 3341 if (!TAILQ_EMPTY(&conn->fc_pub.sending_streams)) 3342 return 1; 3343 TAILQ_FOREACH(stream, &conn->fc_pub.write_streams, next_write_stream) 3344 if (lsquic_stream_write_avail(stream)) 3345 return 1; 3346 } 3347 3348 TAILQ_FOREACH(stream, &conn->fc_pub.read_streams, next_read_stream) 3349 if (lsquic_stream_readable(stream)) 3350 return 1; 3351 3352 return 0; 3353} 3354 3355 3356static lsquic_time_t 3357full_conn_ci_next_tick_time (lsquic_conn_t *lconn) 3358{ 3359 struct full_conn *conn = (struct full_conn *) lconn; 3360 lsquic_time_t alarm_time, pacer_time; 3361 3362 alarm_time = lsquic_alarmset_mintime(&conn->fc_alset); 3363 pacer_time = lsquic_send_ctl_next_pacer_time(&conn->fc_send_ctl); 3364 3365 if (alarm_time && pacer_time) 3366 { 3367 if (alarm_time < pacer_time) 3368 return alarm_time; 3369 else 3370 return pacer_time; 3371 } 3372 else if (alarm_time) 3373 return alarm_time; 3374 else 3375 return pacer_time; 3376} 3377 3378 3379static const struct headers_stream_callbacks headers_callbacks = 3380{ 3381 .hsc_on_headers = headers_stream_on_incoming_headers, 3382 .hsc_on_push_promise = headers_stream_on_push_promise, 3383 .hsc_on_priority = headers_stream_on_priority, 3384 .hsc_on_stream_error = headers_stream_on_stream_error, 3385 .hsc_on_conn_error = headers_stream_on_conn_error, 3386 .hsc_on_enable_push = headers_stream_on_enable_push, 3387}; 3388 3389static const struct headers_stream_callbacks *headers_callbacks_ptr = &headers_callbacks; 3390 3391static const struct conn_iface full_conn_iface = { 3392 .ci_destroy = full_conn_ci_destroy, 3393 .ci_handshake_failed = full_conn_ci_handshake_failed, 3394 .ci_handshake_ok = full_conn_ci_handshake_ok, 3395 .ci_is_tickable = full_conn_ci_is_tickable, 3396 .ci_next_packet_to_send = full_conn_ci_next_packet_to_send, 3397 .ci_next_tick_time = full_conn_ci_next_tick_time, 3398 .ci_packet_in = full_conn_ci_packet_in, 3399 .ci_packet_not_sent = full_conn_ci_packet_not_sent, 3400 .ci_packet_sent = full_conn_ci_packet_sent, 3401 .ci_tick = full_conn_ci_tick, 3402}; 3403 3404static const struct conn_iface *full_conn_iface_ptr = &full_conn_iface; 3405