test_ackgen_gquic_be.c revision b62ec17f
17d09751dSDmitri Tikhonov/* Copyright (c) 2017 - 2020 LiteSpeed Technologies Inc. See LICENSE. */ 250aadb33SDmitri Tikhonov/* 350aadb33SDmitri Tikhonov * Test how ACK frame is encoded. Receive history module is tested by a 450aadb33SDmitri Tikhonov * separate unit test. 550aadb33SDmitri Tikhonov */ 650aadb33SDmitri Tikhonov 750aadb33SDmitri Tikhonov#include <assert.h> 850aadb33SDmitri Tikhonov#include <stdio.h> 950aadb33SDmitri Tikhonov#include <stdlib.h> 1050aadb33SDmitri Tikhonov#include <string.h> 1150aadb33SDmitri Tikhonov 12fb3e20e0SDmitri Tikhonov#ifdef WIN32 13fb3e20e0SDmitri Tikhonov#include "vc_compat.h" 14fb3e20e0SDmitri Tikhonov#endif 15fb3e20e0SDmitri Tikhonov 1650aadb33SDmitri Tikhonov#include "lsquic_types.h" 1750aadb33SDmitri Tikhonov#include "lsquic_int_types.h" 1850aadb33SDmitri Tikhonov#include "lsquic_rechist.h" 1950aadb33SDmitri Tikhonov#include "lsquic_parse.h" 2050aadb33SDmitri Tikhonov#include "lsquic_util.h" 2150aadb33SDmitri Tikhonov#include "lsquic_logger.h" 2250aadb33SDmitri Tikhonov#include "lsquic.h" 2350aadb33SDmitri Tikhonov 24fb96f4ddSDmitri Tikhonovstatic const struct parse_funcs *const pf = select_pf_by_ver(LSQVER_043); 2550aadb33SDmitri Tikhonov 2650aadb33SDmitri Tikhonovstatic void 2750aadb33SDmitri Tikhonovtest1 (void) /* Inverse of quic_framer_test.cc -- NewAckFrameOneAckBlock */ 2850aadb33SDmitri Tikhonov{ 2950aadb33SDmitri Tikhonov lsquic_rechist_t rechist; 3050aadb33SDmitri Tikhonov lsquic_time_t now = lsquic_time_now(); 3116a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 3250aadb33SDmitri Tikhonov 33b62ec17fSDmitri Tikhonov lsquic_rechist_init(&rechist, 0); 3450aadb33SDmitri Tikhonov 3550aadb33SDmitri Tikhonov unsigned i; 3650aadb33SDmitri Tikhonov for (i = 1; i <= 0x1234; ++i) 3750aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, i, now); 3850aadb33SDmitri Tikhonov 3950aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 4050aadb33SDmitri Tikhonov 0x45, 4150aadb33SDmitri Tikhonov 0x12, 0x34, /* Largest acked */ 4250aadb33SDmitri Tikhonov 0x87, 0xFF, /* Delta time */ 4350aadb33SDmitri Tikhonov 0x12, 0x34, /* Block length */ 4450aadb33SDmitri Tikhonov 0x00, /* Number of timestamps */ 4550aadb33SDmitri Tikhonov }; 4650aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 4750aadb33SDmitri Tikhonov 4850aadb33SDmitri Tikhonov int has_missing = -1; 4950aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 5050aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 5150aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 5250aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 535392f7a3SLiteSpeed Tech &rechist, now + 0x7FF8000, &has_missing, &largest, NULL); 5450aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 5550aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 5650aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 5750aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 5850aadb33SDmitri Tikhonov assert(("ACK frame has no missing packets", has_missing == 0)); 5916a9b66aSDmitri Tikhonov assert(largest == 0x1234); 6050aadb33SDmitri Tikhonov 6150aadb33SDmitri Tikhonov lsquic_rechist_cleanup(&rechist); 6250aadb33SDmitri Tikhonov} 6350aadb33SDmitri Tikhonov 6450aadb33SDmitri Tikhonovstatic void 6550aadb33SDmitri Tikhonovtest2 (void) /* Inverse of quic_framer_test.cc -- NewAckFrameOneAckBlock, minus 6650aadb33SDmitri Tikhonov * delta times. 6750aadb33SDmitri Tikhonov */ 6850aadb33SDmitri Tikhonov{ 6950aadb33SDmitri Tikhonov lsquic_rechist_t rechist; 7050aadb33SDmitri Tikhonov lsquic_time_t now = lsquic_time_now(); 7150aadb33SDmitri Tikhonov 72b62ec17fSDmitri Tikhonov lsquic_rechist_init(&rechist, 0); 7350aadb33SDmitri Tikhonov 7450aadb33SDmitri Tikhonov /* Encode the following ranges: 7550aadb33SDmitri Tikhonov * high low 7650aadb33SDmitri Tikhonov * 0x1234 0x1234 7750aadb33SDmitri Tikhonov * 0x1232 0x384 7850aadb33SDmitri Tikhonov * 0x1F3 0xA 7950aadb33SDmitri Tikhonov * 0x4 0x1 8050aadb33SDmitri Tikhonov */ 8150aadb33SDmitri Tikhonov unsigned i; 8250aadb33SDmitri Tikhonov for (i = 4; i >= 1; --i) 8350aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, i, now); 8450aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, 0x1234, now); 8550aadb33SDmitri Tikhonov for (i = 0xA; i <= 0x1F3; ++i) 8650aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, i, now); 8750aadb33SDmitri Tikhonov for (i = 0x1232; i >= 0x384; --i) 8850aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, i, now); 8950aadb33SDmitri Tikhonov 9050aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 9150aadb33SDmitri Tikhonov 0x65, 9250aadb33SDmitri Tikhonov 0x12, 0x34, /* Largest acked */ 9350aadb33SDmitri Tikhonov 0x00, 0x00, /* Zero delta time. */ 9450aadb33SDmitri Tikhonov 0x04, /* Num ack blocks ranges. */ 9550aadb33SDmitri Tikhonov 0x00, 0x01, /* First ack block length. */ 9650aadb33SDmitri Tikhonov 0x01, /* Gap to next block. */ 9750aadb33SDmitri Tikhonov 0x0e, 0xaf, /* Ack block length. */ 9850aadb33SDmitri Tikhonov 0xff, /* Gap to next block. */ 9950aadb33SDmitri Tikhonov 0x00, 0x00, /* Ack block length. */ 10050aadb33SDmitri Tikhonov 0x91, /* Gap to next block. */ 10150aadb33SDmitri Tikhonov 0x01, 0xea, /* Ack block length. */ 10250aadb33SDmitri Tikhonov 0x05, /* Gap to next block. */ 10350aadb33SDmitri Tikhonov 0x00, 0x04, /* Ack block length. */ 10450aadb33SDmitri Tikhonov 0x00, /* Number of timestamps. */ 10550aadb33SDmitri Tikhonov }; 10650aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 10750aadb33SDmitri Tikhonov 10850aadb33SDmitri Tikhonov int has_missing = -1; 10916a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 11050aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 11150aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 11250aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 11350aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 1145392f7a3SLiteSpeed Tech &rechist, now, &has_missing, &largest, NULL); 11550aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 11650aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 11750aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 11850aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 11950aadb33SDmitri Tikhonov assert(("ACK frame has missing packets", has_missing > 0)); 12016a9b66aSDmitri Tikhonov assert(largest == 0x1234); 12150aadb33SDmitri Tikhonov 12250aadb33SDmitri Tikhonov lsquic_rechist_cleanup(&rechist); 12350aadb33SDmitri Tikhonov} 12450aadb33SDmitri Tikhonov 12550aadb33SDmitri Tikhonovstatic void 12650aadb33SDmitri Tikhonovtest3 (void) 12750aadb33SDmitri Tikhonov{ 12850aadb33SDmitri Tikhonov lsquic_rechist_t rechist; 12950aadb33SDmitri Tikhonov lsquic_time_t now = lsquic_time_now(); 13050aadb33SDmitri Tikhonov 131b62ec17fSDmitri Tikhonov lsquic_rechist_init(&rechist, 0); 13250aadb33SDmitri Tikhonov 13350aadb33SDmitri Tikhonov /* Encode the following ranges: 13450aadb33SDmitri Tikhonov * high low 13550aadb33SDmitri Tikhonov * 3 3 13650aadb33SDmitri Tikhonov * 1 1 13750aadb33SDmitri Tikhonov */ 13850aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, 1, now); 13950aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, 3, now); 14050aadb33SDmitri Tikhonov 14150aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 14250aadb33SDmitri Tikhonov 0x60, 14350aadb33SDmitri Tikhonov 0x03, 14450aadb33SDmitri Tikhonov 0x00, 0x00, /* Zero delta time. */ 14550aadb33SDmitri Tikhonov 0x01, /* Num ack blocks ranges. */ 14650aadb33SDmitri Tikhonov 0x01, /* First ack block length. */ 14750aadb33SDmitri Tikhonov 0x01, /* Gap to next block. */ 14850aadb33SDmitri Tikhonov 0x01, /* Ack block length. */ 14950aadb33SDmitri Tikhonov 0x00, /* Number of timestamps. */ 15050aadb33SDmitri Tikhonov }; 15150aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 15250aadb33SDmitri Tikhonov 15350aadb33SDmitri Tikhonov int has_missing = -1; 15416a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 15550aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 15650aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 15750aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 15850aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 1595392f7a3SLiteSpeed Tech &rechist, now, &has_missing, &largest, NULL); 16050aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 16150aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 16250aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 16350aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 16450aadb33SDmitri Tikhonov assert(("ACK frame has missing packets", has_missing > 0)); 16516a9b66aSDmitri Tikhonov assert(largest == 0x03); 16650aadb33SDmitri Tikhonov 16750aadb33SDmitri Tikhonov lsquic_rechist_cleanup(&rechist); 16850aadb33SDmitri Tikhonov} 16950aadb33SDmitri Tikhonov 17050aadb33SDmitri Tikhonov 17150aadb33SDmitri Tikhonovstatic void 17250aadb33SDmitri Tikhonovtest4 (void) 17350aadb33SDmitri Tikhonov{ 17450aadb33SDmitri Tikhonov lsquic_rechist_t rechist; 17550aadb33SDmitri Tikhonov int i; 17650aadb33SDmitri Tikhonov 177b62ec17fSDmitri Tikhonov lsquic_rechist_init(&rechist, 0); 17850aadb33SDmitri Tikhonov 17950aadb33SDmitri Tikhonov lsquic_time_t now = lsquic_time_now(); 18050aadb33SDmitri Tikhonov lsquic_rechist_received(&rechist, 1, now); 18150aadb33SDmitri Tikhonov 18250aadb33SDmitri Tikhonov { 18350aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 18450aadb33SDmitri Tikhonov 0x40, 18550aadb33SDmitri Tikhonov 0x01, /* Largest acked */ 18650aadb33SDmitri Tikhonov 0x00, 0x00, /* Delta time */ 18750aadb33SDmitri Tikhonov 0x01, /* Block length */ 18850aadb33SDmitri Tikhonov 0x00, /* Number of timestamps */ 18950aadb33SDmitri Tikhonov }; 19050aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 19150aadb33SDmitri Tikhonov int has_missing = -1; 19216a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 19350aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 19450aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 19550aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 19650aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 1975392f7a3SLiteSpeed Tech &rechist, now, &has_missing, &largest, NULL); 19850aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 19950aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 20050aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 20150aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 20250aadb33SDmitri Tikhonov assert(("ACK frame has no missing packets", has_missing == 0)); 20316a9b66aSDmitri Tikhonov assert(largest == 1); 20450aadb33SDmitri Tikhonov } 20550aadb33SDmitri Tikhonov 20650aadb33SDmitri Tikhonov for (i = 3; i <= 5; ++i) 20750aadb33SDmitri Tikhonov lsquic_rechist_received(&rechist, i, now); 20850aadb33SDmitri Tikhonov 20950aadb33SDmitri Tikhonov { 21050aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 21150aadb33SDmitri Tikhonov 0x60, 21250aadb33SDmitri Tikhonov 0x05, /* Largest acked */ 21350aadb33SDmitri Tikhonov 0x00, 0x00, /* Delta time */ 21450aadb33SDmitri Tikhonov 0x01, /* Num ack blocks */ 21550aadb33SDmitri Tikhonov 0x03, /* First block length [3, 5] */ 21650aadb33SDmitri Tikhonov 0x01, /* Gap to next block */ 21750aadb33SDmitri Tikhonov 0x01, /* Second block length [1, 1] */ 21850aadb33SDmitri Tikhonov 0x00, /* Number of timestamps */ 21950aadb33SDmitri Tikhonov }; 22050aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 22150aadb33SDmitri Tikhonov int has_missing = -1; 22216a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 22350aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 22450aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 22550aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 22650aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 2275392f7a3SLiteSpeed Tech &rechist, now, &has_missing, &largest, NULL); 22850aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 22950aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 23050aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 23150aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 23250aadb33SDmitri Tikhonov assert(("ACK frame has missing packets", has_missing > 0)); 23316a9b66aSDmitri Tikhonov assert(largest == 5); 23450aadb33SDmitri Tikhonov } 23550aadb33SDmitri Tikhonov 23650aadb33SDmitri Tikhonov lsquic_rechist_cleanup(&rechist); 23750aadb33SDmitri Tikhonov} 23850aadb33SDmitri Tikhonov 23950aadb33SDmitri Tikhonov 24050aadb33SDmitri Tikhonovstatic void 24150aadb33SDmitri Tikhonovtest_4byte_packnos (void) 24250aadb33SDmitri Tikhonov{ 24350aadb33SDmitri Tikhonov lsquic_packno_t packno; 24450aadb33SDmitri Tikhonov lsquic_rechist_t rechist; 24550aadb33SDmitri Tikhonov lsquic_time_t now = lsquic_time_now(); 24650aadb33SDmitri Tikhonov 247b62ec17fSDmitri Tikhonov lsquic_rechist_init(&rechist, 0); 24850aadb33SDmitri Tikhonov 24950aadb33SDmitri Tikhonov packno = 0x23456789; 25050aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, packno - 33, now); 25150aadb33SDmitri Tikhonov (void) lsquic_rechist_received(&rechist, packno, now); 25250aadb33SDmitri Tikhonov 25350aadb33SDmitri Tikhonov /* Adjust: */ 254b62ec17fSDmitri Tikhonov rechist.rh_elems[0].re_low = 1; 255b62ec17fSDmitri Tikhonov rechist.rh_elems[0].re_count = packno - 33; 25650aadb33SDmitri Tikhonov 25750aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 25850aadb33SDmitri Tikhonov 0x60 25950aadb33SDmitri Tikhonov | (2 << 2) /* Four-byte largest acked */ 26050aadb33SDmitri Tikhonov | (2 << 0) /* Four-byte ACK block length */ 26150aadb33SDmitri Tikhonov , 26250aadb33SDmitri Tikhonov 0x23, 0x45, 0x67, 0x89, 26350aadb33SDmitri Tikhonov 0x00, 0x00, /* Zero delta time. */ 26450aadb33SDmitri Tikhonov 0x01, /* Num ack blocks ranges. */ 26550aadb33SDmitri Tikhonov 0x00, 0x00, 0x00, 0x01, /* First ack block length. */ 26650aadb33SDmitri Tikhonov 33 - 1, /* Gap to next block. */ 26750aadb33SDmitri Tikhonov 0x23, 0x45, 0x67, 0x68, /* Ack block length. */ 26850aadb33SDmitri Tikhonov 0x00, /* Number of timestamps. */ 26950aadb33SDmitri Tikhonov }; 27050aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 27150aadb33SDmitri Tikhonov 27250aadb33SDmitri Tikhonov int has_missing = -1; 27316a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 27450aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 27550aadb33SDmitri Tikhonov (gaf_rechist_first_f) lsquic_rechist_first, 27650aadb33SDmitri Tikhonov (gaf_rechist_next_f) lsquic_rechist_next, 27750aadb33SDmitri Tikhonov (gaf_rechist_largest_recv_f) lsquic_rechist_largest_recv, 2785392f7a3SLiteSpeed Tech &rechist, now, &has_missing, &largest, NULL); 27950aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 28050aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 28150aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 28250aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 28350aadb33SDmitri Tikhonov assert(("ACK frame has missing packets", has_missing > 0)); 28416a9b66aSDmitri Tikhonov assert(largest == 0x23456789); 28550aadb33SDmitri Tikhonov 28650aadb33SDmitri Tikhonov lsquic_rechist_cleanup(&rechist); 28750aadb33SDmitri Tikhonov} 28850aadb33SDmitri Tikhonov 28950aadb33SDmitri Tikhonov 290b62ec17fSDmitri Tikhonov/* lsquic_rechist no longer supports ranges that require integers 291b62ec17fSDmitri Tikhonov * wider than four bytes -- modify the test to use a custom receive 292b62ec17fSDmitri Tikhonov * history. 293b62ec17fSDmitri Tikhonov */ 294b62ec17fSDmitri Tikhonovstatic const struct lsquic_packno_range test_6byte_ranges[] = { 295b62ec17fSDmitri Tikhonov { .high = 0xABCD23456789, .low = 0xABCD23456789, }, 296b62ec17fSDmitri Tikhonov { .high = 0xABCD23456789 - 33, .low = 1, }, 297b62ec17fSDmitri Tikhonov}; 298b62ec17fSDmitri Tikhonov 299b62ec17fSDmitri Tikhonov 300b62ec17fSDmitri Tikhonovstatic const struct lsquic_packno_range * 301b62ec17fSDmitri Tikhonovtest_6byte_rechist_first (void *rechist) 30250aadb33SDmitri Tikhonov{ 303b62ec17fSDmitri Tikhonov int *next = rechist; 304b62ec17fSDmitri Tikhonov *next = 1; 305b62ec17fSDmitri Tikhonov return &test_6byte_ranges[0]; 306b62ec17fSDmitri Tikhonov}; 30750aadb33SDmitri Tikhonov 30850aadb33SDmitri Tikhonov 309b62ec17fSDmitri Tikhonovstatic const struct lsquic_packno_range * 310b62ec17fSDmitri Tikhonovtest_6byte_rechist_next (void *rechist) 311b62ec17fSDmitri Tikhonov{ 312b62ec17fSDmitri Tikhonov int *next = rechist; 313b62ec17fSDmitri Tikhonov if (*next == 1) 314b62ec17fSDmitri Tikhonov { 315b62ec17fSDmitri Tikhonov ++*next; 316b62ec17fSDmitri Tikhonov return &test_6byte_ranges[1]; 317b62ec17fSDmitri Tikhonov } 318b62ec17fSDmitri Tikhonov else 319b62ec17fSDmitri Tikhonov return NULL; 320b62ec17fSDmitri Tikhonov} 32150aadb33SDmitri Tikhonov 322b62ec17fSDmitri Tikhonov 323b62ec17fSDmitri Tikhonovstatic lsquic_time_t s_test_6byte_now; 324b62ec17fSDmitri Tikhonovstatic lsquic_time_t 325b62ec17fSDmitri Tikhonovtest_6byte_rechist_largest_recv (void *rechist) 326b62ec17fSDmitri Tikhonov{ 327b62ec17fSDmitri Tikhonov return s_test_6byte_now; 328b62ec17fSDmitri Tikhonov} 329b62ec17fSDmitri Tikhonov 330b62ec17fSDmitri Tikhonov 331b62ec17fSDmitri Tikhonovstatic void 332b62ec17fSDmitri Tikhonovtest_6byte_packnos (void) 333b62ec17fSDmitri Tikhonov{ 334b62ec17fSDmitri Tikhonov int rechist = 0; 335b62ec17fSDmitri Tikhonov s_test_6byte_now = lsquic_time_now(); 33650aadb33SDmitri Tikhonov 33750aadb33SDmitri Tikhonov const unsigned char expected_ack_frame[] = { 33850aadb33SDmitri Tikhonov 0x60 33950aadb33SDmitri Tikhonov | (3 << 2) /* Six-byte largest acked */ 34050aadb33SDmitri Tikhonov | (3 << 0) /* Six-byte ACK block length */ 34150aadb33SDmitri Tikhonov , 34250aadb33SDmitri Tikhonov 0xAB, 0xCD, 0x23, 0x45, 0x67, 0x89, 34350aadb33SDmitri Tikhonov 0x00, 0x00, /* Zero delta time. */ 34450aadb33SDmitri Tikhonov 0x01, /* Num ack blocks ranges. */ 34550aadb33SDmitri Tikhonov 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, /* First ack block length. */ 34650aadb33SDmitri Tikhonov 33 - 1, /* Gap to next block. */ 34750aadb33SDmitri Tikhonov 0xAB, 0xCD, 0x23, 0x45, 0x67, 0x68, /* Ack block length. */ 34850aadb33SDmitri Tikhonov 0x00, /* Number of timestamps. */ 34950aadb33SDmitri Tikhonov }; 35050aadb33SDmitri Tikhonov unsigned char outbuf[0x100]; 35150aadb33SDmitri Tikhonov 35250aadb33SDmitri Tikhonov int has_missing = -1; 35316a9b66aSDmitri Tikhonov lsquic_packno_t largest = 0; 35450aadb33SDmitri Tikhonov int w = pf->pf_gen_ack_frame(outbuf, sizeof(outbuf), 355b62ec17fSDmitri Tikhonov test_6byte_rechist_first, 356b62ec17fSDmitri Tikhonov test_6byte_rechist_next, 357b62ec17fSDmitri Tikhonov test_6byte_rechist_largest_recv, 358b62ec17fSDmitri Tikhonov &rechist, s_test_6byte_now, &has_missing, &largest, NULL); 35950aadb33SDmitri Tikhonov assert(("ACK frame generation successful", w > 0)); 36050aadb33SDmitri Tikhonov assert(("ACK frame length is correct", w == sizeof(expected_ack_frame))); 36150aadb33SDmitri Tikhonov assert(("ACK frame contents are as expected", 36250aadb33SDmitri Tikhonov 0 == memcmp(outbuf, expected_ack_frame, sizeof(expected_ack_frame)))); 36350aadb33SDmitri Tikhonov assert(("ACK frame has missing packets", has_missing > 0)); 36416a9b66aSDmitri Tikhonov assert(largest == 0xABCD23456789ULL); 36550aadb33SDmitri Tikhonov} 36650aadb33SDmitri Tikhonov 36750aadb33SDmitri Tikhonov 36850aadb33SDmitri Tikhonovint 36950aadb33SDmitri Tikhonovmain (void) 37050aadb33SDmitri Tikhonov{ 371c51ce338SDmitri Tikhonov lsquic_global_init(LSQUIC_GLOBAL_SERVER); 37250aadb33SDmitri Tikhonov lsquic_log_to_fstream(stderr, 0); 37350aadb33SDmitri Tikhonov lsq_log_levels[LSQLM_PARSE] = LSQ_LOG_DEBUG; 37450aadb33SDmitri Tikhonov 37550aadb33SDmitri Tikhonov test1(); 37650aadb33SDmitri Tikhonov 37750aadb33SDmitri Tikhonov test2(); 37850aadb33SDmitri Tikhonov 37950aadb33SDmitri Tikhonov test3(); 38050aadb33SDmitri Tikhonov 38150aadb33SDmitri Tikhonov test4(); 38250aadb33SDmitri Tikhonov 38350aadb33SDmitri Tikhonov test_4byte_packnos(); 38450aadb33SDmitri Tikhonov 38550aadb33SDmitri Tikhonov test_6byte_packnos(); 38650aadb33SDmitri Tikhonov 38750aadb33SDmitri Tikhonov return 0; 38850aadb33SDmitri Tikhonov} 389