lsquic_parse_gquic_common.c revision f4841319
1/* Copyright (c) 2017 - 2020 LiteSpeed Technologies Inc. See LICENSE. */ 2/* 3 * lsquic_parse_gquic_common.c -- Parsing functions common to GQUIC 4 */ 5 6#include <assert.h> 7#include <errno.h> 8#include <inttypes.h> 9#include <string.h> 10#include <stdlib.h> 11#include <sys/queue.h> 12#ifndef WIN32 13#include <sys/types.h> 14#else 15#include <vc_compat.h> 16#endif 17 18#include "lsquic_types.h" 19#include "lsquic_int_types.h" 20#include "lsquic_packet_common.h" 21#include "lsquic_packet_out.h" 22#include "lsquic_packet_gquic.h" 23#include "lsquic_packet_in.h" 24#include "lsquic_parse_common.h" 25#include "lsquic_parse.h" 26#include "lsquic_version.h" 27#include "lsquic.h" 28 29#define LSQUIC_LOGGER_MODULE LSQLM_PARSE 30#include "lsquic_logger.h" 31 32#define CHECK_SPACE(need, pstart, pend) \ 33 do { if ((intptr_t) (need) > ((pend) - (pstart))) { return -1; } } while (0) 34 35/* This partially parses `packet_in' and returns 0 if in case it succeeded and 36 * -1 on failure. 37 * 38 * After this function returns 0, connection ID, nonce, and version fields can 39 * be examined. To finsh parsing the packet, call version-specific 40 * pf_parse_packet_in_finish() routine. 41 */ 42int 43lsquic_gquic_parse_packet_in_begin (lsquic_packet_in_t *packet_in, 44 size_t length, int is_server, unsigned cid_len, 45 struct packin_parse_state *state) 46{ 47 int nbytes; 48 enum PACKET_PUBLIC_FLAGS public_flags; 49 const unsigned char *p = packet_in->pi_data; 50 const unsigned char *const pend = packet_in->pi_data + length; 51 52 if (length > GQUIC_MAX_PACKET_SZ) 53 { 54 LSQ_DEBUG("Cannot handle packet_in_size(%zd) > %d packet incoming " 55 "packet's header", length, GQUIC_MAX_PACKET_SZ); 56 return -1; 57 } 58 59 CHECK_SPACE(1, p, pend); 60 61 public_flags = *p++; 62 63 if (public_flags & PACKET_PUBLIC_FLAGS_8BYTE_CONNECTION_ID) 64 { 65 CHECK_SPACE(8, p, pend); 66 memset(&packet_in->pi_conn_id, 0, sizeof(packet_in->pi_conn_id)); 67 packet_in->pi_conn_id.len = 8; 68 memcpy(&packet_in->pi_conn_id.idbuf, p, 8); 69 packet_in->pi_flags |= PI_CONN_ID; 70 p += 8; 71 } 72 73 if (public_flags & PACKET_PUBLIC_FLAGS_VERSION) 74 { 75 /* It seems that version negotiation packets sent by Google may have 76 * NONCE bit set. Ignore it: 77 */ 78 public_flags &= ~PACKET_PUBLIC_FLAGS_NONCE; 79 80 if (is_server) 81 { 82 CHECK_SPACE(4, p, pend); 83 packet_in->pi_quic_ver = p - packet_in->pi_data; 84 p += 4; 85 } 86 else 87 { /* OK, we have a version negotiation packet. We need to verify 88 * that it has correct structure. See Section 4.3 of 89 * [draft-ietf-quic-transport-00]. 90 */ 91 if ((public_flags & ~(PACKET_PUBLIC_FLAGS_VERSION| 92 PACKET_PUBLIC_FLAGS_8BYTE_CONNECTION_ID)) 93 || ((pend - p) & 3)) 94 return -1; 95 CHECK_SPACE(4, p, pend); 96 packet_in->pi_quic_ver = p - packet_in->pi_data; 97 p = pend; 98 } 99 } 100 else 101 { 102 /* From [draft-hamilton-quic-transport-protocol-01]: 103 * 0x40 = MULTIPATH. This bit is reserved for multipath use. 104 * 0x80 is currently unused, and must be set to 0. 105 * 106 * The reference implementation checks that two high bits are not set 107 * if version flag is not set or if the version is the same. For our 108 * purposes, all GQUIC version we support so far have these bits set 109 * to zero. 110 */ 111 if (public_flags & (0x80|0x40)) 112 return -1; 113 packet_in->pi_quic_ver = 0; 114 } 115 116 if (!is_server && (public_flags & PACKET_PUBLIC_FLAGS_NONCE) == 117 PACKET_PUBLIC_FLAGS_NONCE) 118 { 119 CHECK_SPACE(32, p, pend); 120 packet_in->pi_nonce = p - packet_in->pi_data; 121 p += 32; 122 } 123 else 124 packet_in->pi_nonce = 0; 125 126 state->pps_p = p; 127 128 packet_in->pi_packno = 0; 129 if (0 == (public_flags & (PACKET_PUBLIC_FLAGS_VERSION|PACKET_PUBLIC_FLAGS_RST)) 130 || ((public_flags & PACKET_PUBLIC_FLAGS_VERSION) && is_server)) 131 { 132 nbytes = twobit_to_1246((public_flags >> 4) & 3); 133 CHECK_SPACE(nbytes, p, pend); 134 p += nbytes; 135 state->pps_nbytes = nbytes; 136 } 137 else 138 state->pps_nbytes = 0; 139 140 packet_in->pi_header_sz = p - packet_in->pi_data; 141 packet_in->pi_frame_types = 0; 142 memset(&packet_in->pi_next, 0, sizeof(packet_in->pi_next)); 143 packet_in->pi_data_sz = length; 144 packet_in->pi_refcnt = 0; 145 packet_in->pi_received = 0; 146 packet_in->pi_flags |= PI_GQUIC; 147 packet_in->pi_flags |= ((public_flags >> 4) & 3) << PIBIT_BITS_SHIFT; 148 149 return 0; 150} 151 152 153static const unsigned char simple_prst_payload[] = { 154 'P', 'R', 'S', 'T', 155 0x01, 0x00, 0x00, 0x00, 156 'R', 'N', 'O', 'N', 157 0x08, 0x00, 0x00, 0x00, 158 1, 2, 3, 4, 5, 6, 7, 8, 159}; 160 161 162typedef char correct_simple_prst_size[(GQUIC_RESET_SZ == 163 1 + GQUIC_CID_LEN + sizeof(simple_prst_payload)) - 1]; 164 165 166ssize_t 167lsquic_generate_gquic_reset (const lsquic_cid_t *cidp, 168 unsigned char *buf, size_t buf_sz) 169{ 170 lsquic_cid_t cid; 171 172 if (buf_sz < 1 + GQUIC_CID_LEN + sizeof(simple_prst_payload)) 173 { 174 errno = ENOBUFS; 175 return -1; 176 } 177 178 if (cidp) 179 { 180 assert(GQUIC_CID_LEN == cidp->len); 181 cid = *cidp; 182 } 183 else 184 { 185 memset(&cid, 0, sizeof(cid)); 186 cid.len = GQUIC_CID_LEN; 187 } 188 189 *buf++ = PACKET_PUBLIC_FLAGS_RST | PACKET_PUBLIC_FLAGS_8BYTE_CONNECTION_ID; 190 191 memcpy(buf, cid.idbuf, GQUIC_CID_LEN); 192 buf += GQUIC_CID_LEN; 193 194 memcpy(buf, simple_prst_payload, sizeof(simple_prst_payload)); 195 return 1 + GQUIC_CID_LEN + sizeof(simple_prst_payload); 196} 197 198 199static const enum quic_frame_type byte2frame_type_Q035_thru_Q046[0x100] = 200{ 201 [0x00] = QUIC_FRAME_PADDING, 202 [0x01] = QUIC_FRAME_RST_STREAM, 203 [0x02] = QUIC_FRAME_CONNECTION_CLOSE, 204 [0x03] = QUIC_FRAME_GOAWAY, 205 [0x04] = QUIC_FRAME_WINDOW_UPDATE, 206 [0x05] = QUIC_FRAME_BLOCKED, 207 [0x06] = QUIC_FRAME_STOP_WAITING, 208 [0x07] = QUIC_FRAME_PING, 209 [0x08] = QUIC_FRAME_INVALID, 210 [0x09] = QUIC_FRAME_INVALID, 211 [0x0A] = QUIC_FRAME_INVALID, 212 [0x0B] = QUIC_FRAME_INVALID, 213 [0x0C] = QUIC_FRAME_INVALID, 214 [0x0D] = QUIC_FRAME_INVALID, 215 [0x0E] = QUIC_FRAME_INVALID, 216 [0x0F] = QUIC_FRAME_INVALID, 217 [0x10] = QUIC_FRAME_INVALID, 218 [0x11] = QUIC_FRAME_INVALID, 219 [0x12] = QUIC_FRAME_INVALID, 220 [0x13] = QUIC_FRAME_INVALID, 221 [0x14] = QUIC_FRAME_INVALID, 222 [0x15] = QUIC_FRAME_INVALID, 223 [0x16] = QUIC_FRAME_INVALID, 224 [0x17] = QUIC_FRAME_INVALID, 225 [0x18] = QUIC_FRAME_INVALID, 226 [0x19] = QUIC_FRAME_INVALID, 227 [0x1A] = QUIC_FRAME_INVALID, 228 [0x1B] = QUIC_FRAME_INVALID, 229 [0x1C] = QUIC_FRAME_INVALID, 230 [0x1D] = QUIC_FRAME_INVALID, 231 [0x1E] = QUIC_FRAME_INVALID, 232 [0x1F] = QUIC_FRAME_INVALID, 233 [0x20] = QUIC_FRAME_INVALID, 234 [0x21] = QUIC_FRAME_INVALID, 235 [0x22] = QUIC_FRAME_INVALID, 236 [0x23] = QUIC_FRAME_INVALID, 237 [0x24] = QUIC_FRAME_INVALID, 238 [0x25] = QUIC_FRAME_INVALID, 239 [0x26] = QUIC_FRAME_INVALID, 240 [0x27] = QUIC_FRAME_INVALID, 241 [0x28] = QUIC_FRAME_INVALID, 242 [0x29] = QUIC_FRAME_INVALID, 243 [0x2A] = QUIC_FRAME_INVALID, 244 [0x2B] = QUIC_FRAME_INVALID, 245 [0x2C] = QUIC_FRAME_INVALID, 246 [0x2D] = QUIC_FRAME_INVALID, 247 [0x2E] = QUIC_FRAME_INVALID, 248 [0x2F] = QUIC_FRAME_INVALID, 249 [0x30] = QUIC_FRAME_INVALID, 250 [0x31] = QUIC_FRAME_INVALID, 251 [0x32] = QUIC_FRAME_INVALID, 252 [0x33] = QUIC_FRAME_INVALID, 253 [0x34] = QUIC_FRAME_INVALID, 254 [0x35] = QUIC_FRAME_INVALID, 255 [0x36] = QUIC_FRAME_INVALID, 256 [0x37] = QUIC_FRAME_INVALID, 257 [0x38] = QUIC_FRAME_INVALID, 258 [0x39] = QUIC_FRAME_INVALID, 259 [0x3A] = QUIC_FRAME_INVALID, 260 [0x3B] = QUIC_FRAME_INVALID, 261 [0x3C] = QUIC_FRAME_INVALID, 262 [0x3D] = QUIC_FRAME_INVALID, 263 [0x3E] = QUIC_FRAME_INVALID, 264 [0x3F] = QUIC_FRAME_INVALID, 265 [0x40] = QUIC_FRAME_ACK, 266 [0x41] = QUIC_FRAME_ACK, 267 [0x42] = QUIC_FRAME_ACK, 268 [0x43] = QUIC_FRAME_ACK, 269 [0x44] = QUIC_FRAME_ACK, 270 [0x45] = QUIC_FRAME_ACK, 271 [0x46] = QUIC_FRAME_ACK, 272 [0x47] = QUIC_FRAME_ACK, 273 [0x48] = QUIC_FRAME_ACK, 274 [0x49] = QUIC_FRAME_ACK, 275 [0x4A] = QUIC_FRAME_ACK, 276 [0x4B] = QUIC_FRAME_ACK, 277 [0x4C] = QUIC_FRAME_ACK, 278 [0x4D] = QUIC_FRAME_ACK, 279 [0x4E] = QUIC_FRAME_ACK, 280 [0x4F] = QUIC_FRAME_ACK, 281 [0x50] = QUIC_FRAME_ACK, 282 [0x51] = QUIC_FRAME_ACK, 283 [0x52] = QUIC_FRAME_ACK, 284 [0x53] = QUIC_FRAME_ACK, 285 [0x54] = QUIC_FRAME_ACK, 286 [0x55] = QUIC_FRAME_ACK, 287 [0x56] = QUIC_FRAME_ACK, 288 [0x57] = QUIC_FRAME_ACK, 289 [0x58] = QUIC_FRAME_ACK, 290 [0x59] = QUIC_FRAME_ACK, 291 [0x5A] = QUIC_FRAME_ACK, 292 [0x5B] = QUIC_FRAME_ACK, 293 [0x5C] = QUIC_FRAME_ACK, 294 [0x5D] = QUIC_FRAME_ACK, 295 [0x5E] = QUIC_FRAME_ACK, 296 [0x5F] = QUIC_FRAME_ACK, 297 [0x60] = QUIC_FRAME_ACK, 298 [0x61] = QUIC_FRAME_ACK, 299 [0x62] = QUIC_FRAME_ACK, 300 [0x63] = QUIC_FRAME_ACK, 301 [0x64] = QUIC_FRAME_ACK, 302 [0x65] = QUIC_FRAME_ACK, 303 [0x66] = QUIC_FRAME_ACK, 304 [0x67] = QUIC_FRAME_ACK, 305 [0x68] = QUIC_FRAME_ACK, 306 [0x69] = QUIC_FRAME_ACK, 307 [0x6A] = QUIC_FRAME_ACK, 308 [0x6B] = QUIC_FRAME_ACK, 309 [0x6C] = QUIC_FRAME_ACK, 310 [0x6D] = QUIC_FRAME_ACK, 311 [0x6E] = QUIC_FRAME_ACK, 312 [0x6F] = QUIC_FRAME_ACK, 313 [0x70] = QUIC_FRAME_ACK, 314 [0x71] = QUIC_FRAME_ACK, 315 [0x72] = QUIC_FRAME_ACK, 316 [0x73] = QUIC_FRAME_ACK, 317 [0x74] = QUIC_FRAME_ACK, 318 [0x75] = QUIC_FRAME_ACK, 319 [0x76] = QUIC_FRAME_ACK, 320 [0x77] = QUIC_FRAME_ACK, 321 [0x78] = QUIC_FRAME_ACK, 322 [0x79] = QUIC_FRAME_ACK, 323 [0x7A] = QUIC_FRAME_ACK, 324 [0x7B] = QUIC_FRAME_ACK, 325 [0x7C] = QUIC_FRAME_ACK, 326 [0x7D] = QUIC_FRAME_ACK, 327 [0x7E] = QUIC_FRAME_ACK, 328 [0x7F] = QUIC_FRAME_ACK, 329 [0x80] = QUIC_FRAME_STREAM, 330 [0x81] = QUIC_FRAME_STREAM, 331 [0x82] = QUIC_FRAME_STREAM, 332 [0x83] = QUIC_FRAME_STREAM, 333 [0x84] = QUIC_FRAME_STREAM, 334 [0x85] = QUIC_FRAME_STREAM, 335 [0x86] = QUIC_FRAME_STREAM, 336 [0x87] = QUIC_FRAME_STREAM, 337 [0x88] = QUIC_FRAME_STREAM, 338 [0x89] = QUIC_FRAME_STREAM, 339 [0x8A] = QUIC_FRAME_STREAM, 340 [0x8B] = QUIC_FRAME_STREAM, 341 [0x8C] = QUIC_FRAME_STREAM, 342 [0x8D] = QUIC_FRAME_STREAM, 343 [0x8E] = QUIC_FRAME_STREAM, 344 [0x8F] = QUIC_FRAME_STREAM, 345 [0x90] = QUIC_FRAME_STREAM, 346 [0x91] = QUIC_FRAME_STREAM, 347 [0x92] = QUIC_FRAME_STREAM, 348 [0x93] = QUIC_FRAME_STREAM, 349 [0x94] = QUIC_FRAME_STREAM, 350 [0x95] = QUIC_FRAME_STREAM, 351 [0x96] = QUIC_FRAME_STREAM, 352 [0x97] = QUIC_FRAME_STREAM, 353 [0x98] = QUIC_FRAME_STREAM, 354 [0x99] = QUIC_FRAME_STREAM, 355 [0x9A] = QUIC_FRAME_STREAM, 356 [0x9B] = QUIC_FRAME_STREAM, 357 [0x9C] = QUIC_FRAME_STREAM, 358 [0x9D] = QUIC_FRAME_STREAM, 359 [0x9E] = QUIC_FRAME_STREAM, 360 [0x9F] = QUIC_FRAME_STREAM, 361 [0xA0] = QUIC_FRAME_STREAM, 362 [0xA1] = QUIC_FRAME_STREAM, 363 [0xA2] = QUIC_FRAME_STREAM, 364 [0xA3] = QUIC_FRAME_STREAM, 365 [0xA4] = QUIC_FRAME_STREAM, 366 [0xA5] = QUIC_FRAME_STREAM, 367 [0xA6] = QUIC_FRAME_STREAM, 368 [0xA7] = QUIC_FRAME_STREAM, 369 [0xA8] = QUIC_FRAME_STREAM, 370 [0xA9] = QUIC_FRAME_STREAM, 371 [0xAA] = QUIC_FRAME_STREAM, 372 [0xAB] = QUIC_FRAME_STREAM, 373 [0xAC] = QUIC_FRAME_STREAM, 374 [0xAD] = QUIC_FRAME_STREAM, 375 [0xAE] = QUIC_FRAME_STREAM, 376 [0xAF] = QUIC_FRAME_STREAM, 377 [0xB0] = QUIC_FRAME_STREAM, 378 [0xB1] = QUIC_FRAME_STREAM, 379 [0xB2] = QUIC_FRAME_STREAM, 380 [0xB3] = QUIC_FRAME_STREAM, 381 [0xB4] = QUIC_FRAME_STREAM, 382 [0xB5] = QUIC_FRAME_STREAM, 383 [0xB6] = QUIC_FRAME_STREAM, 384 [0xB7] = QUIC_FRAME_STREAM, 385 [0xB8] = QUIC_FRAME_STREAM, 386 [0xB9] = QUIC_FRAME_STREAM, 387 [0xBA] = QUIC_FRAME_STREAM, 388 [0xBB] = QUIC_FRAME_STREAM, 389 [0xBC] = QUIC_FRAME_STREAM, 390 [0xBD] = QUIC_FRAME_STREAM, 391 [0xBE] = QUIC_FRAME_STREAM, 392 [0xBF] = QUIC_FRAME_STREAM, 393 [0xC0] = QUIC_FRAME_STREAM, 394 [0xC1] = QUIC_FRAME_STREAM, 395 [0xC2] = QUIC_FRAME_STREAM, 396 [0xC3] = QUIC_FRAME_STREAM, 397 [0xC4] = QUIC_FRAME_STREAM, 398 [0xC5] = QUIC_FRAME_STREAM, 399 [0xC6] = QUIC_FRAME_STREAM, 400 [0xC7] = QUIC_FRAME_STREAM, 401 [0xC8] = QUIC_FRAME_STREAM, 402 [0xC9] = QUIC_FRAME_STREAM, 403 [0xCA] = QUIC_FRAME_STREAM, 404 [0xCB] = QUIC_FRAME_STREAM, 405 [0xCC] = QUIC_FRAME_STREAM, 406 [0xCD] = QUIC_FRAME_STREAM, 407 [0xCE] = QUIC_FRAME_STREAM, 408 [0xCF] = QUIC_FRAME_STREAM, 409 [0xD0] = QUIC_FRAME_STREAM, 410 [0xD1] = QUIC_FRAME_STREAM, 411 [0xD2] = QUIC_FRAME_STREAM, 412 [0xD3] = QUIC_FRAME_STREAM, 413 [0xD4] = QUIC_FRAME_STREAM, 414 [0xD5] = QUIC_FRAME_STREAM, 415 [0xD6] = QUIC_FRAME_STREAM, 416 [0xD7] = QUIC_FRAME_STREAM, 417 [0xD8] = QUIC_FRAME_STREAM, 418 [0xD9] = QUIC_FRAME_STREAM, 419 [0xDA] = QUIC_FRAME_STREAM, 420 [0xDB] = QUIC_FRAME_STREAM, 421 [0xDC] = QUIC_FRAME_STREAM, 422 [0xDD] = QUIC_FRAME_STREAM, 423 [0xDE] = QUIC_FRAME_STREAM, 424 [0xDF] = QUIC_FRAME_STREAM, 425 [0xE0] = QUIC_FRAME_STREAM, 426 [0xE1] = QUIC_FRAME_STREAM, 427 [0xE2] = QUIC_FRAME_STREAM, 428 [0xE3] = QUIC_FRAME_STREAM, 429 [0xE4] = QUIC_FRAME_STREAM, 430 [0xE5] = QUIC_FRAME_STREAM, 431 [0xE6] = QUIC_FRAME_STREAM, 432 [0xE7] = QUIC_FRAME_STREAM, 433 [0xE8] = QUIC_FRAME_STREAM, 434 [0xE9] = QUIC_FRAME_STREAM, 435 [0xEA] = QUIC_FRAME_STREAM, 436 [0xEB] = QUIC_FRAME_STREAM, 437 [0xEC] = QUIC_FRAME_STREAM, 438 [0xED] = QUIC_FRAME_STREAM, 439 [0xEE] = QUIC_FRAME_STREAM, 440 [0xEF] = QUIC_FRAME_STREAM, 441 [0xF0] = QUIC_FRAME_STREAM, 442 [0xF1] = QUIC_FRAME_STREAM, 443 [0xF2] = QUIC_FRAME_STREAM, 444 [0xF3] = QUIC_FRAME_STREAM, 445 [0xF4] = QUIC_FRAME_STREAM, 446 [0xF5] = QUIC_FRAME_STREAM, 447 [0xF6] = QUIC_FRAME_STREAM, 448 [0xF7] = QUIC_FRAME_STREAM, 449 [0xF8] = QUIC_FRAME_STREAM, 450 [0xF9] = QUIC_FRAME_STREAM, 451 [0xFA] = QUIC_FRAME_STREAM, 452 [0xFB] = QUIC_FRAME_STREAM, 453 [0xFC] = QUIC_FRAME_STREAM, 454 [0xFD] = QUIC_FRAME_STREAM, 455 [0xFE] = QUIC_FRAME_STREAM, 456 [0xFF] = QUIC_FRAME_STREAM, 457}; 458 459 460enum quic_frame_type 461lsquic_parse_frame_type_gquic_Q035_thru_Q046 (unsigned char b) 462{ 463 return byte2frame_type_Q035_thru_Q046[b]; 464} 465 466 467void 468lsquic_turn_on_fin_Q035_thru_Q046 (unsigned char *stream_header) 469{ 470 /* 1fdoooss */ 471 *stream_header |= 0x40; 472} 473 474 475size_t 476calc_stream_frame_header_sz_gquic (lsquic_stream_id_t stream_id, 477 uint64_t offset, unsigned data_sz_IGNORED) 478{ 479 return 480 /* Type */ 481 1 482 /* Stream ID length */ 483 + ((stream_id) > 0x0000FF) 484 + ((stream_id) > 0x00FFFF) 485 + ((stream_id) > 0xFFFFFF) 486 + 1 487 /* Offset length */ 488 + ((offset) >= (1ULL << 56)) 489 + ((offset) >= (1ULL << 48)) 490 + ((offset) >= (1ULL << 40)) 491 + ((offset) >= (1ULL << 32)) 492 + ((offset) >= (1ULL << 24)) 493 + ((offset) >= (1ULL << 16)) 494 + (((offset) > 0) << 1) 495 /* Add data length (2) yourself, if necessary */ 496 ; 497} 498 499 500static const char *const ecn2str[4] = 501{ 502 [ECN_NOT_ECT] = "", 503 [ECN_ECT0] = "ECT(0)", 504 [ECN_ECT1] = "ECT(1)", 505 [ECN_CE] = "CE", 506}; 507 508 509void 510lsquic_acki2str (const struct ack_info *acki, char *buf, size_t bufsz) 511{ 512 size_t off, nw; 513 enum ecn ecn; 514 unsigned n; 515 516 off = 0; 517 for (n = 0; n < acki->n_ranges; ++n) 518 { 519 nw = snprintf(buf + off, bufsz - off, "[%"PRIu64"-%"PRIu64"]", 520 acki->ranges[n].high, acki->ranges[n].low); 521 if (nw > bufsz - off) 522 return; 523 off += nw; 524 } 525 526 if (acki->flags & AI_TRUNCATED) 527 { 528 nw = snprintf(buf + off, bufsz - off, RANGES_TRUNCATED_STR); 529 if (nw > bufsz - off) 530 return; 531 off += nw; 532 } 533 534 if (acki->flags & AI_ECN) 535 { 536 for (ecn = 1; ecn <= 3; ++ecn) 537 { 538 nw = snprintf(buf + off, bufsz - off, " %s: %"PRIu64"%.*s", 539 ecn2str[ecn], acki->ecn_counts[ecn], ecn < 3, ";"); 540 if (nw > bufsz - off) 541 return; 542 off += nw; 543 } 544 } 545} 546 547 548size_t 549lsquic_gquic_po_header_sz (enum packet_out_flags flags) 550{ 551 return 1 /* Type */ 552 + (!!(flags & PO_CONN_ID) << 3) /* Connection ID */ 553 + (!!(flags & PO_VERSION) << 2) /* Version */ 554 + (!!(flags & PO_NONCE) << 5) /* Nonce */ 555 + gquic_packno_bits2len((flags >> POBIT_SHIFT) & 0x3) /* Packet number */ 556 ; 557} 558 559 560size_t 561lsquic_gquic_packout_size (const struct lsquic_conn *conn, 562 const struct lsquic_packet_out *packet_out) 563{ 564 return lsquic_gquic_po_header_sz(packet_out->po_flags) 565 + packet_out->po_data_sz 566 + GQUIC_PACKET_HASH_SZ 567 ; 568} 569 570 571size_t 572lsquic_gquic_packout_header_size (const struct lsquic_conn *conn, 573 enum packet_out_flags flags, size_t dcid_len) 574{ 575 return lsquic_gquic_po_header_sz(flags); 576} 577 578 579int 580lsquic_gquic_gen_ver_nego_pkt (unsigned char *buf, size_t bufsz, 581 const lsquic_cid_t *cid, unsigned version_bitmask) 582{ 583 int sz; 584 unsigned char *p = buf; 585 unsigned char *const pend = p + bufsz; 586 587 CHECK_SPACE(1, p, pend); 588 *p = PACKET_PUBLIC_FLAGS_VERSION | PACKET_PUBLIC_FLAGS_8BYTE_CONNECTION_ID; 589 ++p; 590 591 if (GQUIC_CID_LEN != cid->len) 592 return -1; 593 594 CHECK_SPACE(GQUIC_CID_LEN, p, pend); 595 memcpy(p, cid->idbuf, GQUIC_CID_LEN); 596 p += GQUIC_CID_LEN; 597 598 sz = lsquic_gen_ver_tags(p, pend - p, version_bitmask); 599 if (sz < 0) 600 return -1; 601 602 return p + sz - buf; 603} 604 605 606unsigned 607lsquic_gquic_packno_bits2len (enum packno_bits bits) 608{ 609 return gquic_packno_bits2len(bits); 610} 611 612 613enum packno_bits 614lsquic_gquic_calc_packno_bits (lsquic_packno_t packno, 615 lsquic_packno_t least_unacked, uint64_t n_in_flight) 616{ 617 uint64_t delta; 618 unsigned bits; 619 620 delta = packno - least_unacked; 621 if (n_in_flight > delta) 622 delta = n_in_flight; 623 624 delta *= 4; 625 bits = (delta > (1ULL << 8)) 626 + (delta > (1ULL << 16)) 627 + (delta > (1ULL << 32)); 628 629 return bits; 630} 631 632 633/* `dst' serves both as source and destination. `src' is the new frame */ 634int 635lsquic_merge_acks (struct ack_info *dst, const struct ack_info *src) 636{ 637 const struct lsquic_packno_range *a, *a_end, *b, *b_end, **p; 638 struct lsquic_packno_range *out, *out_end; 639 unsigned i; 640 struct lsquic_packno_range out_ranges[256]; 641 642 if (!(dst->n_ranges && src->n_ranges)) 643 return -1; 644 645 a = dst->ranges; 646 a_end = a + dst->n_ranges; 647 b = src->ranges; 648 b_end = b + src->n_ranges; 649 out = out_ranges; 650 out_end = out + sizeof(out_ranges) / sizeof(out_ranges[0]); 651 652 if (a->high >= b->high) 653 *out = *a; 654 else 655 *out = *b; 656 657 while (1) 658 { 659 if (a < a_end && b < b_end) 660 { 661 if (a->high >= b->high) 662 p = &a; 663 else 664 p = &b; 665 } 666 else if (a < a_end) 667 p = &a; 668 else if (b < b_end) 669 p = &b; 670 else 671 { 672 ++out; 673 break; 674 } 675 676 if ((*p)->high + 1 >= out->low) 677 out->low = (*p)->low; 678 else if (out + 1 < out_end) 679 *++out = **p; 680 else 681 return -1; 682 ++*p; 683 } 684 685 if (src->flags & AI_ECN) 686 for (i = 0; i < sizeof(src->ecn_counts) 687 / sizeof(src->ecn_counts[0]); ++i) 688 dst->ecn_counts[i] += src->ecn_counts[i]; 689 dst->flags |= src->flags; 690 dst->lack_delta = src->lack_delta; 691 dst->n_ranges = out - out_ranges; 692 memcpy(dst->ranges, out_ranges, sizeof(out_ranges[0]) * dst->n_ranges); 693 694 return 0; 695} 696