Home | History | Annotate | Line # | Download | only in quic
      1 /*
      2  * Copyright 2022-2026 The OpenSSL Project Authors. All Rights Reserved.
      3  *
      4  * Licensed under the Apache License 2.0 (the "License").  You may not use
      5  * this file except in compliance with the License.  You can obtain a copy
      6  * in the file LICENSE in the source distribution or at
      7  * https://www.openssl.org/source/license.html
      8  */
      9 
     10 #include "internal/quic_txp.h"
     11 #include "internal/quic_fifd.h"
     12 #include "internal/quic_stream_map.h"
     13 #include "internal/quic_error.h"
     14 #include "internal/common.h"
     15 #include <openssl/err.h>
     16 
     17 #define MIN_CRYPTO_HDR_SIZE 3
     18 
     19 #define MIN_FRAME_SIZE_HANDSHAKE_DONE 1
     20 #define MIN_FRAME_SIZE_MAX_DATA 2
     21 #define MIN_FRAME_SIZE_ACK 5
     22 #define MIN_FRAME_SIZE_CRYPTO (MIN_CRYPTO_HDR_SIZE + 1)
     23 #define MIN_FRAME_SIZE_STREAM 3 /* minimum useful size (for non-FIN) */
     24 #define MIN_FRAME_SIZE_MAX_STREAMS_BIDI 2
     25 #define MIN_FRAME_SIZE_MAX_STREAMS_UNI 2
     26 
     27 /*
     28  * Packet Archetypes
     29  * =================
     30  */
     31 
     32 /* Generate normal packets containing most frame types, subject to EL. */
     33 #define TX_PACKETISER_ARCHETYPE_NORMAL 0
     34 
     35 /*
     36  * A probe packet is different in that:
     37  *   - It bypasses CC, but *is* counted as in flight for purposes of CC;
     38  *   - It must be ACK-eliciting.
     39  */
     40 #define TX_PACKETISER_ARCHETYPE_PROBE 1
     41 
     42 /*
     43  * An ACK-only packet is different in that:
     44  *   - It bypasses CC, and is considered a 'non-inflight' packet;
     45  *   - It may not contain anything other than an ACK frame, not even padding.
     46  */
     47 #define TX_PACKETISER_ARCHETYPE_ACK_ONLY 2
     48 
     49 #define TX_PACKETISER_ARCHETYPE_NUM 3
     50 
     51 struct ossl_quic_tx_packetiser_st {
     52     OSSL_QUIC_TX_PACKETISER_ARGS args;
     53 
     54     /*
     55      * Opaque initial token blob provided by caller. TXP frees using the
     56      * callback when it is no longer needed.
     57      */
     58     const unsigned char *initial_token;
     59     size_t initial_token_len;
     60     ossl_quic_initial_token_free_fn *initial_token_free_cb;
     61     void *initial_token_free_cb_arg;
     62 
     63     /* Subcomponents of the TXP that we own. */
     64     QUIC_FIFD fifd; /* QUIC Frame-in-Flight Dispatcher */
     65 
     66     /* Internal state. */
     67     uint64_t next_pn[QUIC_PN_SPACE_NUM]; /* Next PN to use in given PN space. */
     68     OSSL_TIME last_tx_time; /* Last time a packet was generated, or 0. */
     69 
     70     size_t unvalidated_credit; /* Limit of data we can send until validated */
     71 
     72     /* Internal state - frame (re)generation flags. */
     73     unsigned int want_handshake_done : 1;
     74     unsigned int want_max_data : 1;
     75     unsigned int want_max_streams_bidi : 1;
     76     unsigned int want_max_streams_uni : 1;
     77 
     78     /* Internal state - frame (re)generation flags - per PN space. */
     79     unsigned int want_ack : QUIC_PN_SPACE_NUM;
     80     unsigned int force_ack_eliciting : QUIC_PN_SPACE_NUM;
     81 
     82     /*
     83      * Internal state - connection close terminal state.
     84      * Once this is set, it is not unset unlike other want_ flags - we keep
     85      * sending it in every packet.
     86      */
     87     unsigned int want_conn_close : 1;
     88 
     89     /* Has the handshake been completed? */
     90     unsigned int handshake_complete : 1;
     91 
     92     OSSL_QUIC_FRAME_CONN_CLOSE conn_close_frame;
     93 
     94     /*
     95      * Counts of the number of bytes received and sent while in the closing
     96      * state.
     97      */
     98     uint64_t closing_bytes_recv;
     99     uint64_t closing_bytes_xmit;
    100 
    101     /* Internal state - packet assembly. */
    102     struct txp_el {
    103         unsigned char *scratch; /* scratch buffer for packet assembly */
    104         size_t scratch_len; /* number of bytes allocated for scratch */
    105         OSSL_QTX_IOVEC *iovec; /* scratch iovec array for use with QTX */
    106         size_t alloc_iovec; /* size of iovec array */
    107     } el[QUIC_ENC_LEVEL_NUM];
    108 
    109     /* Message callback related arguments */
    110     ossl_msg_cb msg_callback;
    111     void *msg_callback_arg;
    112     SSL *msg_callback_ssl;
    113 
    114     /* Callbacks. */
    115     void (*ack_tx_cb)(const OSSL_QUIC_FRAME_ACK *ack,
    116         uint32_t pn_space,
    117         void *arg);
    118     void *ack_tx_cb_arg;
    119 };
    120 
    121 /*
    122  * The TX helper records state used while generating frames into packets. It
    123  * enables serialization into the packet to be done "transactionally" where
    124  * serialization of a frame can be rolled back if it fails midway (e.g. if it
    125  * does not fit).
    126  */
    127 struct tx_helper {
    128     OSSL_QUIC_TX_PACKETISER *txp;
    129     /*
    130      * The Maximum Packet Payload Length in bytes. This is the amount of
    131      * space we have to generate frames into.
    132      */
    133     size_t max_ppl;
    134     /*
    135      * Number of bytes we have generated so far.
    136      */
    137     size_t bytes_appended;
    138     /*
    139      * Number of scratch bytes in txp->scratch we have used so far. Some iovecs
    140      * will reference this scratch buffer. When we need to use more of it (e.g.
    141      * when we need to put frame headers somewhere), we append to the scratch
    142      * buffer, resizing if necessary, and increase this accordingly.
    143      */
    144     size_t scratch_bytes;
    145     /*
    146      * Bytes reserved in the MaxPPL budget. We keep this number of bytes spare
    147      * until reserve_allowed is set to 1. Currently this is always at most 1, as
    148      * a PING frame takes up one byte and this mechanism is only used to ensure
    149      * we can encode a PING frame if we have been asked to ensure a packet is
    150      * ACK-eliciting and we are unusure if we are going to add any other
    151      * ACK-eliciting frames before we reach our MaxPPL budget.
    152      */
    153     size_t reserve;
    154     /*
    155      * Number of iovecs we have currently appended. This is the number of
    156      * entries valid in txp->iovec.
    157      */
    158     size_t num_iovec;
    159     /* The EL this TX helper is being used for. */
    160     uint32_t enc_level;
    161     /*
    162      * Whether we are allowed to make use of the reserve bytes in our MaxPPL
    163      * budget. This is used to ensure we have room to append a PING frame later
    164      * if we need to. Once we know we will not need to append a PING frame, this
    165      * is set to 1.
    166      */
    167     unsigned int reserve_allowed : 1;
    168     /*
    169      * Set to 1 if we have appended a STREAM frame with an implicit length. If
    170      * this happens we should never append another frame after that frame as it
    171      * cannot be validly encoded. This is just a safety check.
    172      */
    173     unsigned int done_implicit : 1;
    174     struct {
    175         /*
    176          * The fields in this structure are valid if active is set, which means
    177          * that a serialization transaction is currently in progress.
    178          */
    179         unsigned char *data;
    180         WPACKET wpkt;
    181         unsigned int active : 1;
    182     } txn;
    183 };
    184 
    185 static void tx_helper_rollback(struct tx_helper *h);
    186 static int txp_el_ensure_iovec(struct txp_el *el, size_t num);
    187 
    188 /* Initialises the TX helper. */
    189 static int tx_helper_init(struct tx_helper *h, OSSL_QUIC_TX_PACKETISER *txp,
    190     uint32_t enc_level, size_t max_ppl, size_t reserve)
    191 {
    192     if (reserve > max_ppl)
    193         return 0;
    194 
    195     h->txp = txp;
    196     h->enc_level = enc_level;
    197     h->max_ppl = max_ppl;
    198     h->reserve = reserve;
    199     h->num_iovec = 0;
    200     h->bytes_appended = 0;
    201     h->scratch_bytes = 0;
    202     h->reserve_allowed = 0;
    203     h->done_implicit = 0;
    204     h->txn.data = NULL;
    205     h->txn.active = 0;
    206 
    207     if (max_ppl > h->txp->el[enc_level].scratch_len) {
    208         unsigned char *scratch;
    209 
    210         scratch = OPENSSL_realloc(h->txp->el[enc_level].scratch, max_ppl);
    211         if (scratch == NULL)
    212             return 0;
    213 
    214         h->txp->el[enc_level].scratch = scratch;
    215         h->txp->el[enc_level].scratch_len = max_ppl;
    216     }
    217 
    218     return 1;
    219 }
    220 
    221 static void tx_helper_cleanup(struct tx_helper *h)
    222 {
    223     if (h->txn.active)
    224         tx_helper_rollback(h);
    225 
    226     h->txp = NULL;
    227 }
    228 
    229 static void tx_helper_unrestrict(struct tx_helper *h)
    230 {
    231     h->reserve_allowed = 1;
    232 }
    233 
    234 /*
    235  * Append an extent of memory to the iovec list. The memory must remain
    236  * allocated until we finish generating the packet and call the QTX.
    237  *
    238  * In general, the buffers passed to this function will be from one of two
    239  * ranges:
    240  *
    241  *   - Application data contained in stream buffers managed elsewhere
    242  *     in the QUIC stack; or
    243  *
    244  *   - Control frame data appended into txp->scratch using tx_helper_begin and
    245  *     tx_helper_commit.
    246  *
    247  */
    248 static int tx_helper_append_iovec(struct tx_helper *h,
    249     const unsigned char *buf,
    250     size_t buf_len)
    251 {
    252     struct txp_el *el = &h->txp->el[h->enc_level];
    253 
    254     if (buf_len == 0)
    255         return 1;
    256 
    257     if (!ossl_assert(!h->done_implicit))
    258         return 0;
    259 
    260     if (!txp_el_ensure_iovec(el, h->num_iovec + 1))
    261         return 0;
    262 
    263     el->iovec[h->num_iovec].buf = buf;
    264     el->iovec[h->num_iovec].buf_len = buf_len;
    265 
    266     ++h->num_iovec;
    267     h->bytes_appended += buf_len;
    268     return 1;
    269 }
    270 
    271 /*
    272  * How many more bytes of space do we have left in our plaintext packet payload?
    273  */
    274 static size_t tx_helper_get_space_left(struct tx_helper *h)
    275 {
    276     return h->max_ppl
    277         - (h->reserve_allowed ? 0 : h->reserve) - h->bytes_appended;
    278 }
    279 
    280 /*
    281  * Begin a control frame serialization transaction. This allows the
    282  * serialization of the control frame to be backed out if it turns out it won't
    283  * fit. Write the control frame to the returned WPACKET. Ensure you always
    284  * call tx_helper_rollback or tx_helper_commit (or tx_helper_cleanup). Returns
    285  * NULL on failure.
    286  */
    287 static WPACKET *tx_helper_begin(struct tx_helper *h)
    288 {
    289     size_t space_left, len;
    290     unsigned char *data;
    291     struct txp_el *el = &h->txp->el[h->enc_level];
    292 
    293     if (!ossl_assert(!h->txn.active))
    294         return NULL;
    295 
    296     if (!ossl_assert(!h->done_implicit))
    297         return NULL;
    298 
    299     data = (unsigned char *)el->scratch + h->scratch_bytes;
    300     len = el->scratch_len - h->scratch_bytes;
    301 
    302     space_left = tx_helper_get_space_left(h);
    303     if (!ossl_assert(space_left <= len))
    304         return NULL;
    305 
    306     if (!WPACKET_init_static_len(&h->txn.wpkt, data, len, 0))
    307         return NULL;
    308 
    309     if (!WPACKET_set_max_size(&h->txn.wpkt, space_left)) {
    310         WPACKET_cleanup(&h->txn.wpkt);
    311         return NULL;
    312     }
    313 
    314     h->txn.data = data;
    315     h->txn.active = 1;
    316     return &h->txn.wpkt;
    317 }
    318 
    319 static void tx_helper_end(struct tx_helper *h, int success)
    320 {
    321     if (success)
    322         WPACKET_finish(&h->txn.wpkt);
    323     else
    324         WPACKET_cleanup(&h->txn.wpkt);
    325 
    326     h->txn.active = 0;
    327     h->txn.data = NULL;
    328 }
    329 
    330 /* Abort a control frame serialization transaction. */
    331 static void tx_helper_rollback(struct tx_helper *h)
    332 {
    333     if (!h->txn.active)
    334         return;
    335 
    336     tx_helper_end(h, 0);
    337 }
    338 
    339 /* Commit a control frame. */
    340 static int tx_helper_commit(struct tx_helper *h)
    341 {
    342     size_t l = 0;
    343 
    344     if (!h->txn.active)
    345         return 0;
    346 
    347     if (!WPACKET_get_total_written(&h->txn.wpkt, &l)) {
    348         tx_helper_end(h, 0);
    349         return 0;
    350     }
    351 
    352     if (!tx_helper_append_iovec(h, h->txn.data, l)) {
    353         tx_helper_end(h, 0);
    354         return 0;
    355     }
    356 
    357     if (h->txp->msg_callback != NULL && l > 0) {
    358         uint64_t ftype;
    359         int ctype = SSL3_RT_QUIC_FRAME_FULL;
    360         PACKET pkt;
    361 
    362         if (!PACKET_buf_init(&pkt, h->txn.data, l)
    363             || !ossl_quic_wire_peek_frame_header(&pkt, &ftype, NULL)) {
    364             tx_helper_end(h, 0);
    365             return 0;
    366         }
    367 
    368         if (ftype == OSSL_QUIC_FRAME_TYPE_PADDING)
    369             ctype = SSL3_RT_QUIC_FRAME_PADDING;
    370         else if (OSSL_QUIC_FRAME_TYPE_IS_STREAM(ftype)
    371             || ftype == OSSL_QUIC_FRAME_TYPE_CRYPTO)
    372             ctype = SSL3_RT_QUIC_FRAME_HEADER;
    373 
    374         h->txp->msg_callback(1, OSSL_QUIC1_VERSION, ctype, h->txn.data, l,
    375             h->txp->msg_callback_ssl,
    376             h->txp->msg_callback_arg);
    377     }
    378 
    379     h->scratch_bytes += l;
    380     tx_helper_end(h, 1);
    381     return 1;
    382 }
    383 
    384 struct archetype_data {
    385     unsigned int allow_ack : 1;
    386     unsigned int allow_ping : 1;
    387     unsigned int allow_crypto : 1;
    388     unsigned int allow_handshake_done : 1;
    389     unsigned int allow_path_challenge : 1;
    390     unsigned int allow_path_response : 1;
    391     unsigned int allow_new_conn_id : 1;
    392     unsigned int allow_retire_conn_id : 1;
    393     unsigned int allow_stream_rel : 1;
    394     unsigned int allow_conn_fc : 1;
    395     unsigned int allow_conn_close : 1;
    396     unsigned int allow_cfq_other : 1;
    397     unsigned int allow_new_token : 1;
    398     unsigned int allow_force_ack_eliciting : 1;
    399     unsigned int allow_padding : 1;
    400     unsigned int require_ack_eliciting : 1;
    401     unsigned int bypass_cc : 1;
    402 };
    403 
    404 struct txp_pkt_geom {
    405     size_t cmpl, cmppl, hwm, pkt_overhead;
    406     uint32_t archetype;
    407     struct archetype_data adata;
    408 };
    409 
    410 struct txp_pkt {
    411     struct tx_helper h;
    412     int h_valid;
    413     QUIC_TXPIM_PKT *tpkt;
    414     QUIC_STREAM *stream_head;
    415     QUIC_PKT_HDR phdr;
    416     struct txp_pkt_geom geom;
    417     int force_pad;
    418 };
    419 
    420 static QUIC_SSTREAM *get_sstream_by_id(uint64_t stream_id, uint32_t pn_space,
    421     void *arg);
    422 static void on_regen_notify(uint64_t frame_type, uint64_t stream_id,
    423     QUIC_TXPIM_PKT *pkt, void *arg);
    424 static void on_confirm_notify(uint64_t frame_type, uint64_t stream_id,
    425     QUIC_TXPIM_PKT *pkt, void *arg);
    426 static void on_sstream_updated(uint64_t stream_id, void *arg);
    427 static int sstream_is_pending(QUIC_SSTREAM *sstream);
    428 static int txp_should_try_staging(OSSL_QUIC_TX_PACKETISER *txp,
    429     uint32_t enc_level,
    430     uint32_t archetype,
    431     uint64_t cc_limit,
    432     uint32_t *conn_close_enc_level);
    433 static size_t txp_determine_pn_len(OSSL_QUIC_TX_PACKETISER *txp);
    434 static int txp_determine_ppl_from_pl(OSSL_QUIC_TX_PACKETISER *txp,
    435     size_t pl,
    436     uint32_t enc_level,
    437     size_t hdr_len,
    438     size_t *r);
    439 static size_t txp_get_mdpl(OSSL_QUIC_TX_PACKETISER *txp);
    440 static int txp_generate_for_el(OSSL_QUIC_TX_PACKETISER *txp,
    441     struct txp_pkt *pkt,
    442     int chosen_for_conn_close);
    443 static int txp_pkt_init(struct txp_pkt *pkt, OSSL_QUIC_TX_PACKETISER *txp,
    444     uint32_t enc_level, uint32_t archetype,
    445     size_t running_total);
    446 static void txp_pkt_cleanup(struct txp_pkt *pkt, OSSL_QUIC_TX_PACKETISER *txp);
    447 static int txp_pkt_postgen_update_pkt_overhead(struct txp_pkt *pkt,
    448     OSSL_QUIC_TX_PACKETISER *txp);
    449 static int txp_pkt_append_padding(struct txp_pkt *pkt,
    450     OSSL_QUIC_TX_PACKETISER *txp, size_t num_bytes);
    451 static int txp_pkt_commit(OSSL_QUIC_TX_PACKETISER *txp, struct txp_pkt *pkt,
    452     uint32_t archetype, int *txpim_pkt_reffed);
    453 static uint32_t txp_determine_archetype(OSSL_QUIC_TX_PACKETISER *txp,
    454     uint64_t cc_limit);
    455 
    456 /**
    457  * Sets the validated state of a QUIC TX packetiser.
    458  *
    459  * This function marks the provided QUIC TX packetiser as having its credit
    460  * fully validated by setting its `unvalidated_credit` field to `SIZE_MAX`.
    461  *
    462  * @param txp A pointer to the OSSL_QUIC_TX_PACKETISER structure to update.
    463  */
    464 void ossl_quic_tx_packetiser_set_validated(OSSL_QUIC_TX_PACKETISER *txp)
    465 {
    466     txp->unvalidated_credit = SIZE_MAX;
    467     return;
    468 }
    469 
    470 /**
    471  * Adds unvalidated credit to a QUIC TX packetiser.
    472  *
    473  * This function increases the unvalidated credit of the provided QUIC TX
    474  * packetiser. If the current unvalidated credit is not `SIZE_MAX`, the
    475  * function adds three times the specified `credit` value, ensuring it does
    476  * not exceed the maximum allowable value (`SIZE_MAX - 1`). If the addition
    477  * would cause an overflow, the unvalidated credit is capped at
    478  * `SIZE_MAX - 1`. If the current unvalidated credit is already `SIZE_MAX`,
    479  * the function does nothing.
    480  *
    481  * @param txp    A pointer to the OSSL_QUIC_TX_PACKETISER structure to update.
    482  * @param credit The amount of credit to add, multiplied by 3.
    483  */
    484 void ossl_quic_tx_packetiser_add_unvalidated_credit(OSSL_QUIC_TX_PACKETISER *txp,
    485     size_t credit)
    486 {
    487     if (txp->unvalidated_credit != SIZE_MAX) {
    488         if ((SIZE_MAX - txp->unvalidated_credit) > (credit * 3))
    489             txp->unvalidated_credit += credit * 3;
    490         else
    491             txp->unvalidated_credit = SIZE_MAX - 1;
    492     }
    493 
    494     return;
    495 }
    496 
    497 /**
    498  * Consumes unvalidated credit from a QUIC TX packetiser.
    499  *
    500  * This function decreases the unvalidated credit of the specified
    501  * QUIC TX packetiser by the given `credit` value. If the unvalidated credit
    502  * is set to `SIZE_MAX`, the function does nothing, as `SIZE_MAX` represents
    503  * an unlimited credit state.
    504  *
    505  * @param txp    A pointer to the OSSL_QUIC_TX_PACKETISER structure to update.
    506  * @param credit The amount of credit to consume.
    507  */
    508 void ossl_quic_tx_packetiser_consume_unvalidated_credit(OSSL_QUIC_TX_PACKETISER *txp,
    509     size_t credit)
    510 {
    511     if (txp->unvalidated_credit != SIZE_MAX) {
    512         if (txp->unvalidated_credit < credit)
    513             txp->unvalidated_credit = 0;
    514         else
    515             txp->unvalidated_credit -= credit;
    516     }
    517 }
    518 
    519 /**
    520  * Checks if the QUIC TX packetiser has sufficient unvalidated credit.
    521  *
    522  * This function determines whether the unvalidated credit of the specified
    523  * QUIC TX packetiser exceeds the required credit value (`req_credit`).
    524  * If the unvalidated credit is greater than `req_credit`, the function
    525  * returns 1 (true); otherwise, it returns 0 (false).
    526  *
    527  * @param txp        A pointer to the OSSL_QUIC_TX_PACKETISER structure to check.
    528  * @param req_credit The required credit value to compare against.
    529  *
    530  * @return 1 if the unvalidated credit exceeds `req_credit`, 0 otherwise.
    531  */
    532 int ossl_quic_tx_packetiser_check_unvalidated_credit(OSSL_QUIC_TX_PACKETISER *txp,
    533     size_t req_credit)
    534 {
    535     return (txp->unvalidated_credit > req_credit);
    536 }
    537 
    538 OSSL_QUIC_TX_PACKETISER *ossl_quic_tx_packetiser_new(const OSSL_QUIC_TX_PACKETISER_ARGS *args)
    539 {
    540     OSSL_QUIC_TX_PACKETISER *txp;
    541 
    542     if (args == NULL
    543         || args->qtx == NULL
    544         || args->txpim == NULL
    545         || args->cfq == NULL
    546         || args->ackm == NULL
    547         || args->qsm == NULL
    548         || args->conn_txfc == NULL
    549         || args->conn_rxfc == NULL
    550         || args->max_streams_bidi_rxfc == NULL
    551         || args->max_streams_uni_rxfc == NULL
    552         || args->protocol_version == 0) {
    553         ERR_raise(ERR_LIB_SSL, ERR_R_PASSED_NULL_PARAMETER);
    554         return NULL;
    555     }
    556 
    557     txp = OPENSSL_zalloc(sizeof(*txp));
    558     if (txp == NULL)
    559         return NULL;
    560 
    561     txp->args = *args;
    562     txp->last_tx_time = ossl_time_zero();
    563 
    564     if (!ossl_quic_fifd_init(&txp->fifd,
    565             txp->args.cfq, txp->args.ackm, txp->args.txpim,
    566             get_sstream_by_id, txp,
    567             on_regen_notify, txp,
    568             on_confirm_notify, txp,
    569             on_sstream_updated, txp,
    570             args->get_qlog_cb,
    571             args->get_qlog_cb_arg)) {
    572         OPENSSL_free(txp);
    573         return NULL;
    574     }
    575 
    576     return txp;
    577 }
    578 
    579 void ossl_quic_tx_packetiser_free(OSSL_QUIC_TX_PACKETISER *txp)
    580 {
    581     uint32_t enc_level;
    582 
    583     if (txp == NULL)
    584         return;
    585 
    586     ossl_quic_tx_packetiser_set_initial_token(txp, NULL, 0, NULL, NULL);
    587     ossl_quic_fifd_cleanup(&txp->fifd);
    588     OPENSSL_free(txp->conn_close_frame.reason);
    589 
    590     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
    591         enc_level < QUIC_ENC_LEVEL_NUM;
    592         ++enc_level) {
    593         OPENSSL_free(txp->el[enc_level].iovec);
    594         OPENSSL_free(txp->el[enc_level].scratch);
    595     }
    596 
    597     OPENSSL_free(txp);
    598 }
    599 
    600 /*
    601  * Determine if an Initial packet token length is reasonable based on the
    602  * current MDPL, returning 1 if it is OK.
    603  *
    604  * The real PMTU to the peer could differ from our (pessimistic) understanding
    605  * of the PMTU, therefore it is possible we could receive an Initial token from
    606  * a server in a Retry packet which is bigger than the MDPL. In this case it is
    607  * impossible for us ever to make forward progress and we need to error out
    608  * and fail the connection attempt.
    609  *
    610  * The specific boundary condition is complex: for example, after the size of
    611  * the Initial token, there are the Initial packet header overheads and then
    612  * encryption/AEAD tag overheads. After that, the minimum room for frame data in
    613  * order to guarantee forward progress must be guaranteed. For example, a crypto
    614  * stream needs to always be able to serialize at least one byte in a CRYPTO
    615  * frame in order to make forward progress. Because the offset field of a CRYPTO
    616  * frame uses a variable-length integer, the number of bytes needed to ensure
    617  * this also varies.
    618  *
    619  * Rather than trying to get this boundary condition check actually right,
    620  * require a reasonable amount of slack to avoid pathological behaviours. (After
    621  * all, transmitting a CRYPTO stream one byte at a time is probably not
    622  * desirable anyway.)
    623  *
    624  * We choose 160 bytes as the required margin, which is double the rough
    625  * estimation of the minimum we would require to guarantee forward progress
    626  * under worst case packet overheads.
    627  */
    628 #define TXP_REQUIRED_TOKEN_MARGIN 160
    629 
    630 static int txp_check_token_len(size_t token_len, size_t mdpl)
    631 {
    632     if (token_len == 0)
    633         return 1;
    634 
    635     if (token_len >= mdpl)
    636         return 0;
    637 
    638     if (TXP_REQUIRED_TOKEN_MARGIN >= mdpl)
    639         /* (should not be possible because MDPL must be at least 1200) */
    640         return 0;
    641 
    642     if (token_len > mdpl - TXP_REQUIRED_TOKEN_MARGIN)
    643         return 0;
    644 
    645     return 1;
    646 }
    647 
    648 int ossl_quic_tx_packetiser_set_initial_token(OSSL_QUIC_TX_PACKETISER *txp,
    649     const unsigned char *token,
    650     size_t token_len,
    651     ossl_quic_initial_token_free_fn *free_cb,
    652     void *free_cb_arg)
    653 {
    654     if (!txp_check_token_len(token_len, txp_get_mdpl(txp)))
    655         return 0;
    656 
    657     if (txp->initial_token != NULL && txp->initial_token_free_cb != NULL)
    658         txp->initial_token_free_cb(txp->initial_token, txp->initial_token_len,
    659             txp->initial_token_free_cb_arg);
    660 
    661     txp->initial_token = token;
    662     txp->initial_token_len = token_len;
    663     txp->initial_token_free_cb = free_cb;
    664     txp->initial_token_free_cb_arg = free_cb_arg;
    665     return 1;
    666 }
    667 
    668 int ossl_quic_tx_packetiser_set_protocol_version(OSSL_QUIC_TX_PACKETISER *txp,
    669     uint32_t protocol_version)
    670 {
    671     txp->args.protocol_version = protocol_version;
    672     return 1;
    673 }
    674 
    675 int ossl_quic_tx_packetiser_set_cur_dcid(OSSL_QUIC_TX_PACKETISER *txp,
    676     const QUIC_CONN_ID *dcid)
    677 {
    678     if (dcid == NULL) {
    679         ERR_raise(ERR_LIB_SSL, ERR_R_PASSED_NULL_PARAMETER);
    680         return 0;
    681     }
    682 
    683     txp->args.cur_dcid = *dcid;
    684     return 1;
    685 }
    686 
    687 int ossl_quic_tx_packetiser_set_cur_scid(OSSL_QUIC_TX_PACKETISER *txp,
    688     const QUIC_CONN_ID *scid)
    689 {
    690     if (scid == NULL) {
    691         ERR_raise(ERR_LIB_SSL, ERR_R_PASSED_NULL_PARAMETER);
    692         return 0;
    693     }
    694 
    695     txp->args.cur_scid = *scid;
    696     return 1;
    697 }
    698 
    699 /* Change the destination L4 address the TXP uses to send datagrams. */
    700 int ossl_quic_tx_packetiser_set_peer(OSSL_QUIC_TX_PACKETISER *txp,
    701     const BIO_ADDR *peer)
    702 {
    703     if (peer == NULL) {
    704         BIO_ADDR_clear(&txp->args.peer);
    705         return 1;
    706     }
    707 
    708     return BIO_ADDR_copy(&txp->args.peer, peer);
    709 }
    710 
    711 void ossl_quic_tx_packetiser_set_ack_tx_cb(OSSL_QUIC_TX_PACKETISER *txp,
    712     void (*cb)(const OSSL_QUIC_FRAME_ACK *ack,
    713         uint32_t pn_space,
    714         void *arg),
    715     void *cb_arg)
    716 {
    717     txp->ack_tx_cb = cb;
    718     txp->ack_tx_cb_arg = cb_arg;
    719 }
    720 
    721 void ossl_quic_tx_packetiser_set_qlog_cb(OSSL_QUIC_TX_PACKETISER *txp,
    722     QLOG *(*get_qlog_cb)(void *arg),
    723     void *get_qlog_cb_arg)
    724 {
    725     ossl_quic_fifd_set_qlog_cb(&txp->fifd, get_qlog_cb, get_qlog_cb_arg);
    726 }
    727 
    728 int ossl_quic_tx_packetiser_discard_enc_level(OSSL_QUIC_TX_PACKETISER *txp,
    729     uint32_t enc_level)
    730 {
    731     if (enc_level >= QUIC_ENC_LEVEL_NUM) {
    732         ERR_raise(ERR_LIB_SSL, ERR_R_PASSED_INVALID_ARGUMENT);
    733         return 0;
    734     }
    735 
    736     if (enc_level != QUIC_ENC_LEVEL_0RTT)
    737         txp->args.crypto[ossl_quic_enc_level_to_pn_space(enc_level)] = NULL;
    738 
    739     return 1;
    740 }
    741 
    742 void ossl_quic_tx_packetiser_notify_handshake_complete(OSSL_QUIC_TX_PACKETISER *txp)
    743 {
    744     txp->handshake_complete = 1;
    745 }
    746 
    747 void ossl_quic_tx_packetiser_schedule_handshake_done(OSSL_QUIC_TX_PACKETISER *txp)
    748 {
    749     txp->want_handshake_done = 1;
    750 }
    751 
    752 void ossl_quic_tx_packetiser_schedule_ack_eliciting(OSSL_QUIC_TX_PACKETISER *txp,
    753     uint32_t pn_space)
    754 {
    755     txp->force_ack_eliciting |= (1UL << pn_space);
    756 }
    757 
    758 void ossl_quic_tx_packetiser_schedule_ack(OSSL_QUIC_TX_PACKETISER *txp,
    759     uint32_t pn_space)
    760 {
    761     txp->want_ack |= (1UL << pn_space);
    762 }
    763 
    764 #define TXP_ERR_INTERNAL 0 /* Internal (e.g. alloc) error */
    765 #define TXP_ERR_SUCCESS 1 /* Success */
    766 #define TXP_ERR_SPACE 2 /* Not enough room for another packet */
    767 #define TXP_ERR_INPUT 3 /* Invalid/malformed input */
    768 
    769 /*
    770  * Generates a datagram by polling the various ELs to determine if they want to
    771  * generate any frames, and generating a datagram which coalesces packets for
    772  * any ELs which do.
    773  */
    774 int ossl_quic_tx_packetiser_generate(OSSL_QUIC_TX_PACKETISER *txp,
    775     QUIC_TXP_STATUS *status)
    776 {
    777     /*
    778      * Called to generate one or more datagrams, each containing one or more
    779      * packets.
    780      *
    781      * There are some tricky things to note here:
    782      *
    783      *   - The TXP is only concerned with generating encrypted packets;
    784      *     other packets use a different path.
    785      *
    786      *   - Any datagram containing an Initial packet must have a payload length
    787      *     (DPL) of at least 1200 bytes. This padding need not necessarily be
    788      *     found in the Initial packet.
    789      *
    790      *     - It is desirable to be able to coalesce an Initial packet
    791      *       with a Handshake packet. Since, before generating the Handshake
    792      *       packet, we do not know how long it will be, we cannot know the
    793      *       correct amount of padding to ensure a DPL of at least 1200 bytes.
    794      *       Thus this padding must added to the Handshake packet (or whatever
    795      *       packet is the last in the datagram).
    796      *
    797      *     - However, at the time that we generate the Initial packet,
    798      *       we do not actually know for sure that we will be followed
    799      *       in the datagram by another packet. For example, suppose we have
    800      *       some queued data (e.g. crypto stream data for the HANDSHAKE EL)
    801      *       it looks like we will want to send on the HANDSHAKE EL.
    802      *       We could assume padding will be placed in the Handshake packet
    803      *       subsequently and avoid adding any padding to the Initial packet
    804      *       (which would leave no room for the Handshake packet in the
    805      *       datagram).
    806      *
    807      *       However, this is not actually a safe assumption. Suppose that we
    808      *       are using a link with a MDPL of 1200 bytes, the minimum allowed by
    809      *       QUIC. Suppose that the Initial packet consumes 1195 bytes in total.
    810      *       Since it is not possible to fit a Handshake packet in just 5 bytes,
    811      *       upon trying to add a Handshake packet after generating the Initial
    812      *       packet, we will discover we have no room to fit it! This is not a
    813      *       problem in itself as another datagram can be sent subsequently, but
    814      *       it is a problem because we were counting to use that packet to hold
    815      *       the essential padding. But if we have already finished encrypting
    816      *       the Initial packet, we cannot go and add padding to it anymore.
    817      *       This leaves us stuck.
    818      *
    819      * Because of this, we have to plan multiple packets simultaneously, such
    820      * that we can start generating a Handshake (or 0-RTT or 1-RTT, or so on)
    821      * packet while still having the option to go back and add padding to the
    822      * Initial packet if it turns out to be needed.
    823      *
    824      * Trying to predict ahead of time (e.g. during Initial packet generation)
    825      * whether we will successfully generate a subsequent packet is fraught with
    826      * error as it relies on a large number of variables:
    827      *
    828      *   - Do we have room to fit a packet header? (Consider that due to
    829      *     variable-length integer encoding this is highly variable and can even
    830      *     depend on payload length due to a variable-length Length field.)
    831      *
    832      *   - Can we fit even a single one of the frames we want to put in this
    833      *     packet in the packet? (Each frame type has a bespoke encoding. While
    834      *     our encodings of some frame types are adaptive based on the available
    835      *     room - e.g. STREAM frames - ultimately all frame types have some
    836      *     absolute minimum number of bytes to be successfully encoded. For
    837      *     example, if after an Initial packet there is enough room to encode
    838      *     only one byte of frame data, it is quite likely we can't send any of
    839      *     the frames we wanted to send.) While this is not strictly a problem
    840      *     because we could just fill the packet with padding frames, this is a
    841      *     pointless packet and is wasteful.
    842      *
    843      * Thus we adopt a multi-phase architecture:
    844      *
    845      *   1. Archetype Selection: Determine desired packet archetype.
    846      *
    847      *   2. Packet Staging: Generation of packet information and packet payload
    848      *      data (frame data) into staging areas.
    849      *
    850      *   3. Packet Adjustment: Adjustment of staged packets, adding padding to
    851      *      the staged packets if needed.
    852      *
    853      *   4. Commit: The packets are sent to the QTX and recorded as having been
    854      *      sent to the FIFM.
    855      *
    856      */
    857     int res = 0, rc;
    858     uint32_t archetype, enc_level;
    859     uint32_t conn_close_enc_level = QUIC_ENC_LEVEL_NUM;
    860     struct txp_pkt pkt[QUIC_ENC_LEVEL_NUM];
    861     size_t pkts_done = 0;
    862     uint64_t cc_limit = txp->args.cc_method->get_tx_allowance(txp->args.cc_data);
    863     int need_padding = 0, txpim_pkt_reffed;
    864 
    865     memset(status, 0, sizeof(*status));
    866 
    867     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
    868         enc_level < QUIC_ENC_LEVEL_NUM;
    869         ++enc_level)
    870         pkt[enc_level].h_valid = 0;
    871 
    872     /*
    873      * Should not be needed, but a sanity check in case anyone else has been
    874      * using the QTX.
    875      */
    876     ossl_qtx_finish_dgram(txp->args.qtx);
    877 
    878     /* 1. Archetype Selection */
    879     archetype = txp_determine_archetype(txp, cc_limit);
    880 
    881     /* 2. Packet Staging */
    882     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
    883         enc_level < QUIC_ENC_LEVEL_NUM;
    884         ++enc_level) {
    885         size_t running_total = (enc_level > QUIC_ENC_LEVEL_INITIAL)
    886             ? pkt[enc_level - 1].geom.hwm
    887             : 0;
    888 
    889         pkt[enc_level].geom.hwm = running_total;
    890 
    891         if (!txp_should_try_staging(txp, enc_level, archetype, cc_limit,
    892                 &conn_close_enc_level))
    893             continue;
    894 
    895         if (!txp_pkt_init(&pkt[enc_level], txp, enc_level, archetype,
    896                 running_total))
    897             /*
    898              * If this fails this is not a fatal error - it means the geometry
    899              * planning determined there was not enough space for another
    900              * packet. So just proceed with what we've already planned for.
    901              */
    902             break;
    903 
    904         rc = txp_generate_for_el(txp, &pkt[enc_level],
    905             conn_close_enc_level == enc_level);
    906         if (rc != TXP_ERR_SUCCESS)
    907             goto out;
    908 
    909         if (pkt[enc_level].force_pad)
    910             /*
    911              * txp_generate_for_el emitted a frame which forces packet padding.
    912              */
    913             need_padding = 1;
    914 
    915         pkt[enc_level].geom.hwm = running_total
    916             + pkt[enc_level].h.bytes_appended
    917             + pkt[enc_level].geom.pkt_overhead;
    918     }
    919 
    920     /* 3. Packet Adjustment */
    921     if (pkt[QUIC_ENC_LEVEL_INITIAL].h_valid
    922         && pkt[QUIC_ENC_LEVEL_INITIAL].h.bytes_appended > 0)
    923         /*
    924          * We have an Initial packet in this datagram, so we need to make sure
    925          * the total size of the datagram is adequate.
    926          */
    927         need_padding = 1;
    928 
    929     if (need_padding) {
    930         size_t total_dgram_size = 0;
    931         const size_t min_dpl = QUIC_MIN_INITIAL_DGRAM_LEN;
    932         uint32_t pad_el = QUIC_ENC_LEVEL_NUM;
    933 
    934         for (enc_level = QUIC_ENC_LEVEL_INITIAL;
    935             enc_level < QUIC_ENC_LEVEL_NUM;
    936             ++enc_level)
    937             if (pkt[enc_level].h_valid && pkt[enc_level].h.bytes_appended > 0) {
    938                 if (pad_el == QUIC_ENC_LEVEL_NUM
    939                     /*
    940                      * We might not be able to add padding, for example if we
    941                      * are using the ACK_ONLY archetype.
    942                      */
    943                     && pkt[enc_level].geom.adata.allow_padding
    944                     && !pkt[enc_level].h.done_implicit)
    945                     pad_el = enc_level;
    946 
    947                 txp_pkt_postgen_update_pkt_overhead(&pkt[enc_level], txp);
    948                 total_dgram_size += pkt[enc_level].geom.pkt_overhead
    949                     + pkt[enc_level].h.bytes_appended;
    950             }
    951 
    952         if (pad_el != QUIC_ENC_LEVEL_NUM && total_dgram_size < min_dpl) {
    953             size_t deficit = min_dpl - total_dgram_size;
    954 
    955             if (!txp_pkt_append_padding(&pkt[pad_el], txp, deficit))
    956                 goto out;
    957 
    958             total_dgram_size += deficit;
    959 
    960             /*
    961              * Padding frames make a packet ineligible for being a non-inflight
    962              * packet.
    963              */
    964             pkt[pad_el].tpkt->ackm_pkt.is_inflight = 1;
    965         }
    966 
    967         /*
    968          * If we have failed to make a datagram of adequate size, for example
    969          * because we have a padding requirement but are using the ACK_ONLY
    970          * archetype (because we are CC limited), which precludes us from
    971          * sending padding, give up on generating the datagram - there is
    972          * nothing we can do.
    973          */
    974         if (total_dgram_size < min_dpl) {
    975             res = 1;
    976             goto out;
    977         }
    978     }
    979 
    980     /* 4. Commit */
    981     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
    982         enc_level < QUIC_ENC_LEVEL_NUM;
    983         ++enc_level) {
    984 
    985         if (!pkt[enc_level].h_valid)
    986             /* Did not attempt to generate a packet for this EL. */
    987             continue;
    988 
    989         if (pkt[enc_level].h.bytes_appended == 0)
    990             /* Nothing was generated for this EL, so skip. */
    991             continue;
    992 
    993         if (!ossl_quic_tx_packetiser_check_unvalidated_credit(txp,
    994                 pkt[enc_level].h.bytes_appended)) {
    995             res = TXP_ERR_SPACE;
    996             goto out;
    997         }
    998         ossl_quic_tx_packetiser_consume_unvalidated_credit(txp, pkt[enc_level].h.bytes_appended);
    999 
   1000         rc = txp_pkt_commit(txp, &pkt[enc_level], archetype,
   1001             &txpim_pkt_reffed);
   1002         if (rc) {
   1003             status->sent_ack_eliciting
   1004                 = status->sent_ack_eliciting
   1005                 || pkt[enc_level].tpkt->ackm_pkt.is_ack_eliciting;
   1006 
   1007             if (enc_level == QUIC_ENC_LEVEL_HANDSHAKE)
   1008                 status->sent_handshake
   1009                     = (pkt[enc_level].h_valid
   1010                         && pkt[enc_level].h.bytes_appended > 0);
   1011         }
   1012 
   1013         if (txpim_pkt_reffed)
   1014             pkt[enc_level].tpkt = NULL; /* don't free */
   1015 
   1016         if (!rc)
   1017             goto out;
   1018 
   1019         ++pkts_done;
   1020     }
   1021 
   1022     /* Flush & Cleanup */
   1023     res = 1;
   1024 out:
   1025     ossl_qtx_finish_dgram(txp->args.qtx);
   1026 
   1027     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
   1028         enc_level < QUIC_ENC_LEVEL_NUM;
   1029         ++enc_level)
   1030         txp_pkt_cleanup(&pkt[enc_level], txp);
   1031 
   1032     status->sent_pkt = pkts_done;
   1033 
   1034     return res;
   1035 }
   1036 
   1037 static const struct archetype_data archetypes[QUIC_ENC_LEVEL_NUM][TX_PACKETISER_ARCHETYPE_NUM] = {
   1038     /* EL 0(INITIAL) */
   1039     {
   1040         /* EL 0(INITIAL) - Archetype 0(NORMAL) */
   1041         {
   1042             /*allow_ack                       =*/1,
   1043             /*allow_ping                      =*/1,
   1044             /*allow_crypto                    =*/1,
   1045             /*allow_handshake_done            =*/0,
   1046             /*allow_path_challenge            =*/0,
   1047             /*allow_path_response             =*/0,
   1048             /*allow_new_conn_id               =*/0,
   1049             /*allow_retire_conn_id            =*/0,
   1050             /*allow_stream_rel                =*/0,
   1051             /*allow_conn_fc                   =*/0,
   1052             /*allow_conn_close                =*/1,
   1053             /*allow_cfq_other                 =*/0,
   1054             /*allow_new_token                 =*/0,
   1055             /*allow_force_ack_eliciting       =*/1,
   1056             /*allow_padding                   =*/1,
   1057             /*require_ack_eliciting           =*/0,
   1058             /*bypass_cc                       =*/0,
   1059         },
   1060         /* EL 0(INITIAL) - Archetype 1(PROBE) */
   1061         {
   1062             /*allow_ack                       =*/1,
   1063             /*allow_ping                      =*/1,
   1064             /*allow_crypto                    =*/1,
   1065             /*allow_handshake_done            =*/0,
   1066             /*allow_path_challenge            =*/0,
   1067             /*allow_path_response             =*/0,
   1068             /*allow_new_conn_id               =*/0,
   1069             /*allow_retire_conn_id            =*/0,
   1070             /*allow_stream_rel                =*/0,
   1071             /*allow_conn_fc                   =*/0,
   1072             /*allow_conn_close                =*/1,
   1073             /*allow_cfq_other                 =*/0,
   1074             /*allow_new_token                 =*/0,
   1075             /*allow_force_ack_eliciting       =*/1,
   1076             /*allow_padding                   =*/1,
   1077             /*require_ack_eliciting           =*/1,
   1078             /*bypass_cc                       =*/1,
   1079         },
   1080         /* EL 0(INITIAL) - Archetype 2(ACK_ONLY) */
   1081         {
   1082             /*allow_ack                       =*/1,
   1083             /*allow_ping                      =*/0,
   1084             /*allow_crypto                    =*/0,
   1085             /*allow_handshake_done            =*/0,
   1086             /*allow_path_challenge            =*/0,
   1087             /*allow_path_response             =*/0,
   1088             /*allow_new_conn_id               =*/0,
   1089             /*allow_retire_conn_id            =*/0,
   1090             /*allow_stream_rel                =*/0,
   1091             /*allow_conn_fc                   =*/0,
   1092             /*allow_conn_close                =*/0,
   1093             /*allow_cfq_other                 =*/0,
   1094             /*allow_new_token                 =*/0,
   1095             /*allow_force_ack_eliciting       =*/1,
   1096             /*allow_padding                   =*/0,
   1097             /*require_ack_eliciting           =*/0,
   1098             /*bypass_cc                       =*/1,
   1099         },
   1100     },
   1101     /* EL 1(0RTT) */
   1102     {
   1103         /* EL 1(0RTT) - Archetype 0(NORMAL) */
   1104         {
   1105             /*allow_ack                       =*/0,
   1106             /*allow_ping                      =*/1,
   1107             /*allow_crypto                    =*/0,
   1108             /*allow_handshake_done            =*/0,
   1109             /*allow_path_challenge            =*/0,
   1110             /*allow_path_response             =*/0,
   1111             /*allow_new_conn_id               =*/1,
   1112             /*allow_retire_conn_id            =*/1,
   1113             /*allow_stream_rel                =*/1,
   1114             /*allow_conn_fc                   =*/1,
   1115             /*allow_conn_close                =*/1,
   1116             /*allow_cfq_other                 =*/0,
   1117             /*allow_new_token                 =*/0,
   1118             /*allow_force_ack_eliciting       =*/0,
   1119             /*allow_padding                   =*/1,
   1120             /*require_ack_eliciting           =*/0,
   1121             /*bypass_cc                       =*/0,
   1122         },
   1123         /* EL 1(0RTT) - Archetype 1(PROBE) */
   1124         {
   1125             /*allow_ack                       =*/0,
   1126             /*allow_ping                      =*/1,
   1127             /*allow_crypto                    =*/0,
   1128             /*allow_handshake_done            =*/0,
   1129             /*allow_path_challenge            =*/0,
   1130             /*allow_path_response             =*/0,
   1131             /*allow_new_conn_id               =*/1,
   1132             /*allow_retire_conn_id            =*/1,
   1133             /*allow_stream_rel                =*/1,
   1134             /*allow_conn_fc                   =*/1,
   1135             /*allow_conn_close                =*/1,
   1136             /*allow_cfq_other                 =*/0,
   1137             /*allow_new_token                 =*/0,
   1138             /*allow_force_ack_eliciting       =*/0,
   1139             /*allow_padding                   =*/1,
   1140             /*require_ack_eliciting           =*/1,
   1141             /*bypass_cc                       =*/1,
   1142         },
   1143         /* EL 1(0RTT) - Archetype 2(ACK_ONLY) */
   1144         {
   1145             /*allow_ack                       =*/0,
   1146             /*allow_ping                      =*/0,
   1147             /*allow_crypto                    =*/0,
   1148             /*allow_handshake_done            =*/0,
   1149             /*allow_path_challenge            =*/0,
   1150             /*allow_path_response             =*/0,
   1151             /*allow_new_conn_id               =*/0,
   1152             /*allow_retire_conn_id            =*/0,
   1153             /*allow_stream_rel                =*/0,
   1154             /*allow_conn_fc                   =*/0,
   1155             /*allow_conn_close                =*/0,
   1156             /*allow_cfq_other                 =*/0,
   1157             /*allow_new_token                 =*/0,
   1158             /*allow_force_ack_eliciting       =*/0,
   1159             /*allow_padding                   =*/0,
   1160             /*require_ack_eliciting           =*/0,
   1161             /*bypass_cc                       =*/1,
   1162         },
   1163     },
   1164     /* EL (HANDSHAKE) */
   1165     {
   1166         /* EL 2(HANDSHAKE) - Archetype 0(NORMAL) */
   1167         {
   1168             /*allow_ack                       =*/1,
   1169             /*allow_ping                      =*/1,
   1170             /*allow_crypto                    =*/1,
   1171             /*allow_handshake_done            =*/0,
   1172             /*allow_path_challenge            =*/0,
   1173             /*allow_path_response             =*/0,
   1174             /*allow_new_conn_id               =*/0,
   1175             /*allow_retire_conn_id            =*/0,
   1176             /*allow_stream_rel                =*/0,
   1177             /*allow_conn_fc                   =*/0,
   1178             /*allow_conn_close                =*/1,
   1179             /*allow_cfq_other                 =*/0,
   1180             /*allow_new_token                 =*/0,
   1181             /*allow_force_ack_eliciting       =*/1,
   1182             /*allow_padding                   =*/1,
   1183             /*require_ack_eliciting           =*/0,
   1184             /*bypass_cc                       =*/0,
   1185         },
   1186         /* EL 2(HANDSHAKE) - Archetype 1(PROBE) */
   1187         {
   1188             /*allow_ack                       =*/1,
   1189             /*allow_ping                      =*/1,
   1190             /*allow_crypto                    =*/1,
   1191             /*allow_handshake_done            =*/0,
   1192             /*allow_path_challenge            =*/0,
   1193             /*allow_path_response             =*/0,
   1194             /*allow_new_conn_id               =*/0,
   1195             /*allow_retire_conn_id            =*/0,
   1196             /*allow_stream_rel                =*/0,
   1197             /*allow_conn_fc                   =*/0,
   1198             /*allow_conn_close                =*/1,
   1199             /*allow_cfq_other                 =*/0,
   1200             /*allow_new_token                 =*/0,
   1201             /*allow_force_ack_eliciting       =*/1,
   1202             /*allow_padding                   =*/1,
   1203             /*require_ack_eliciting           =*/1,
   1204             /*bypass_cc                       =*/1,
   1205         },
   1206         /* EL 2(HANDSHAKE) - Archetype 2(ACK_ONLY) */
   1207         {
   1208             /*allow_ack                       =*/1,
   1209             /*allow_ping                      =*/0,
   1210             /*allow_crypto                    =*/0,
   1211             /*allow_handshake_done            =*/0,
   1212             /*allow_path_challenge            =*/0,
   1213             /*allow_path_response             =*/0,
   1214             /*allow_new_conn_id               =*/0,
   1215             /*allow_retire_conn_id            =*/0,
   1216             /*allow_stream_rel                =*/0,
   1217             /*allow_conn_fc                   =*/0,
   1218             /*allow_conn_close                =*/0,
   1219             /*allow_cfq_other                 =*/0,
   1220             /*allow_new_token                 =*/0,
   1221             /*allow_force_ack_eliciting       =*/1,
   1222             /*allow_padding                   =*/0,
   1223             /*require_ack_eliciting           =*/0,
   1224             /*bypass_cc                       =*/1,
   1225         },
   1226     },
   1227     /* EL 3(1RTT) */
   1228     {
   1229         /* EL 3(1RTT) - Archetype 0(NORMAL) */
   1230         {
   1231             /*allow_ack                       =*/1,
   1232             /*allow_ping                      =*/1,
   1233             /*allow_crypto                    =*/1,
   1234             /*allow_handshake_done            =*/1,
   1235             /*allow_path_challenge            =*/0,
   1236             /*allow_path_response             =*/1,
   1237             /*allow_new_conn_id               =*/1,
   1238             /*allow_retire_conn_id            =*/1,
   1239             /*allow_stream_rel                =*/1,
   1240             /*allow_conn_fc                   =*/1,
   1241             /*allow_conn_close                =*/1,
   1242             /*allow_cfq_other                 =*/1,
   1243             /*allow_new_token                 =*/1,
   1244             /*allow_force_ack_eliciting       =*/1,
   1245             /*allow_padding                   =*/1,
   1246             /*require_ack_eliciting           =*/0,
   1247             /*bypass_cc                       =*/0,
   1248         },
   1249         /* EL 3(1RTT) - Archetype 1(PROBE) */
   1250         {
   1251             /*allow_ack                       =*/1,
   1252             /*allow_ping                      =*/1,
   1253             /*allow_crypto                    =*/1,
   1254             /*allow_handshake_done            =*/1,
   1255             /*allow_path_challenge            =*/0,
   1256             /*allow_path_response             =*/1,
   1257             /*allow_new_conn_id               =*/1,
   1258             /*allow_retire_conn_id            =*/1,
   1259             /*allow_stream_rel                =*/1,
   1260             /*allow_conn_fc                   =*/1,
   1261             /*allow_conn_close                =*/1,
   1262             /*allow_cfq_other                 =*/1,
   1263             /*allow_new_token                 =*/1,
   1264             /*allow_force_ack_eliciting       =*/1,
   1265             /*allow_padding                   =*/1,
   1266             /*require_ack_eliciting           =*/1,
   1267             /*bypass_cc                       =*/1,
   1268         },
   1269         /* EL 3(1RTT) - Archetype 2(ACK_ONLY) */
   1270         {
   1271             /*allow_ack                       =*/1,
   1272             /*allow_ping                      =*/0,
   1273             /*allow_crypto                    =*/0,
   1274             /*allow_handshake_done            =*/0,
   1275             /*allow_path_challenge            =*/0,
   1276             /*allow_path_response             =*/0,
   1277             /*allow_new_conn_id               =*/0,
   1278             /*allow_retire_conn_id            =*/0,
   1279             /*allow_stream_rel                =*/0,
   1280             /*allow_conn_fc                   =*/0,
   1281             /*allow_conn_close                =*/0,
   1282             /*allow_cfq_other                 =*/0,
   1283             /*allow_new_token                 =*/0,
   1284             /*allow_force_ack_eliciting       =*/1,
   1285             /*allow_padding                   =*/0,
   1286             /*require_ack_eliciting           =*/0,
   1287             /*bypass_cc                       =*/1,
   1288         } }
   1289 };
   1290 
   1291 static int txp_get_archetype_data(uint32_t enc_level,
   1292     uint32_t archetype,
   1293     struct archetype_data *a)
   1294 {
   1295     if (enc_level >= QUIC_ENC_LEVEL_NUM
   1296         || archetype >= TX_PACKETISER_ARCHETYPE_NUM)
   1297         return 0;
   1298 
   1299     /* No need to avoid copying this as it should not exceed one int in size. */
   1300     *a = archetypes[enc_level][archetype];
   1301     return 1;
   1302 }
   1303 
   1304 static int txp_determine_geometry(OSSL_QUIC_TX_PACKETISER *txp,
   1305     uint32_t archetype,
   1306     uint32_t enc_level,
   1307     size_t running_total,
   1308     QUIC_PKT_HDR *phdr,
   1309     struct txp_pkt_geom *geom)
   1310 {
   1311     size_t mdpl, cmpl, hdr_len;
   1312 
   1313     /* Get information about packet archetype. */
   1314     if (!txp_get_archetype_data(enc_level, archetype, &geom->adata))
   1315         return 0;
   1316 
   1317     /* Assemble packet header. */
   1318     phdr->type = ossl_quic_enc_level_to_pkt_type(enc_level);
   1319     phdr->spin_bit = 0;
   1320     phdr->pn_len = txp_determine_pn_len(txp);
   1321     phdr->partial = 0;
   1322     phdr->fixed = 1;
   1323     phdr->reserved = 0;
   1324     phdr->version = txp->args.protocol_version;
   1325     phdr->dst_conn_id = txp->args.cur_dcid;
   1326     phdr->src_conn_id = txp->args.cur_scid;
   1327 
   1328     /*
   1329      * We need to know the length of the payload to get an accurate header
   1330      * length for non-1RTT packets, because the Length field found in
   1331      * Initial/Handshake/0-RTT packets uses a variable-length encoding. However,
   1332      * we don't have a good idea of the length of our payload, because the
   1333      * length of the payload depends on the room in the datagram after fitting
   1334      * the header, which depends on the size of the header.
   1335      *
   1336      * In general, it does not matter if a packet is slightly shorter (because
   1337      * e.g. we predicted use of a 2-byte length field, but ended up only needing
   1338      * a 1-byte length field). However this does matter for Initial packets
   1339      * which must be at least 1200 bytes, which is also the assumed default MTU;
   1340      * therefore in many cases Initial packets will be padded to 1200 bytes,
   1341      * which means if we overestimated the header size, we will be short by a
   1342      * few bytes and the server will ignore the packet for being too short. In
   1343      * this case, however, such packets always *will* be padded to meet 1200
   1344      * bytes, which requires a 2-byte length field, so we don't actually need to
   1345      * worry about this. Thus we estimate the header length assuming a 2-byte
   1346      * length field here, which should in practice work well in all cases.
   1347      */
   1348     phdr->len = OSSL_QUIC_VLINT_2B_MAX - phdr->pn_len;
   1349 
   1350     if (enc_level == QUIC_ENC_LEVEL_INITIAL) {
   1351         phdr->token = txp->initial_token;
   1352         phdr->token_len = txp->initial_token_len;
   1353     } else {
   1354         phdr->token = NULL;
   1355         phdr->token_len = 0;
   1356     }
   1357 
   1358     hdr_len = ossl_quic_wire_get_encoded_pkt_hdr_len(phdr->dst_conn_id.id_len,
   1359         phdr);
   1360     if (hdr_len == 0)
   1361         return 0;
   1362 
   1363     /* MDPL: Maximum datagram payload length. */
   1364     mdpl = txp_get_mdpl(txp);
   1365 
   1366     /*
   1367      * CMPL: Maximum encoded packet size we can put into this datagram given any
   1368      * previous packets coalesced into it.
   1369      */
   1370     if (running_total > mdpl)
   1371         /* Should not be possible, but if it happens: */
   1372         cmpl = 0;
   1373     else
   1374         cmpl = mdpl - running_total;
   1375 
   1376     /* CMPPL: Maximum amount we can put into the current packet payload */
   1377     if (!txp_determine_ppl_from_pl(txp, cmpl, enc_level, hdr_len, &geom->cmppl))
   1378         return 0;
   1379 
   1380     geom->cmpl = cmpl;
   1381     geom->pkt_overhead = cmpl - geom->cmppl;
   1382     geom->archetype = archetype;
   1383     return 1;
   1384 }
   1385 
   1386 static uint32_t txp_determine_archetype(OSSL_QUIC_TX_PACKETISER *txp,
   1387     uint64_t cc_limit)
   1388 {
   1389     OSSL_ACKM_PROBE_INFO *probe_info
   1390         = ossl_ackm_get0_probe_request(txp->args.ackm);
   1391     uint32_t pn_space;
   1392 
   1393     /*
   1394      * If ACKM has requested probe generation (e.g. due to PTO), we generate a
   1395      * Probe-archetype packet. Actually, we determine archetype on a
   1396      * per-datagram basis, so if any EL wants a probe, do a pass in which
   1397      * we try and generate a probe (if needed) for all ELs.
   1398      */
   1399     if (probe_info->anti_deadlock_initial > 0
   1400         || probe_info->anti_deadlock_handshake > 0)
   1401         return TX_PACKETISER_ARCHETYPE_PROBE;
   1402 
   1403     for (pn_space = QUIC_PN_SPACE_INITIAL;
   1404         pn_space < QUIC_PN_SPACE_NUM;
   1405         ++pn_space)
   1406         if (probe_info->pto[pn_space] > 0)
   1407             return TX_PACKETISER_ARCHETYPE_PROBE;
   1408 
   1409     /*
   1410      * If we are out of CC budget, we cannot send a normal packet,
   1411      * but we can do an ACK-only packet (potentially, if we
   1412      * want to send an ACK).
   1413      */
   1414     if (cc_limit == 0)
   1415         return TX_PACKETISER_ARCHETYPE_ACK_ONLY;
   1416 
   1417     /* All other packets. */
   1418     return TX_PACKETISER_ARCHETYPE_NORMAL;
   1419 }
   1420 
   1421 static int txp_should_try_staging(OSSL_QUIC_TX_PACKETISER *txp,
   1422     uint32_t enc_level,
   1423     uint32_t archetype,
   1424     uint64_t cc_limit,
   1425     uint32_t *conn_close_enc_level)
   1426 {
   1427     struct archetype_data a;
   1428     uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   1429     QUIC_CFQ_ITEM *cfq_item;
   1430 
   1431     if (!ossl_qtx_is_enc_level_provisioned(txp->args.qtx, enc_level))
   1432         return 0;
   1433 
   1434     if (!txp_get_archetype_data(enc_level, archetype, &a))
   1435         return 0;
   1436 
   1437     if (!a.bypass_cc && cc_limit == 0)
   1438         /* CC not allowing us to send. */
   1439         return 0;
   1440 
   1441     /*
   1442      * We can produce CONNECTION_CLOSE frames on any EL in principle, which
   1443      * means we need to choose which EL we would prefer to use. After a
   1444      * connection is fully established we have only one provisioned EL and this
   1445      * is a non-issue. Where multiple ELs are provisioned, it is possible the
   1446      * peer does not have the keys for the EL yet, which suggests in general it
   1447      * is preferable to use the lowest EL which is still provisioned.
   1448      *
   1449      * However (RFC 9000 s. 10.2.3 & 12.5) we are also required to not send
   1450      * application CONNECTION_CLOSE frames in non-1-RTT ELs, so as to not
   1451      * potentially leak application data on a connection which has yet to be
   1452      * authenticated. Thus when we have an application CONNECTION_CLOSE frame
   1453      * queued and need to send it on a non-1-RTT EL, we have to convert it
   1454      * into a transport CONNECTION_CLOSE frame which contains no application
   1455      * data. Since this loses information, it suggests we should use the 1-RTT
   1456      * EL to avoid this if possible, even if a lower EL is also available.
   1457      *
   1458      * At the same time, just because we have the 1-RTT EL provisioned locally
   1459      * does not necessarily mean the peer does, for example if a handshake
   1460      * CRYPTO frame has been lost. It is fairly important that CONNECTION_CLOSE
   1461      * is signalled in a way we know our peer can decrypt, as we stop processing
   1462      * connection retransmission logic for real after connection close and
   1463      * simply 'blindly' retransmit the same CONNECTION_CLOSE frame.
   1464      *
   1465      * This is not a major concern for clients, since if a client has a 1-RTT EL
   1466      * provisioned the server is guaranteed to also have a 1-RTT EL provisioned.
   1467      *
   1468      * TODO(QUIC FUTURE): Revisit this when when have reached a decision on how
   1469      * best to implement this
   1470      */
   1471     if (*conn_close_enc_level > enc_level
   1472         && *conn_close_enc_level != QUIC_ENC_LEVEL_1RTT)
   1473         *conn_close_enc_level = enc_level;
   1474 
   1475     /* Do we need to send a PTO probe? */
   1476     if (a.allow_force_ack_eliciting) {
   1477         OSSL_ACKM_PROBE_INFO *probe_info
   1478             = ossl_ackm_get0_probe_request(txp->args.ackm);
   1479 
   1480         if ((enc_level == QUIC_ENC_LEVEL_INITIAL
   1481                 && probe_info->anti_deadlock_initial > 0)
   1482             || (enc_level == QUIC_ENC_LEVEL_HANDSHAKE
   1483                 && probe_info->anti_deadlock_handshake > 0)
   1484             || probe_info->pto[pn_space] > 0)
   1485             return 1;
   1486     }
   1487 
   1488     /* Does the crypto stream for this EL want to produce anything? */
   1489     if (a.allow_crypto && sstream_is_pending(txp->args.crypto[pn_space]))
   1490         return 1;
   1491 
   1492     /* Does the ACKM for this PN space want to produce anything? */
   1493     if (a.allow_ack && (ossl_ackm_is_ack_desired(txp->args.ackm, pn_space) || (txp->want_ack & (1UL << pn_space)) != 0))
   1494         return 1;
   1495 
   1496     /* Do we need to force emission of an ACK-eliciting packet? */
   1497     if (a.allow_force_ack_eliciting
   1498         && (txp->force_ack_eliciting & (1UL << pn_space)) != 0)
   1499         return 1;
   1500 
   1501     /* Does the connection-level RXFC want to produce a frame? */
   1502     if (a.allow_conn_fc && (txp->want_max_data || ossl_quic_rxfc_has_cwm_changed(txp->args.conn_rxfc, 0)))
   1503         return 1;
   1504 
   1505     /* Do we want to produce a MAX_STREAMS frame? */
   1506     if (a.allow_conn_fc
   1507         && (txp->want_max_streams_bidi
   1508             || ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_bidi_rxfc,
   1509                 0)
   1510             || txp->want_max_streams_uni
   1511             || ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_uni_rxfc,
   1512                 0)))
   1513         return 1;
   1514 
   1515     /* Do we want to produce a HANDSHAKE_DONE frame? */
   1516     if (a.allow_handshake_done && txp->want_handshake_done)
   1517         return 1;
   1518 
   1519     /* Do we want to produce a CONNECTION_CLOSE frame? */
   1520     if (a.allow_conn_close && txp->want_conn_close && *conn_close_enc_level == enc_level)
   1521         /*
   1522          * This is a bit of a special case since CONNECTION_CLOSE can appear in
   1523          * most packet types, and when we decide we want to send it this status
   1524          * isn't tied to a specific EL. So if we want to send it, we send it
   1525          * only on the lowest non-dropped EL.
   1526          */
   1527         return 1;
   1528 
   1529     /* Does the CFQ have any frames queued for this PN space? */
   1530     if (enc_level != QUIC_ENC_LEVEL_0RTT)
   1531         for (cfq_item = ossl_quic_cfq_get_priority_head(txp->args.cfq, pn_space);
   1532             cfq_item != NULL;
   1533             cfq_item = ossl_quic_cfq_item_get_priority_next(cfq_item, pn_space)) {
   1534             uint64_t frame_type = ossl_quic_cfq_item_get_frame_type(cfq_item);
   1535 
   1536             switch (frame_type) {
   1537             case OSSL_QUIC_FRAME_TYPE_NEW_CONN_ID:
   1538                 if (a.allow_new_conn_id)
   1539                     return 1;
   1540                 break;
   1541             case OSSL_QUIC_FRAME_TYPE_RETIRE_CONN_ID:
   1542                 if (a.allow_retire_conn_id)
   1543                     return 1;
   1544                 break;
   1545             case OSSL_QUIC_FRAME_TYPE_NEW_TOKEN:
   1546                 if (a.allow_new_token)
   1547                     return 1;
   1548                 break;
   1549             case OSSL_QUIC_FRAME_TYPE_PATH_RESPONSE:
   1550                 if (a.allow_path_response)
   1551                     return 1;
   1552                 break;
   1553             default:
   1554                 if (a.allow_cfq_other)
   1555                     return 1;
   1556                 break;
   1557             }
   1558         }
   1559 
   1560     if (a.allow_stream_rel && txp->handshake_complete) {
   1561         QUIC_STREAM_ITER it;
   1562 
   1563         /* If there are any active streams, 0/1-RTT wants to produce a packet.
   1564          * Whether a stream is on the active list is required to be precise
   1565          * (i.e., a stream is never on the active list if we cannot produce a
   1566          * frame for it), and all stream-related frames are governed by
   1567          * a.allow_stream_rel (i.e., if we can send one type of stream-related
   1568          * frame, we can send any of them), so we don't need to inspect
   1569          * individual streams on the active list, just confirm that the active
   1570          * list is non-empty.
   1571          */
   1572         ossl_quic_stream_iter_init(&it, txp->args.qsm, 0);
   1573         if (it.stream != NULL)
   1574             return 1;
   1575     }
   1576 
   1577     return 0;
   1578 }
   1579 
   1580 static int sstream_is_pending(QUIC_SSTREAM *sstream)
   1581 {
   1582     OSSL_QUIC_FRAME_STREAM hdr;
   1583     OSSL_QTX_IOVEC iov[2];
   1584     size_t num_iov = OSSL_NELEM(iov);
   1585 
   1586     return ossl_quic_sstream_get_stream_frame(sstream, 0, &hdr, iov, &num_iov);
   1587 }
   1588 
   1589 /* Determine how many bytes we should use for the encoded PN. */
   1590 static size_t txp_determine_pn_len(OSSL_QUIC_TX_PACKETISER *txp)
   1591 {
   1592     return 4; /* TODO(QUIC FUTURE) */
   1593 }
   1594 
   1595 /* Determine plaintext packet payload length from payload length. */
   1596 static int txp_determine_ppl_from_pl(OSSL_QUIC_TX_PACKETISER *txp,
   1597     size_t pl,
   1598     uint32_t enc_level,
   1599     size_t hdr_len,
   1600     size_t *r)
   1601 {
   1602     if (pl < hdr_len)
   1603         return 0;
   1604 
   1605     pl -= hdr_len;
   1606 
   1607     if (!ossl_qtx_calculate_plaintext_payload_len(txp->args.qtx, enc_level,
   1608             pl, &pl))
   1609         return 0;
   1610 
   1611     *r = pl;
   1612     return 1;
   1613 }
   1614 
   1615 static size_t txp_get_mdpl(OSSL_QUIC_TX_PACKETISER *txp)
   1616 {
   1617     return ossl_qtx_get_mdpl(txp->args.qtx);
   1618 }
   1619 
   1620 static QUIC_SSTREAM *get_sstream_by_id(uint64_t stream_id, uint32_t pn_space,
   1621     void *arg)
   1622 {
   1623     OSSL_QUIC_TX_PACKETISER *txp = arg;
   1624     QUIC_STREAM *s;
   1625 
   1626     if (stream_id == UINT64_MAX)
   1627         return txp->args.crypto[pn_space];
   1628 
   1629     s = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1630     if (s == NULL)
   1631         return NULL;
   1632 
   1633     return s->sstream;
   1634 }
   1635 
   1636 static void on_regen_notify(uint64_t frame_type, uint64_t stream_id,
   1637     QUIC_TXPIM_PKT *pkt, void *arg)
   1638 {
   1639     OSSL_QUIC_TX_PACKETISER *txp = arg;
   1640 
   1641     switch (frame_type) {
   1642     case OSSL_QUIC_FRAME_TYPE_HANDSHAKE_DONE:
   1643         txp->want_handshake_done = 1;
   1644         break;
   1645     case OSSL_QUIC_FRAME_TYPE_MAX_DATA:
   1646         txp->want_max_data = 1;
   1647         break;
   1648     case OSSL_QUIC_FRAME_TYPE_MAX_STREAMS_BIDI:
   1649         txp->want_max_streams_bidi = 1;
   1650         break;
   1651     case OSSL_QUIC_FRAME_TYPE_MAX_STREAMS_UNI:
   1652         txp->want_max_streams_uni = 1;
   1653         break;
   1654     case OSSL_QUIC_FRAME_TYPE_ACK_WITH_ECN:
   1655         txp->want_ack |= (1UL << pkt->ackm_pkt.pkt_space);
   1656         break;
   1657     case OSSL_QUIC_FRAME_TYPE_MAX_STREAM_DATA: {
   1658         QUIC_STREAM *s
   1659             = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1660 
   1661         if (s == NULL)
   1662             return;
   1663 
   1664         s->want_max_stream_data = 1;
   1665         ossl_quic_stream_map_update_state(txp->args.qsm, s);
   1666     } break;
   1667     case OSSL_QUIC_FRAME_TYPE_STOP_SENDING: {
   1668         QUIC_STREAM *s
   1669             = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1670 
   1671         if (s == NULL)
   1672             return;
   1673 
   1674         ossl_quic_stream_map_schedule_stop_sending(txp->args.qsm, s);
   1675     } break;
   1676     case OSSL_QUIC_FRAME_TYPE_RESET_STREAM: {
   1677         QUIC_STREAM *s
   1678             = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1679 
   1680         if (s == NULL)
   1681             return;
   1682 
   1683         s->want_reset_stream = 1;
   1684         ossl_quic_stream_map_update_state(txp->args.qsm, s);
   1685     } break;
   1686     default:
   1687         assert(0);
   1688         break;
   1689     }
   1690 }
   1691 
   1692 static int txp_need_ping(OSSL_QUIC_TX_PACKETISER *txp,
   1693     uint32_t pn_space,
   1694     const struct archetype_data *adata)
   1695 {
   1696     return adata->allow_ping
   1697         && (adata->require_ack_eliciting
   1698             || (txp->force_ack_eliciting & (1UL << pn_space)) != 0);
   1699 }
   1700 
   1701 static int txp_pkt_init(struct txp_pkt *pkt, OSSL_QUIC_TX_PACKETISER *txp,
   1702     uint32_t enc_level, uint32_t archetype,
   1703     size_t running_total)
   1704 {
   1705     uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   1706 
   1707     if (!txp_determine_geometry(txp, archetype, enc_level,
   1708             running_total, &pkt->phdr, &pkt->geom))
   1709         return 0;
   1710 
   1711     /*
   1712      * Initialise TX helper. If we must be ACK eliciting, reserve 1 byte for
   1713      * PING.
   1714      */
   1715     if (!tx_helper_init(&pkt->h, txp, enc_level,
   1716             pkt->geom.cmppl,
   1717             txp_need_ping(txp, pn_space, &pkt->geom.adata) ? 1 : 0))
   1718         return 0;
   1719 
   1720     pkt->h_valid = 1;
   1721     pkt->tpkt = NULL;
   1722     pkt->stream_head = NULL;
   1723     pkt->force_pad = 0;
   1724     return 1;
   1725 }
   1726 
   1727 static void txp_pkt_cleanup(struct txp_pkt *pkt, OSSL_QUIC_TX_PACKETISER *txp)
   1728 {
   1729     if (!pkt->h_valid)
   1730         return;
   1731 
   1732     tx_helper_cleanup(&pkt->h);
   1733     pkt->h_valid = 0;
   1734 
   1735     if (pkt->tpkt != NULL) {
   1736         ossl_quic_txpim_pkt_release(txp->args.txpim, pkt->tpkt);
   1737         pkt->tpkt = NULL;
   1738     }
   1739 }
   1740 
   1741 static int txp_pkt_postgen_update_pkt_overhead(struct txp_pkt *pkt,
   1742     OSSL_QUIC_TX_PACKETISER *txp)
   1743 {
   1744     /*
   1745      * After we have staged and generated our packets, but before we commit
   1746      * them, it is possible for the estimated packet overhead (packet header +
   1747      * AEAD tag size) to shrink slightly because we generated a short packet
   1748      * whose which can be represented in fewer bytes as a variable-length
   1749      * integer than we were (pessimistically) budgeting for. We need to account
   1750      * for this to ensure that we get our padding calculation exactly right.
   1751      *
   1752      * Update pkt_overhead to be accurate now that we know how much data is
   1753      * going in a packet.
   1754      */
   1755     size_t hdr_len, ciphertext_len;
   1756 
   1757     if (pkt->h.enc_level == QUIC_ENC_LEVEL_INITIAL)
   1758         /*
   1759          * Don't update overheads for the INITIAL EL - we have not finished
   1760          * appending padding to it and would potentially miscalculate the
   1761          * correct padding if we now update the pkt_overhead field to switch to
   1762          * e.g. a 1-byte length field in the packet header. Since we are padding
   1763          * to QUIC_MIN_INITIAL_DGRAM_LEN which requires a 2-byte length field,
   1764          * this is guaranteed to be moot anyway. See comment in
   1765          * txp_determine_geometry for more information.
   1766          */
   1767         return 1;
   1768 
   1769     if (!ossl_qtx_calculate_ciphertext_payload_len(txp->args.qtx, pkt->h.enc_level,
   1770             pkt->h.bytes_appended,
   1771             &ciphertext_len))
   1772         return 0;
   1773 
   1774     pkt->phdr.len = ciphertext_len;
   1775 
   1776     hdr_len = ossl_quic_wire_get_encoded_pkt_hdr_len(pkt->phdr.dst_conn_id.id_len,
   1777         &pkt->phdr);
   1778 
   1779     pkt->geom.pkt_overhead = hdr_len + ciphertext_len - pkt->h.bytes_appended;
   1780     return 1;
   1781 }
   1782 
   1783 static void on_confirm_notify(uint64_t frame_type, uint64_t stream_id,
   1784     QUIC_TXPIM_PKT *pkt, void *arg)
   1785 {
   1786     OSSL_QUIC_TX_PACKETISER *txp = arg;
   1787 
   1788     switch (frame_type) {
   1789     case OSSL_QUIC_FRAME_TYPE_STOP_SENDING: {
   1790         QUIC_STREAM *s
   1791             = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1792 
   1793         if (s == NULL)
   1794             return;
   1795 
   1796         s->acked_stop_sending = 1;
   1797         ossl_quic_stream_map_update_state(txp->args.qsm, s);
   1798     } break;
   1799     case OSSL_QUIC_FRAME_TYPE_RESET_STREAM: {
   1800         QUIC_STREAM *s
   1801             = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1802 
   1803         if (s == NULL)
   1804             return;
   1805 
   1806         /*
   1807          * We must already be in RESET_SENT or RESET_RECVD if we are
   1808          * here, so we don't need to check state here.
   1809          */
   1810         ossl_quic_stream_map_notify_reset_stream_acked(txp->args.qsm, s);
   1811         ossl_quic_stream_map_update_state(txp->args.qsm, s);
   1812     } break;
   1813     default:
   1814         assert(0);
   1815         break;
   1816     }
   1817 }
   1818 
   1819 static int txp_pkt_append_padding(struct txp_pkt *pkt,
   1820     OSSL_QUIC_TX_PACKETISER *txp, size_t num_bytes)
   1821 {
   1822     WPACKET *wpkt;
   1823 
   1824     if (num_bytes == 0)
   1825         return 1;
   1826 
   1827     if (!ossl_assert(pkt->h_valid))
   1828         return 0;
   1829 
   1830     if (!ossl_assert(pkt->tpkt != NULL))
   1831         return 0;
   1832 
   1833     wpkt = tx_helper_begin(&pkt->h);
   1834     if (wpkt == NULL)
   1835         return 0;
   1836 
   1837     if (!ossl_quic_wire_encode_padding(wpkt, num_bytes)) {
   1838         tx_helper_rollback(&pkt->h);
   1839         return 0;
   1840     }
   1841 
   1842     if (!tx_helper_commit(&pkt->h))
   1843         return 0;
   1844 
   1845     pkt->tpkt->ackm_pkt.num_bytes += num_bytes;
   1846     /* Cannot be non-inflight if we have a PADDING frame */
   1847     pkt->tpkt->ackm_pkt.is_inflight = 1;
   1848     return 1;
   1849 }
   1850 
   1851 static void on_sstream_updated(uint64_t stream_id, void *arg)
   1852 {
   1853     OSSL_QUIC_TX_PACKETISER *txp = arg;
   1854     QUIC_STREAM *s;
   1855 
   1856     s = ossl_quic_stream_map_get_by_id(txp->args.qsm, stream_id);
   1857     if (s == NULL)
   1858         return;
   1859 
   1860     ossl_quic_stream_map_update_state(txp->args.qsm, s);
   1861 }
   1862 
   1863 /*
   1864  * Returns 1 if we can send that many bytes in closing state, 0 otherwise.
   1865  * Also maintains the bytes sent state if it returns a success.
   1866  */
   1867 static int try_commit_conn_close(OSSL_QUIC_TX_PACKETISER *txp, size_t n)
   1868 {
   1869     int res;
   1870 
   1871     /* We can always send the first connection close frame */
   1872     if (txp->closing_bytes_recv == 0)
   1873         return 1;
   1874 
   1875     /*
   1876      * RFC 9000 s. 10.2.1 Closing Connection State:
   1877      *      To avoid being used for an amplification attack, such
   1878      *      endpoints MUST limit the cumulative size of packets it sends
   1879      *      to three times the cumulative size of the packets that are
   1880      *      received and attributed to the connection.
   1881      * and:
   1882      *      An endpoint in the closing state MUST either discard packets
   1883      *      received from an unvalidated address or limit the cumulative
   1884      *      size of packets it sends to an unvalidated address to three
   1885      *      times the size of packets it receives from that address.
   1886      */
   1887     res = txp->closing_bytes_xmit + n <= txp->closing_bytes_recv * 3;
   1888 
   1889     /*
   1890      * Attribute the bytes to the connection, if we are allowed to send them
   1891      * and this isn't the first closing frame.
   1892      */
   1893     if (res && txp->closing_bytes_recv != 0)
   1894         txp->closing_bytes_xmit += n;
   1895     return res;
   1896 }
   1897 
   1898 void ossl_quic_tx_packetiser_record_received_closing_bytes(
   1899     OSSL_QUIC_TX_PACKETISER *txp, size_t n)
   1900 {
   1901     txp->closing_bytes_recv += n;
   1902 }
   1903 
   1904 static int txp_generate_pre_token(OSSL_QUIC_TX_PACKETISER *txp,
   1905     struct txp_pkt *pkt,
   1906     int chosen_for_conn_close,
   1907     int *can_be_non_inflight)
   1908 {
   1909     const uint32_t enc_level = pkt->h.enc_level;
   1910     const uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   1911     const struct archetype_data *a = &pkt->geom.adata;
   1912     QUIC_TXPIM_PKT *tpkt = pkt->tpkt;
   1913     struct tx_helper *h = &pkt->h;
   1914     const OSSL_QUIC_FRAME_ACK *ack;
   1915     OSSL_QUIC_FRAME_ACK ack2;
   1916 
   1917     tpkt->ackm_pkt.largest_acked = QUIC_PN_INVALID;
   1918 
   1919     /* ACK Frames (Regenerate) */
   1920     if (a->allow_ack
   1921         && tx_helper_get_space_left(h) >= MIN_FRAME_SIZE_ACK
   1922         && (((txp->want_ack & (1UL << pn_space)) != 0)
   1923             || ossl_ackm_is_ack_desired(txp->args.ackm, pn_space))
   1924         && (ack = ossl_ackm_get_ack_frame(txp->args.ackm, pn_space)) != NULL) {
   1925         WPACKET *wpkt = tx_helper_begin(h);
   1926 
   1927         if (wpkt == NULL)
   1928             return 0;
   1929 
   1930         /* We do not currently support ECN */
   1931         ack2 = *ack;
   1932         ack2.ecn_present = 0;
   1933 
   1934         if (ossl_quic_wire_encode_frame_ack(wpkt,
   1935                 txp->args.ack_delay_exponent,
   1936                 &ack2)) {
   1937             if (!tx_helper_commit(h))
   1938                 return 0;
   1939 
   1940             tpkt->had_ack_frame = 1;
   1941 
   1942             if (ack->num_ack_ranges > 0)
   1943                 tpkt->ackm_pkt.largest_acked = ack->ack_ranges[0].end;
   1944 
   1945             if (txp->ack_tx_cb != NULL)
   1946                 txp->ack_tx_cb(&ack2, pn_space, txp->ack_tx_cb_arg);
   1947         } else {
   1948             tx_helper_rollback(h);
   1949         }
   1950     }
   1951 
   1952     /* CONNECTION_CLOSE Frames (Regenerate) */
   1953     if (a->allow_conn_close && txp->want_conn_close && chosen_for_conn_close) {
   1954         WPACKET *wpkt = tx_helper_begin(h);
   1955         OSSL_QUIC_FRAME_CONN_CLOSE f, *pf = &txp->conn_close_frame;
   1956         size_t l;
   1957 
   1958         if (wpkt == NULL)
   1959             return 0;
   1960 
   1961         /*
   1962          * Application CONNECTION_CLOSE frames may only be sent in the
   1963          * Application PN space, as otherwise they may be sent before a
   1964          * connection is authenticated and leak application data. Therefore, if
   1965          * we need to send a CONNECTION_CLOSE frame in another PN space and were
   1966          * given an application CONNECTION_CLOSE frame, convert it into a
   1967          * transport CONNECTION_CLOSE frame, removing any sensitive application
   1968          * data.
   1969          *
   1970          * RFC 9000 s. 10.2.3: "A CONNECTION_CLOSE of type 0x1d MUST be replaced
   1971          * by a CONNECTION_CLOSE of type 0x1c when sending the frame in Initial
   1972          * or Handshake packets. Otherwise, information about the application
   1973          * state might be revealed. Endpoints MUST clear the value of the Reason
   1974          * Phrase field and SHOULD use the APPLICATION_ERROR code when
   1975          * converting to a CONNECTION_CLOSE of type 0x1c."
   1976          */
   1977         if (pn_space != QUIC_PN_SPACE_APP && pf->is_app) {
   1978             pf = &f;
   1979             pf->is_app = 0;
   1980             pf->frame_type = 0;
   1981             pf->error_code = OSSL_QUIC_ERR_APPLICATION_ERROR;
   1982             pf->reason = NULL;
   1983             pf->reason_len = 0;
   1984         }
   1985 
   1986         if (ossl_quic_wire_encode_frame_conn_close(wpkt, pf)
   1987             && WPACKET_get_total_written(wpkt, &l)
   1988             && try_commit_conn_close(txp, l)) {
   1989             if (!tx_helper_commit(h))
   1990                 return 0;
   1991 
   1992             tpkt->had_conn_close = 1;
   1993             *can_be_non_inflight = 0;
   1994         } else {
   1995             tx_helper_rollback(h);
   1996         }
   1997     }
   1998 
   1999     return 1;
   2000 }
   2001 
   2002 static int try_len(size_t space_left, size_t orig_len,
   2003     size_t base_hdr_len, size_t lenbytes,
   2004     uint64_t maxn, size_t *hdr_len, size_t *payload_len)
   2005 {
   2006     size_t n;
   2007     size_t maxn_ = maxn > SIZE_MAX ? SIZE_MAX : (size_t)maxn;
   2008 
   2009     *hdr_len = base_hdr_len + lenbytes;
   2010 
   2011     if (orig_len == 0 && space_left >= *hdr_len) {
   2012         *payload_len = 0;
   2013         return 1;
   2014     }
   2015 
   2016     n = orig_len;
   2017     if (n > maxn_)
   2018         n = maxn_;
   2019     if (n + *hdr_len > space_left)
   2020         n = (space_left >= *hdr_len) ? space_left - *hdr_len : 0;
   2021 
   2022     *payload_len = n;
   2023     return n > 0;
   2024 }
   2025 
   2026 static int determine_len(size_t space_left, size_t orig_len,
   2027     size_t base_hdr_len,
   2028     uint64_t *hlen, uint64_t *len)
   2029 {
   2030     int ok = 0;
   2031     size_t chosen_payload_len = 0;
   2032     size_t chosen_hdr_len = 0;
   2033     size_t payload_len[4], hdr_len[4];
   2034     int i, valid[4] = { 0 };
   2035 
   2036     valid[0] = try_len(space_left, orig_len, base_hdr_len,
   2037         1, OSSL_QUIC_VLINT_1B_MAX,
   2038         &hdr_len[0], &payload_len[0]);
   2039     valid[1] = try_len(space_left, orig_len, base_hdr_len,
   2040         2, OSSL_QUIC_VLINT_2B_MAX,
   2041         &hdr_len[1], &payload_len[1]);
   2042     valid[2] = try_len(space_left, orig_len, base_hdr_len,
   2043         4, OSSL_QUIC_VLINT_4B_MAX,
   2044         &hdr_len[2], &payload_len[2]);
   2045     valid[3] = try_len(space_left, orig_len, base_hdr_len,
   2046         8, OSSL_QUIC_VLINT_8B_MAX,
   2047         &hdr_len[3], &payload_len[3]);
   2048 
   2049     for (i = OSSL_NELEM(valid) - 1; i >= 0; --i)
   2050         if (valid[i] && payload_len[i] >= chosen_payload_len) {
   2051             chosen_payload_len = payload_len[i];
   2052             chosen_hdr_len = hdr_len[i];
   2053             ok = 1;
   2054         }
   2055 
   2056     *hlen = chosen_hdr_len;
   2057     *len = chosen_payload_len;
   2058     return ok;
   2059 }
   2060 
   2061 /*
   2062  * Given a CRYPTO frame header with accurate chdr->len and a budget
   2063  * (space_left), try to find the optimal value of chdr->len to fill as much of
   2064  * the budget as possible. This is slightly hairy because larger values of
   2065  * chdr->len cause larger encoded sizes of the length field of the frame, which
   2066  * in turn mean less space available for payload data. We check all possible
   2067  * encodings and choose the optimal encoding.
   2068  */
   2069 static int determine_crypto_len(struct tx_helper *h,
   2070     OSSL_QUIC_FRAME_CRYPTO *chdr,
   2071     size_t space_left,
   2072     uint64_t *hlen,
   2073     uint64_t *len)
   2074 {
   2075     size_t orig_len;
   2076     size_t base_hdr_len; /* CRYPTO header length without length field */
   2077 
   2078     if (chdr->len > SIZE_MAX)
   2079         return 0;
   2080 
   2081     orig_len = (size_t)chdr->len;
   2082 
   2083     chdr->len = 0;
   2084     base_hdr_len = ossl_quic_wire_get_encoded_frame_len_crypto_hdr(chdr);
   2085     chdr->len = orig_len;
   2086     if (base_hdr_len == 0)
   2087         return 0;
   2088 
   2089     --base_hdr_len;
   2090 
   2091     return determine_len(space_left, orig_len, base_hdr_len, hlen, len);
   2092 }
   2093 
   2094 static int determine_stream_len(struct tx_helper *h,
   2095     OSSL_QUIC_FRAME_STREAM *shdr,
   2096     size_t space_left,
   2097     uint64_t *hlen,
   2098     uint64_t *len)
   2099 {
   2100     size_t orig_len;
   2101     size_t base_hdr_len; /* STREAM header length without length field */
   2102 
   2103     if (shdr->len > SIZE_MAX)
   2104         return 0;
   2105 
   2106     orig_len = (size_t)shdr->len;
   2107 
   2108     shdr->len = 0;
   2109     base_hdr_len = ossl_quic_wire_get_encoded_frame_len_stream_hdr(shdr);
   2110     shdr->len = orig_len;
   2111     if (base_hdr_len == 0)
   2112         return 0;
   2113 
   2114     if (shdr->has_explicit_len)
   2115         --base_hdr_len;
   2116 
   2117     return determine_len(space_left, orig_len, base_hdr_len, hlen, len);
   2118 }
   2119 
   2120 static int txp_generate_crypto_frames(OSSL_QUIC_TX_PACKETISER *txp,
   2121     struct txp_pkt *pkt,
   2122     int *have_ack_eliciting)
   2123 {
   2124     const uint32_t enc_level = pkt->h.enc_level;
   2125     const uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   2126     QUIC_TXPIM_PKT *tpkt = pkt->tpkt;
   2127     struct tx_helper *h = &pkt->h;
   2128     size_t num_stream_iovec;
   2129     OSSL_QUIC_FRAME_STREAM shdr = { 0 };
   2130     OSSL_QUIC_FRAME_CRYPTO chdr = { 0 };
   2131     OSSL_QTX_IOVEC iov[2];
   2132     uint64_t hdr_bytes;
   2133     WPACKET *wpkt;
   2134     QUIC_TXPIM_CHUNK chunk = { 0 };
   2135     size_t i, space_left;
   2136 
   2137     for (i = 0;; ++i) {
   2138         space_left = tx_helper_get_space_left(h);
   2139 
   2140         if (space_left < MIN_FRAME_SIZE_CRYPTO)
   2141             return 1; /* no point trying */
   2142 
   2143         /* Do we have any CRYPTO data waiting? */
   2144         num_stream_iovec = OSSL_NELEM(iov);
   2145         if (!ossl_quic_sstream_get_stream_frame(txp->args.crypto[pn_space],
   2146                 i, &shdr, iov,
   2147                 &num_stream_iovec))
   2148             return 1; /* nothing to do */
   2149 
   2150         /* Convert STREAM frame header to CRYPTO frame header */
   2151         chdr.offset = shdr.offset;
   2152         chdr.len = shdr.len;
   2153 
   2154         if (chdr.len == 0)
   2155             return 1; /* nothing to do */
   2156 
   2157         /* Find best fit (header length, payload length) combination. */
   2158         if (!determine_crypto_len(h, &chdr, space_left, &hdr_bytes,
   2159                 &chdr.len))
   2160             return 1; /* can't fit anything */
   2161 
   2162         /*
   2163          * Truncate IOVs to match our chosen length.
   2164          *
   2165          * The length cannot be more than SIZE_MAX because this length comes
   2166          * from our send stream buffer.
   2167          */
   2168         ossl_quic_sstream_adjust_iov((size_t)chdr.len, iov, num_stream_iovec);
   2169 
   2170         /*
   2171          * Ensure we have enough iovecs allocated (1 for the header, up to 2 for
   2172          * the stream data.)
   2173          */
   2174         if (!txp_el_ensure_iovec(&txp->el[enc_level], h->num_iovec + 3))
   2175             return 0; /* alloc error */
   2176 
   2177         /* Encode the header. */
   2178         wpkt = tx_helper_begin(h);
   2179         if (wpkt == NULL)
   2180             return 0; /* alloc error */
   2181 
   2182         if (!ossl_quic_wire_encode_frame_crypto_hdr(wpkt, &chdr)) {
   2183             tx_helper_rollback(h);
   2184             return 1; /* can't fit */
   2185         }
   2186 
   2187         if (!tx_helper_commit(h))
   2188             return 0; /* alloc error */
   2189 
   2190         /* Add payload iovecs to the helper (infallible). */
   2191         for (i = 0; i < num_stream_iovec; ++i)
   2192             tx_helper_append_iovec(h, iov[i].buf, iov[i].buf_len);
   2193 
   2194         *have_ack_eliciting = 1;
   2195         tx_helper_unrestrict(h); /* no longer need PING */
   2196 
   2197         /* Log chunk to TXPIM. */
   2198         chunk.stream_id = UINT64_MAX; /* crypto stream */
   2199         chunk.start = chdr.offset;
   2200         chunk.end = chdr.offset + chdr.len - 1;
   2201         chunk.has_fin = 0; /* Crypto stream never ends */
   2202         if (!ossl_quic_txpim_pkt_append_chunk(tpkt, &chunk))
   2203             return 0; /* alloc error */
   2204     }
   2205 }
   2206 
   2207 struct chunk_info {
   2208     OSSL_QUIC_FRAME_STREAM shdr;
   2209     uint64_t orig_len;
   2210     OSSL_QTX_IOVEC iov[2];
   2211     size_t num_stream_iovec;
   2212     int valid;
   2213 };
   2214 
   2215 static int txp_plan_stream_chunk(OSSL_QUIC_TX_PACKETISER *txp,
   2216     struct tx_helper *h,
   2217     QUIC_SSTREAM *sstream,
   2218     QUIC_TXFC *stream_txfc,
   2219     size_t skip,
   2220     struct chunk_info *chunk,
   2221     uint64_t consumed)
   2222 {
   2223     uint64_t fc_credit, fc_swm, fc_limit;
   2224 
   2225     chunk->num_stream_iovec = OSSL_NELEM(chunk->iov);
   2226     chunk->valid = ossl_quic_sstream_get_stream_frame(sstream, skip,
   2227         &chunk->shdr,
   2228         chunk->iov,
   2229         &chunk->num_stream_iovec);
   2230     if (!chunk->valid)
   2231         return 1;
   2232 
   2233     if (!ossl_assert(chunk->shdr.len > 0 || chunk->shdr.is_fin))
   2234         /* Should only have 0-length chunk if FIN */
   2235         return 0;
   2236 
   2237     chunk->orig_len = chunk->shdr.len;
   2238 
   2239     /* Clamp according to connection and stream-level TXFC. */
   2240     fc_credit = ossl_quic_txfc_get_credit(stream_txfc, consumed);
   2241     fc_swm = ossl_quic_txfc_get_swm(stream_txfc);
   2242     fc_limit = fc_swm + fc_credit;
   2243 
   2244     if (chunk->shdr.len > 0 && chunk->shdr.offset + chunk->shdr.len > fc_limit) {
   2245         chunk->shdr.len = (fc_limit <= chunk->shdr.offset)
   2246             ? 0
   2247             : fc_limit - chunk->shdr.offset;
   2248         chunk->shdr.is_fin = 0;
   2249     }
   2250 
   2251     if (chunk->shdr.len == 0 && !chunk->shdr.is_fin) {
   2252         /*
   2253          * Nothing to do due to TXFC. Since SSTREAM returns chunks in ascending
   2254          * order of offset we don't need to check any later chunks, so stop
   2255          * iterating here.
   2256          */
   2257         chunk->valid = 0;
   2258         return 1;
   2259     }
   2260 
   2261     return 1;
   2262 }
   2263 
   2264 /*
   2265  * Returns 0 on fatal error (e.g. allocation failure), 1 on success.
   2266  * *packet_full is set to 1 if there is no longer enough room for another STREAM
   2267  * frame.
   2268  */
   2269 static int txp_generate_stream_frames(OSSL_QUIC_TX_PACKETISER *txp,
   2270     struct txp_pkt *pkt,
   2271     uint64_t id,
   2272     QUIC_SSTREAM *sstream,
   2273     QUIC_TXFC *stream_txfc,
   2274     QUIC_STREAM *next_stream,
   2275     int *have_ack_eliciting,
   2276     int *packet_full,
   2277     uint64_t *new_credit_consumed,
   2278     uint64_t conn_consumed)
   2279 {
   2280     int rc = 0;
   2281     struct chunk_info chunks[2] = { 0 };
   2282     const uint32_t enc_level = pkt->h.enc_level;
   2283     QUIC_TXPIM_PKT *tpkt = pkt->tpkt;
   2284     struct tx_helper *h = &pkt->h;
   2285     OSSL_QUIC_FRAME_STREAM *shdr;
   2286     WPACKET *wpkt;
   2287     QUIC_TXPIM_CHUNK chunk;
   2288     size_t i, j, space_left;
   2289     int can_fill_payload, use_explicit_len;
   2290     int could_have_following_chunk;
   2291     uint64_t orig_len;
   2292     uint64_t hdr_len_implicit, payload_len_implicit;
   2293     uint64_t hdr_len_explicit, payload_len_explicit;
   2294     uint64_t fc_swm, fc_new_hwm;
   2295 
   2296     fc_swm = ossl_quic_txfc_get_swm(stream_txfc);
   2297     fc_new_hwm = fc_swm;
   2298 
   2299     /*
   2300      * Load the first two chunks if any offered by the send stream. We retrieve
   2301      * the next chunk in advance so we can determine if we need to send any more
   2302      * chunks from the same stream after this one, which is needed when
   2303      * determining when we can use an implicit length in a STREAM frame.
   2304      */
   2305     for (i = 0; i < 2; ++i) {
   2306         if (!txp_plan_stream_chunk(txp, h, sstream, stream_txfc, i, &chunks[i],
   2307                 conn_consumed))
   2308             goto err;
   2309 
   2310         if (i == 0 && !chunks[i].valid) {
   2311             /* No chunks, nothing to do. */
   2312             rc = 1;
   2313             goto err;
   2314         }
   2315         chunks[i].shdr.stream_id = id;
   2316     }
   2317 
   2318     for (i = 0;; ++i) {
   2319         space_left = tx_helper_get_space_left(h);
   2320 
   2321         if (!chunks[i % 2].valid) {
   2322             /* Out of chunks; we're done. */
   2323             rc = 1;
   2324             goto err;
   2325         }
   2326 
   2327         if (space_left < MIN_FRAME_SIZE_STREAM) {
   2328             *packet_full = 1;
   2329             rc = 1;
   2330             goto err;
   2331         }
   2332 
   2333         if (!ossl_assert(!h->done_implicit))
   2334             /*
   2335              * Logic below should have ensured we didn't append an
   2336              * implicit-length unless we filled the packet or didn't have
   2337              * another stream to handle, so this should not be possible.
   2338              */
   2339             goto err;
   2340 
   2341         shdr = &chunks[i % 2].shdr;
   2342         orig_len = chunks[i % 2].orig_len;
   2343         if (i > 0)
   2344             /* Load next chunk for lookahead. */
   2345             if (!txp_plan_stream_chunk(txp, h, sstream, stream_txfc, i + 1,
   2346                     &chunks[(i + 1) % 2], conn_consumed))
   2347                 goto err;
   2348 
   2349         /*
   2350          * Find best fit (header length, payload length) combination for if we
   2351          * use an implicit length.
   2352          */
   2353         shdr->has_explicit_len = 0;
   2354         hdr_len_implicit = payload_len_implicit = 0;
   2355         if (!determine_stream_len(h, shdr, space_left,
   2356                 &hdr_len_implicit, &payload_len_implicit)) {
   2357             *packet_full = 1;
   2358             rc = 1;
   2359             goto err; /* can't fit anything */
   2360         }
   2361 
   2362         /*
   2363          * If there is a next stream, we don't use the implicit length so we can
   2364          * add more STREAM frames after this one, unless there is enough data
   2365          * for this STREAM frame to fill the packet.
   2366          */
   2367         can_fill_payload = (hdr_len_implicit + payload_len_implicit
   2368             >= space_left);
   2369 
   2370         /*
   2371          * Is there is a stream after this one, or another chunk pending
   2372          * transmission in this stream?
   2373          */
   2374         could_have_following_chunk
   2375             = (next_stream != NULL || chunks[(i + 1) % 2].valid);
   2376 
   2377         /* Choose between explicit or implicit length representations. */
   2378         use_explicit_len = !((can_fill_payload || !could_have_following_chunk)
   2379             && !pkt->force_pad);
   2380 
   2381         if (use_explicit_len) {
   2382             /*
   2383              * Find best fit (header length, payload length) combination for if
   2384              * we use an explicit length.
   2385              */
   2386             shdr->has_explicit_len = 1;
   2387             hdr_len_explicit = payload_len_explicit = 0;
   2388             if (!determine_stream_len(h, shdr, space_left,
   2389                     &hdr_len_explicit, &payload_len_explicit)) {
   2390                 *packet_full = 1;
   2391                 rc = 1;
   2392                 goto err; /* can't fit anything */
   2393             }
   2394 
   2395             shdr->len = payload_len_explicit;
   2396         } else {
   2397             *packet_full = 1;
   2398             shdr->has_explicit_len = 0;
   2399             shdr->len = payload_len_implicit;
   2400         }
   2401 
   2402         /* If this is a FIN, don't keep filling the packet with more FINs. */
   2403         if (shdr->is_fin)
   2404             chunks[(i + 1) % 2].valid = 0;
   2405 
   2406         /*
   2407          * We are now committed to our length (shdr->len can't change).
   2408          * If we truncated the chunk, clear the FIN bit.
   2409          */
   2410         if (shdr->len < orig_len)
   2411             shdr->is_fin = 0;
   2412 
   2413         /* Truncate IOVs to match our chosen length. */
   2414         ossl_quic_sstream_adjust_iov((size_t)shdr->len, chunks[i % 2].iov,
   2415             chunks[i % 2].num_stream_iovec);
   2416 
   2417         /*
   2418          * Ensure we have enough iovecs allocated (1 for the header, up to 2 for
   2419          * the stream data.)
   2420          */
   2421         if (!txp_el_ensure_iovec(&txp->el[enc_level], h->num_iovec + 3))
   2422             goto err; /* alloc error */
   2423 
   2424         /* Encode the header. */
   2425         wpkt = tx_helper_begin(h);
   2426         if (wpkt == NULL)
   2427             goto err; /* alloc error */
   2428 
   2429         if (!ossl_assert(ossl_quic_wire_encode_frame_stream_hdr(wpkt, shdr))) {
   2430             /* (Should not be possible.) */
   2431             tx_helper_rollback(h);
   2432             *packet_full = 1;
   2433             rc = 1;
   2434             goto err; /* can't fit */
   2435         }
   2436 
   2437         if (!tx_helper_commit(h))
   2438             goto err; /* alloc error */
   2439 
   2440         /* Add payload iovecs to the helper (infallible). */
   2441         for (j = 0; j < chunks[i % 2].num_stream_iovec; ++j)
   2442             tx_helper_append_iovec(h, chunks[i % 2].iov[j].buf,
   2443                 chunks[i % 2].iov[j].buf_len);
   2444 
   2445         *have_ack_eliciting = 1;
   2446         tx_helper_unrestrict(h); /* no longer need PING */
   2447         if (!shdr->has_explicit_len)
   2448             h->done_implicit = 1;
   2449 
   2450         /* Log new TXFC credit which was consumed. */
   2451         if (shdr->len > 0 && shdr->offset + shdr->len > fc_new_hwm)
   2452             fc_new_hwm = shdr->offset + shdr->len;
   2453 
   2454         /* Log chunk to TXPIM. */
   2455         chunk.stream_id = shdr->stream_id;
   2456         chunk.start = shdr->offset;
   2457         chunk.end = shdr->offset + shdr->len - 1;
   2458         chunk.has_fin = shdr->is_fin;
   2459         chunk.has_stop_sending = 0;
   2460         chunk.has_reset_stream = 0;
   2461         if (!ossl_quic_txpim_pkt_append_chunk(tpkt, &chunk))
   2462             goto err; /* alloc error */
   2463 
   2464         if (shdr->len < orig_len) {
   2465             /*
   2466              * If we did not serialize all of this chunk we definitely do not
   2467              * want to try the next chunk
   2468              */
   2469             rc = 1;
   2470             goto err;
   2471         }
   2472     }
   2473 
   2474 err:
   2475     *new_credit_consumed = fc_new_hwm - fc_swm;
   2476     return rc;
   2477 }
   2478 
   2479 static void txp_enlink_tmp(QUIC_STREAM **tmp_head, QUIC_STREAM *stream)
   2480 {
   2481     stream->txp_next = *tmp_head;
   2482     *tmp_head = stream;
   2483 }
   2484 
   2485 static int txp_generate_stream_related(OSSL_QUIC_TX_PACKETISER *txp,
   2486     struct txp_pkt *pkt,
   2487     int *have_ack_eliciting,
   2488     QUIC_STREAM **tmp_head)
   2489 {
   2490     QUIC_STREAM_ITER it;
   2491     WPACKET *wpkt;
   2492     uint64_t cwm;
   2493     QUIC_STREAM *stream, *snext;
   2494     struct tx_helper *h = &pkt->h;
   2495     uint64_t conn_consumed = 0;
   2496 
   2497     for (ossl_quic_stream_iter_init(&it, txp->args.qsm, 1);
   2498         it.stream != NULL;) {
   2499 
   2500         stream = it.stream;
   2501         ossl_quic_stream_iter_next(&it);
   2502         snext = it.stream;
   2503 
   2504         stream->txp_sent_fc = 0;
   2505         stream->txp_sent_stop_sending = 0;
   2506         stream->txp_sent_reset_stream = 0;
   2507         stream->txp_blocked = 0;
   2508         stream->txp_txfc_new_credit_consumed = 0;
   2509 
   2510         /* Stream Abort Frames (STOP_SENDING, RESET_STREAM) */
   2511         if (stream->want_stop_sending) {
   2512             OSSL_QUIC_FRAME_STOP_SENDING f;
   2513 
   2514             wpkt = tx_helper_begin(h);
   2515             if (wpkt == NULL)
   2516                 return 0; /* alloc error */
   2517 
   2518             f.stream_id = stream->id;
   2519             f.app_error_code = stream->stop_sending_aec;
   2520             if (!ossl_quic_wire_encode_frame_stop_sending(wpkt, &f)) {
   2521                 tx_helper_rollback(h); /* can't fit */
   2522                 txp_enlink_tmp(tmp_head, stream);
   2523                 break;
   2524             }
   2525 
   2526             if (!tx_helper_commit(h))
   2527                 return 0; /* alloc error */
   2528 
   2529             *have_ack_eliciting = 1;
   2530             tx_helper_unrestrict(h); /* no longer need PING */
   2531             stream->txp_sent_stop_sending = 1;
   2532         }
   2533 
   2534         if (stream->want_reset_stream) {
   2535             OSSL_QUIC_FRAME_RESET_STREAM f;
   2536 
   2537             if (!ossl_assert(stream->send_state == QUIC_SSTREAM_STATE_RESET_SENT))
   2538                 return 0;
   2539 
   2540             wpkt = tx_helper_begin(h);
   2541             if (wpkt == NULL)
   2542                 return 0; /* alloc error */
   2543 
   2544             f.stream_id = stream->id;
   2545             f.app_error_code = stream->reset_stream_aec;
   2546             if (!ossl_quic_stream_send_get_final_size(stream, &f.final_size))
   2547                 return 0; /* should not be possible */
   2548 
   2549             if (!ossl_quic_wire_encode_frame_reset_stream(wpkt, &f)) {
   2550                 tx_helper_rollback(h); /* can't fit */
   2551                 txp_enlink_tmp(tmp_head, stream);
   2552                 break;
   2553             }
   2554 
   2555             if (!tx_helper_commit(h))
   2556                 return 0; /* alloc error */
   2557 
   2558             *have_ack_eliciting = 1;
   2559             tx_helper_unrestrict(h); /* no longer need PING */
   2560             stream->txp_sent_reset_stream = 1;
   2561 
   2562             /*
   2563              * The final size of the stream as indicated by RESET_STREAM is used
   2564              * to ensure a consistent view of flow control state by both
   2565              * parties; if we happen to send a RESET_STREAM that consumes more
   2566              * flow control credit, make sure we account for that.
   2567              */
   2568             if (!ossl_assert(f.final_size <= ossl_quic_txfc_get_swm(&stream->txfc)))
   2569                 return 0;
   2570 
   2571             stream->txp_txfc_new_credit_consumed
   2572                 = f.final_size - ossl_quic_txfc_get_swm(&stream->txfc);
   2573         }
   2574 
   2575         /*
   2576          * Stream Flow Control Frames (MAX_STREAM_DATA)
   2577          *
   2578          * RFC 9000 s. 13.3: "An endpoint SHOULD stop sending MAX_STREAM_DATA
   2579          * frames when the receiving part of the stream enters a "Size Known" or
   2580          * "Reset Recvd" state." -- In practice, RECV is the only state
   2581          * in which it makes sense to generate more MAX_STREAM_DATA frames.
   2582          */
   2583         if (stream->recv_state == QUIC_RSTREAM_STATE_RECV
   2584             && (stream->want_max_stream_data
   2585                 || ossl_quic_rxfc_has_cwm_changed(&stream->rxfc, 0))) {
   2586 
   2587             wpkt = tx_helper_begin(h);
   2588             if (wpkt == NULL)
   2589                 return 0; /* alloc error */
   2590 
   2591             cwm = ossl_quic_rxfc_get_cwm(&stream->rxfc);
   2592 
   2593             if (!ossl_quic_wire_encode_frame_max_stream_data(wpkt, stream->id,
   2594                     cwm)) {
   2595                 tx_helper_rollback(h); /* can't fit */
   2596                 txp_enlink_tmp(tmp_head, stream);
   2597                 break;
   2598             }
   2599 
   2600             if (!tx_helper_commit(h))
   2601                 return 0; /* alloc error */
   2602 
   2603             *have_ack_eliciting = 1;
   2604             tx_helper_unrestrict(h); /* no longer need PING */
   2605             stream->txp_sent_fc = 1;
   2606         }
   2607 
   2608         /*
   2609          * Stream Data Frames (STREAM)
   2610          *
   2611          * RFC 9000 s. 3.3: A sender MUST NOT send a STREAM [...] frame for a
   2612          * stream in the "Reset Sent" state [or any terminal state]. We don't
   2613          * send any more STREAM frames if we are sending, have sent, or are
   2614          * planning to send, RESET_STREAM. The other terminal state is Data
   2615          * Recvd, but txp_generate_stream_frames() is guaranteed to generate
   2616          * nothing in this case.
   2617          */
   2618         if (ossl_quic_stream_has_send_buffer(stream)
   2619             && !ossl_quic_stream_send_is_reset(stream)) {
   2620             int packet_full = 0;
   2621 
   2622             if (!ossl_assert(!stream->want_reset_stream))
   2623                 return 0;
   2624 
   2625             if (!txp_generate_stream_frames(txp, pkt,
   2626                     stream->id, stream->sstream,
   2627                     &stream->txfc,
   2628                     snext,
   2629                     have_ack_eliciting,
   2630                     &packet_full,
   2631                     &stream->txp_txfc_new_credit_consumed,
   2632                     conn_consumed)) {
   2633                 /* Fatal error (allocation, etc.) */
   2634                 txp_enlink_tmp(tmp_head, stream);
   2635                 return 0;
   2636             }
   2637             conn_consumed += stream->txp_txfc_new_credit_consumed;
   2638 
   2639             if (packet_full) {
   2640                 txp_enlink_tmp(tmp_head, stream);
   2641                 break;
   2642             }
   2643         }
   2644 
   2645         txp_enlink_tmp(tmp_head, stream);
   2646     }
   2647 
   2648     return 1;
   2649 }
   2650 
   2651 static int txp_generate_for_el(OSSL_QUIC_TX_PACKETISER *txp,
   2652     struct txp_pkt *pkt,
   2653     int chosen_for_conn_close)
   2654 {
   2655     int rc = TXP_ERR_SUCCESS;
   2656     const uint32_t enc_level = pkt->h.enc_level;
   2657     const uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   2658     int have_ack_eliciting = 0, done_pre_token = 0;
   2659     const struct archetype_data a = pkt->geom.adata;
   2660     /*
   2661      * Cleared if we encode any non-ACK-eliciting frame type which rules out the
   2662      * packet being a non-inflight frame. This means any non-ACK ACK-eliciting
   2663      * frame, even PADDING frames. ACK eliciting frames always cause a packet to
   2664      * become ineligible for non-inflight treatment so it is not necessary to
   2665      * clear this in cases where have_ack_eliciting is set, as it is ignored in
   2666      * that case.
   2667      */
   2668     int can_be_non_inflight = 1;
   2669     QUIC_CFQ_ITEM *cfq_item;
   2670     QUIC_TXPIM_PKT *tpkt = NULL;
   2671     struct tx_helper *h = &pkt->h;
   2672 
   2673     /* Maximum PN reached? */
   2674     if (!ossl_quic_pn_valid(txp->next_pn[pn_space]))
   2675         goto fatal_err;
   2676 
   2677     if (!ossl_assert(pkt->tpkt == NULL))
   2678         goto fatal_err;
   2679 
   2680     if ((pkt->tpkt = tpkt = ossl_quic_txpim_pkt_alloc(txp->args.txpim)) == NULL)
   2681         goto fatal_err;
   2682 
   2683     /*
   2684      * Frame Serialization
   2685      * ===================
   2686      *
   2687      * We now serialize frames into the packet in descending order of priority.
   2688      */
   2689 
   2690     /* HANDSHAKE_DONE (Regenerate) */
   2691     if (a.allow_handshake_done && txp->want_handshake_done
   2692         && tx_helper_get_space_left(h) >= MIN_FRAME_SIZE_HANDSHAKE_DONE) {
   2693         WPACKET *wpkt = tx_helper_begin(h);
   2694 
   2695         if (wpkt == NULL)
   2696             goto fatal_err;
   2697 
   2698         if (ossl_quic_wire_encode_frame_handshake_done(wpkt)) {
   2699             tpkt->had_handshake_done_frame = 1;
   2700             have_ack_eliciting = 1;
   2701 
   2702             if (!tx_helper_commit(h))
   2703                 goto fatal_err;
   2704 
   2705             tx_helper_unrestrict(h); /* no longer need PING */
   2706         } else {
   2707             tx_helper_rollback(h);
   2708         }
   2709     }
   2710 
   2711     /* MAX_DATA (Regenerate) */
   2712     if (a.allow_conn_fc
   2713         && (txp->want_max_data
   2714             || ossl_quic_rxfc_has_cwm_changed(txp->args.conn_rxfc, 0))
   2715         && tx_helper_get_space_left(h) >= MIN_FRAME_SIZE_MAX_DATA) {
   2716         WPACKET *wpkt = tx_helper_begin(h);
   2717         uint64_t cwm = ossl_quic_rxfc_get_cwm(txp->args.conn_rxfc);
   2718 
   2719         if (wpkt == NULL)
   2720             goto fatal_err;
   2721 
   2722         if (ossl_quic_wire_encode_frame_max_data(wpkt, cwm)) {
   2723             tpkt->had_max_data_frame = 1;
   2724             have_ack_eliciting = 1;
   2725 
   2726             if (!tx_helper_commit(h))
   2727                 goto fatal_err;
   2728 
   2729             tx_helper_unrestrict(h); /* no longer need PING */
   2730         } else {
   2731             tx_helper_rollback(h);
   2732         }
   2733     }
   2734 
   2735     /* MAX_STREAMS_BIDI (Regenerate) */
   2736     if (a.allow_conn_fc
   2737         && (txp->want_max_streams_bidi
   2738             || ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_bidi_rxfc, 0))
   2739         && tx_helper_get_space_left(h) >= MIN_FRAME_SIZE_MAX_STREAMS_BIDI) {
   2740         WPACKET *wpkt = tx_helper_begin(h);
   2741         uint64_t max_streams
   2742             = ossl_quic_rxfc_get_cwm(txp->args.max_streams_bidi_rxfc);
   2743 
   2744         if (wpkt == NULL)
   2745             goto fatal_err;
   2746 
   2747         if (ossl_quic_wire_encode_frame_max_streams(wpkt, /*is_uni=*/0,
   2748                 max_streams)) {
   2749             tpkt->had_max_streams_bidi_frame = 1;
   2750             have_ack_eliciting = 1;
   2751 
   2752             if (!tx_helper_commit(h))
   2753                 goto fatal_err;
   2754 
   2755             tx_helper_unrestrict(h); /* no longer need PING */
   2756         } else {
   2757             tx_helper_rollback(h);
   2758         }
   2759     }
   2760 
   2761     /* MAX_STREAMS_UNI (Regenerate) */
   2762     if (a.allow_conn_fc
   2763         && (txp->want_max_streams_uni
   2764             || ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_uni_rxfc, 0))
   2765         && tx_helper_get_space_left(h) >= MIN_FRAME_SIZE_MAX_STREAMS_UNI) {
   2766         WPACKET *wpkt = tx_helper_begin(h);
   2767         uint64_t max_streams
   2768             = ossl_quic_rxfc_get_cwm(txp->args.max_streams_uni_rxfc);
   2769 
   2770         if (wpkt == NULL)
   2771             goto fatal_err;
   2772 
   2773         if (ossl_quic_wire_encode_frame_max_streams(wpkt, /*is_uni=*/1,
   2774                 max_streams)) {
   2775             tpkt->had_max_streams_uni_frame = 1;
   2776             have_ack_eliciting = 1;
   2777 
   2778             if (!tx_helper_commit(h))
   2779                 goto fatal_err;
   2780 
   2781             tx_helper_unrestrict(h); /* no longer need PING */
   2782         } else {
   2783             tx_helper_rollback(h);
   2784         }
   2785     }
   2786 
   2787     /* GCR Frames */
   2788     for (cfq_item = ossl_quic_cfq_get_priority_head(txp->args.cfq, pn_space);
   2789         cfq_item != NULL;
   2790         cfq_item = ossl_quic_cfq_item_get_priority_next(cfq_item, pn_space)) {
   2791         uint64_t frame_type = ossl_quic_cfq_item_get_frame_type(cfq_item);
   2792         const unsigned char *encoded = ossl_quic_cfq_item_get_encoded(cfq_item);
   2793         size_t encoded_len = ossl_quic_cfq_item_get_encoded_len(cfq_item);
   2794 
   2795         switch (frame_type) {
   2796         case OSSL_QUIC_FRAME_TYPE_NEW_CONN_ID:
   2797             if (!a.allow_new_conn_id)
   2798                 continue;
   2799             break;
   2800         case OSSL_QUIC_FRAME_TYPE_RETIRE_CONN_ID:
   2801             if (!a.allow_retire_conn_id)
   2802                 continue;
   2803             break;
   2804         case OSSL_QUIC_FRAME_TYPE_NEW_TOKEN:
   2805             if (!a.allow_new_token)
   2806                 continue;
   2807 
   2808             /*
   2809              * NEW_TOKEN frames are handled via GCR, but some
   2810              * Regenerate-strategy frames should come before them (namely
   2811              * ACK, CONNECTION_CLOSE, PATH_CHALLENGE and PATH_RESPONSE). If
   2812              * we find a NEW_TOKEN frame, do these now. If there are no
   2813              * NEW_TOKEN frames in the GCR queue we will handle these below.
   2814              */
   2815             if (!done_pre_token)
   2816                 if (txp_generate_pre_token(txp, pkt,
   2817                         chosen_for_conn_close,
   2818                         &can_be_non_inflight))
   2819                     done_pre_token = 1;
   2820 
   2821             break;
   2822         case OSSL_QUIC_FRAME_TYPE_PATH_RESPONSE:
   2823             if (!a.allow_path_response)
   2824                 continue;
   2825 
   2826             /*
   2827              * RFC 9000 s. 8.2.2: An endpoint MUST expand datagrams that
   2828              * contain a PATH_RESPONSE frame to at least the smallest
   2829              * allowed maximum datagram size of 1200 bytes.
   2830              */
   2831             pkt->force_pad = 1;
   2832             break;
   2833         default:
   2834             if (!a.allow_cfq_other)
   2835                 continue;
   2836             break;
   2837         }
   2838 
   2839         /*
   2840          * If the frame is too big, don't try to schedule any more GCR frames in
   2841          * this packet rather than sending subsequent ones out of order.
   2842          */
   2843         if (encoded_len > tx_helper_get_space_left(h))
   2844             break;
   2845 
   2846         if (!tx_helper_append_iovec(h, encoded, encoded_len))
   2847             goto fatal_err;
   2848 
   2849         ossl_quic_txpim_pkt_add_cfq_item(tpkt, cfq_item);
   2850 
   2851         if (ossl_quic_frame_type_is_ack_eliciting(frame_type)) {
   2852             have_ack_eliciting = 1;
   2853             tx_helper_unrestrict(h); /* no longer need PING */
   2854         }
   2855     }
   2856 
   2857     /*
   2858      * If we didn't generate ACK, CONNECTION_CLOSE, PATH_CHALLENGE or
   2859      * PATH_RESPONSE (as desired) before, do so now.
   2860      */
   2861     if (!done_pre_token)
   2862         if (txp_generate_pre_token(txp, pkt,
   2863                 chosen_for_conn_close,
   2864                 &can_be_non_inflight))
   2865             done_pre_token = 1;
   2866 
   2867     /* CRYPTO Frames */
   2868     if (a.allow_crypto)
   2869         if (!txp_generate_crypto_frames(txp, pkt, &have_ack_eliciting))
   2870             goto fatal_err;
   2871 
   2872     /* Stream-specific frames */
   2873     if (a.allow_stream_rel && txp->handshake_complete)
   2874         if (!txp_generate_stream_related(txp, pkt,
   2875                 &have_ack_eliciting,
   2876                 &pkt->stream_head))
   2877             goto fatal_err;
   2878 
   2879     /* PING */
   2880     tx_helper_unrestrict(h);
   2881 
   2882     if (!have_ack_eliciting && txp_need_ping(txp, pn_space, &a)) {
   2883         WPACKET *wpkt;
   2884 
   2885         assert(h->reserve > 0);
   2886         wpkt = tx_helper_begin(h);
   2887         if (wpkt == NULL)
   2888             goto fatal_err;
   2889 
   2890         if (!ossl_quic_wire_encode_frame_ping(wpkt)
   2891             || !tx_helper_commit(h))
   2892             /*
   2893              * We treat a request to be ACK-eliciting as a requirement, so this
   2894              * is an error.
   2895              */
   2896             goto fatal_err;
   2897 
   2898         have_ack_eliciting = 1;
   2899     }
   2900 
   2901     /* PADDING is added by ossl_quic_tx_packetiser_generate(). */
   2902 
   2903     /*
   2904      * ACKM Data
   2905      * =========
   2906      */
   2907     if (have_ack_eliciting)
   2908         can_be_non_inflight = 0;
   2909 
   2910     /* ACKM Data */
   2911     tpkt->ackm_pkt.num_bytes = h->bytes_appended + pkt->geom.pkt_overhead;
   2912     tpkt->ackm_pkt.pkt_num = txp->next_pn[pn_space];
   2913     /* largest_acked is set in txp_generate_pre_token */
   2914     tpkt->ackm_pkt.pkt_space = pn_space;
   2915     tpkt->ackm_pkt.is_inflight = !can_be_non_inflight;
   2916     tpkt->ackm_pkt.is_ack_eliciting = have_ack_eliciting;
   2917     tpkt->ackm_pkt.is_pto_probe = 0;
   2918     tpkt->ackm_pkt.is_mtu_probe = 0;
   2919     tpkt->ackm_pkt.time = txp->args.now(txp->args.now_arg);
   2920     tpkt->pkt_type = pkt->phdr.type;
   2921 
   2922     /* Done. */
   2923     return rc;
   2924 
   2925 fatal_err:
   2926     /*
   2927      * Handler for fatal errors, i.e. errors causing us to abort the entire
   2928      * packet rather than just one frame. Examples of such errors include
   2929      * allocation errors.
   2930      */
   2931     if (tpkt != NULL) {
   2932         ossl_quic_txpim_pkt_release(txp->args.txpim, tpkt);
   2933         pkt->tpkt = NULL;
   2934     }
   2935     return TXP_ERR_INTERNAL;
   2936 }
   2937 
   2938 /*
   2939  * Commits and queues a packet for transmission. There is no backing out after
   2940  * this.
   2941  *
   2942  * This:
   2943  *
   2944  *   - Sends the packet to the QTX for encryption and transmission;
   2945  *
   2946  *   - Records the packet as having been transmitted in FIFM. ACKM is informed,
   2947  *     etc. and the TXPIM record is filed.
   2948  *
   2949  *   - Informs various subsystems of frames that were sent and clears frame
   2950  *     wanted flags so that we do not generate the same frames again.
   2951  *
   2952  * Assumptions:
   2953  *
   2954  *   - pkt is a txp_pkt for the correct EL;
   2955  *
   2956  *   - pkt->tpkt is valid;
   2957  *
   2958  *   - pkt->tpkt->ackm_pkt has been fully filled in;
   2959  *
   2960  *   - Stream chunk records have been appended to pkt->tpkt for STREAM and
   2961  *     CRYPTO frames, but not for RESET_STREAM or STOP_SENDING frames;
   2962  *
   2963  *   - The chosen stream list for the packet can be fully walked from
   2964  *     pkt->stream_head using stream->txp_next;
   2965  *
   2966  *   - pkt->has_ack_eliciting is set correctly.
   2967  *
   2968  */
   2969 static int txp_pkt_commit(OSSL_QUIC_TX_PACKETISER *txp,
   2970     struct txp_pkt *pkt,
   2971     uint32_t archetype,
   2972     int *txpim_pkt_reffed)
   2973 {
   2974     int rc = 1;
   2975     uint32_t enc_level = pkt->h.enc_level;
   2976     uint32_t pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   2977     QUIC_TXPIM_PKT *tpkt = pkt->tpkt;
   2978     QUIC_STREAM *stream;
   2979     OSSL_QTX_PKT txpkt;
   2980     struct archetype_data a;
   2981 
   2982     *txpim_pkt_reffed = 0;
   2983 
   2984     /* Cannot send a packet with an empty payload. */
   2985     if (pkt->h.bytes_appended == 0)
   2986         return 0;
   2987 
   2988     if (!txp_get_archetype_data(enc_level, archetype, &a))
   2989         return 0;
   2990 
   2991     /* Packet Information for QTX */
   2992     txpkt.hdr = &pkt->phdr;
   2993     txpkt.iovec = txp->el[enc_level].iovec;
   2994     txpkt.num_iovec = pkt->h.num_iovec;
   2995     txpkt.local = NULL;
   2996     txpkt.peer = BIO_ADDR_family(&txp->args.peer) == AF_UNSPEC
   2997         ? NULL
   2998         : &txp->args.peer;
   2999     txpkt.pn = txp->next_pn[pn_space];
   3000     txpkt.flags = OSSL_QTX_PKT_FLAG_COALESCE; /* always try to coalesce */
   3001 
   3002     /* Generate TXPIM chunks representing STOP_SENDING and RESET_STREAM frames. */
   3003     for (stream = pkt->stream_head; stream != NULL; stream = stream->txp_next)
   3004         if (stream->txp_sent_stop_sending || stream->txp_sent_reset_stream) {
   3005             /* Log STOP_SENDING/RESET_STREAM chunk to TXPIM. */
   3006             QUIC_TXPIM_CHUNK chunk;
   3007 
   3008             chunk.stream_id = stream->id;
   3009             chunk.start = UINT64_MAX;
   3010             chunk.end = 0;
   3011             chunk.has_fin = 0;
   3012             chunk.has_stop_sending = stream->txp_sent_stop_sending;
   3013             chunk.has_reset_stream = stream->txp_sent_reset_stream;
   3014             if (!ossl_quic_txpim_pkt_append_chunk(tpkt, &chunk))
   3015                 return 0; /* alloc error */
   3016         }
   3017 
   3018     /* Dispatch to FIFD. */
   3019     if (!ossl_quic_fifd_pkt_commit(&txp->fifd, tpkt))
   3020         return 0;
   3021 
   3022     /*
   3023      * Transmission and Post-Packet Generation Bookkeeping
   3024      * ===================================================
   3025      *
   3026      * No backing out anymore - at this point the ACKM has recorded the packet
   3027      * as having been sent, so we need to increment our next PN counter, or
   3028      * the ACKM will complain when we try to record a duplicate packet with
   3029      * the same PN later. At this point actually sending the packet may still
   3030      * fail. In this unlikely event it will simply be handled as though it
   3031      * were a lost packet.
   3032      */
   3033     ++txp->next_pn[pn_space];
   3034     *txpim_pkt_reffed = 1;
   3035 
   3036     /* Send the packet. */
   3037     if (!ossl_qtx_write_pkt(txp->args.qtx, &txpkt))
   3038         return 0;
   3039 
   3040     /*
   3041      * Record FC and stream abort frames as sent; deactivate streams which no
   3042      * longer have anything to do.
   3043      */
   3044     for (stream = pkt->stream_head; stream != NULL; stream = stream->txp_next) {
   3045         if (stream->txp_sent_fc) {
   3046             stream->want_max_stream_data = 0;
   3047             ossl_quic_rxfc_has_cwm_changed(&stream->rxfc, 1);
   3048         }
   3049 
   3050         if (stream->txp_sent_stop_sending)
   3051             stream->want_stop_sending = 0;
   3052 
   3053         if (stream->txp_sent_reset_stream)
   3054             stream->want_reset_stream = 0;
   3055 
   3056         if (stream->txp_txfc_new_credit_consumed > 0) {
   3057             if (!ossl_assert(ossl_quic_txfc_consume_credit(&stream->txfc,
   3058                     stream->txp_txfc_new_credit_consumed)))
   3059                 /*
   3060                  * Should not be possible, but we should continue with our
   3061                  * bookkeeping as we have already committed the packet to the
   3062                  * FIFD. Just change the value we return.
   3063                  */
   3064                 rc = 0;
   3065 
   3066             stream->txp_txfc_new_credit_consumed = 0;
   3067         }
   3068 
   3069         /*
   3070          * If we no longer need to generate any flow control (MAX_STREAM_DATA),
   3071          * STOP_SENDING or RESET_STREAM frames, nor any STREAM frames (because
   3072          * the stream is drained of data or TXFC-blocked), we can mark the
   3073          * stream as inactive.
   3074          */
   3075         ossl_quic_stream_map_update_state(txp->args.qsm, stream);
   3076 
   3077         if (ossl_quic_stream_has_send_buffer(stream)
   3078             && !ossl_quic_sstream_has_pending(stream->sstream)
   3079             && ossl_quic_sstream_get_final_size(stream->sstream, NULL))
   3080             /*
   3081              * Transition to DATA_SENT if stream has a final size and we have
   3082              * sent all data.
   3083              */
   3084             ossl_quic_stream_map_notify_all_data_sent(txp->args.qsm, stream);
   3085     }
   3086 
   3087     /* We have now sent the packet, so update state accordingly. */
   3088     if (tpkt->ackm_pkt.is_ack_eliciting)
   3089         txp->force_ack_eliciting &= ~(1UL << pn_space);
   3090 
   3091     if (tpkt->had_handshake_done_frame)
   3092         txp->want_handshake_done = 0;
   3093 
   3094     if (tpkt->had_max_data_frame) {
   3095         txp->want_max_data = 0;
   3096         ossl_quic_rxfc_has_cwm_changed(txp->args.conn_rxfc, 1);
   3097     }
   3098 
   3099     if (tpkt->had_max_streams_bidi_frame) {
   3100         txp->want_max_streams_bidi = 0;
   3101         ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_bidi_rxfc, 1);
   3102     }
   3103 
   3104     if (tpkt->had_max_streams_uni_frame) {
   3105         txp->want_max_streams_uni = 0;
   3106         ossl_quic_rxfc_has_cwm_changed(txp->args.max_streams_uni_rxfc, 1);
   3107     }
   3108 
   3109     if (tpkt->had_ack_frame)
   3110         txp->want_ack &= ~(1UL << pn_space);
   3111 
   3112     if (tpkt->had_conn_close)
   3113         txp->want_conn_close = 0;
   3114 
   3115     /*
   3116      * Decrement probe request counts if we have sent a packet that meets
   3117      * the requirement of a probe, namely being ACK-eliciting.
   3118      */
   3119     if (tpkt->ackm_pkt.is_ack_eliciting) {
   3120         OSSL_ACKM_PROBE_INFO *probe_info
   3121             = ossl_ackm_get0_probe_request(txp->args.ackm);
   3122 
   3123         if (enc_level == QUIC_ENC_LEVEL_INITIAL
   3124             && probe_info->anti_deadlock_initial > 0)
   3125             --probe_info->anti_deadlock_initial;
   3126 
   3127         if (enc_level == QUIC_ENC_LEVEL_HANDSHAKE
   3128             && probe_info->anti_deadlock_handshake > 0)
   3129             --probe_info->anti_deadlock_handshake;
   3130 
   3131         if (a.allow_force_ack_eliciting /* (i.e., not for 0-RTT) */
   3132             && probe_info->pto[pn_space] > 0)
   3133             --probe_info->pto[pn_space];
   3134     }
   3135 
   3136     ossl_quic_fifd_pkt_discard_unreliable(&txp->fifd, tpkt);
   3137 
   3138     return rc;
   3139 }
   3140 
   3141 /* Ensure the iovec array is at least num elements long. */
   3142 static int txp_el_ensure_iovec(struct txp_el *el, size_t num)
   3143 {
   3144     OSSL_QTX_IOVEC *iovec;
   3145 
   3146     if (el->alloc_iovec >= num)
   3147         return 1;
   3148 
   3149     num = el->alloc_iovec != 0 ? el->alloc_iovec * 2 : 8;
   3150 
   3151     iovec = OPENSSL_realloc(el->iovec, sizeof(OSSL_QTX_IOVEC) * num);
   3152     if (iovec == NULL)
   3153         return 0;
   3154 
   3155     el->iovec = iovec;
   3156     el->alloc_iovec = num;
   3157     return 1;
   3158 }
   3159 
   3160 int ossl_quic_tx_packetiser_schedule_conn_close(OSSL_QUIC_TX_PACKETISER *txp,
   3161     const OSSL_QUIC_FRAME_CONN_CLOSE *f)
   3162 {
   3163     char *reason = NULL;
   3164     size_t reason_len = f->reason_len;
   3165     size_t max_reason_len = txp_get_mdpl(txp) / 2;
   3166 
   3167     if (txp->want_conn_close)
   3168         return 0;
   3169 
   3170     /*
   3171      * Arbitrarily limit the length of the reason length string to half of the
   3172      * MDPL.
   3173      */
   3174     if (reason_len > max_reason_len)
   3175         reason_len = max_reason_len;
   3176 
   3177     if (reason_len > 0) {
   3178         reason = OPENSSL_memdup(f->reason, reason_len);
   3179         if (reason == NULL)
   3180             return 0;
   3181     }
   3182 
   3183     txp->conn_close_frame = *f;
   3184     txp->conn_close_frame.reason = reason;
   3185     txp->conn_close_frame.reason_len = reason_len;
   3186     txp->want_conn_close = 1;
   3187     return 1;
   3188 }
   3189 
   3190 void ossl_quic_tx_packetiser_set_msg_callback(OSSL_QUIC_TX_PACKETISER *txp,
   3191     ossl_msg_cb msg_callback,
   3192     SSL *msg_callback_ssl)
   3193 {
   3194     txp->msg_callback = msg_callback;
   3195     txp->msg_callback_ssl = msg_callback_ssl;
   3196 }
   3197 
   3198 void ossl_quic_tx_packetiser_set_msg_callback_arg(OSSL_QUIC_TX_PACKETISER *txp,
   3199     void *msg_callback_arg)
   3200 {
   3201     txp->msg_callback_arg = msg_callback_arg;
   3202 }
   3203 
   3204 QUIC_PN ossl_quic_tx_packetiser_get_next_pn(OSSL_QUIC_TX_PACKETISER *txp,
   3205     uint32_t pn_space)
   3206 {
   3207     if (pn_space >= QUIC_PN_SPACE_NUM)
   3208         return UINT64_MAX;
   3209 
   3210     return txp->next_pn[pn_space];
   3211 }
   3212 
   3213 OSSL_TIME ossl_quic_tx_packetiser_get_deadline(OSSL_QUIC_TX_PACKETISER *txp)
   3214 {
   3215     /*
   3216      * TXP-specific deadline computations which rely on TXP innards. This is in
   3217      * turn relied on by the QUIC_CHANNEL code to determine the channel event
   3218      * handling deadline.
   3219      */
   3220     OSSL_TIME deadline = ossl_time_infinite();
   3221     uint32_t enc_level, pn_space;
   3222 
   3223     /*
   3224      * ACK generation is not CC-gated - packets containing only ACKs are allowed
   3225      * to bypass CC. We want to generate ACK frames even if we are currently
   3226      * restricted by CC so the peer knows we have received data. The generate
   3227      * call will take care of selecting the correct packet archetype.
   3228      */
   3229     for (enc_level = QUIC_ENC_LEVEL_INITIAL;
   3230         enc_level < QUIC_ENC_LEVEL_NUM;
   3231         ++enc_level)
   3232         if (ossl_qtx_is_enc_level_provisioned(txp->args.qtx, enc_level)) {
   3233             pn_space = ossl_quic_enc_level_to_pn_space(enc_level);
   3234             deadline = ossl_time_min(deadline,
   3235                 ossl_ackm_get_ack_deadline(txp->args.ackm, pn_space));
   3236         }
   3237 
   3238     /* When will CC let us send more? */
   3239     if (txp->args.cc_method->get_tx_allowance(txp->args.cc_data) == 0)
   3240         deadline = ossl_time_min(deadline,
   3241             txp->args.cc_method->get_wakeup_deadline(txp->args.cc_data));
   3242 
   3243     return deadline;
   3244 }
   3245