1a74702c6SGeorge Wang/* Copyright (c) 2017 - 2022 LiteSpeed Technologies Inc.  See LICENSE. */
25392f7a3SLiteSpeed Tech/*
35392f7a3SLiteSpeed Tech * lsquic_pr_queue.h -- a queue of packet requests
45392f7a3SLiteSpeed Tech *
55392f7a3SLiteSpeed Tech * Some packets need to be replied to outside of context of existing
65392f7a3SLiteSpeed Tech * mini or full connections:
75392f7a3SLiteSpeed Tech *
85392f7a3SLiteSpeed Tech *  1. A version negotiation packet needs to be sent when a packet
95392f7a3SLiteSpeed Tech *     arrives that specifies QUIC version that we do not support.
105392f7a3SLiteSpeed Tech *  2. A public reset packet needs to be sent when we receive a
115392f7a3SLiteSpeed Tech *     packet that does not belong to a known QUIC connection.
125392f7a3SLiteSpeed Tech *
135392f7a3SLiteSpeed Tech * The replies cannot be sent immediately.  They share outgoing
145392f7a3SLiteSpeed Tech * socket with existing connections and must be scheduled according
155392f7a3SLiteSpeed Tech * to prioritization rules.
165392f7a3SLiteSpeed Tech *
175392f7a3SLiteSpeed Tech * The information needed to generate reply packet  -- connection ID,
185392f7a3SLiteSpeed Tech * connection context, and the peer address -- is saved in the Packet
195392f7a3SLiteSpeed Tech * Request Queue.
205392f7a3SLiteSpeed Tech *
215392f7a3SLiteSpeed Tech * When it is time to send packets, the connection iterator knows to
225392f7a3SLiteSpeed Tech * call prq_next_conn() when appropriate.  What is returned is an
235392f7a3SLiteSpeed Tech * evanescent connection object that disappears as soon as the reply
245392f7a3SLiteSpeed Tech * packet is successfully sent out.
255392f7a3SLiteSpeed Tech *
265392f7a3SLiteSpeed Tech * There are two limits associated with Packet Request Queue:
275392f7a3SLiteSpeed Tech *  1. Maximum number of packet requests that are allowed to be
285392f7a3SLiteSpeed Tech *     pending at any one time.  This is simply to prevent memory
295392f7a3SLiteSpeed Tech *     blowout.
305392f7a3SLiteSpeed Tech *  2. Maximum verneg connection objects to be allocated at any one
315392f7a3SLiteSpeed Tech *     time.  This number is the same as the maximum batch size in
325392f7a3SLiteSpeed Tech *     the engine, because the packet (and, therefore, the connection)
335392f7a3SLiteSpeed Tech *     is returned to the Packet Request Queue when it could not be
345392f7a3SLiteSpeed Tech *     sent.
355392f7a3SLiteSpeed Tech *
365392f7a3SLiteSpeed Tech * We call this a "request" queue because it describes what we do with
375392f7a3SLiteSpeed Tech * QUIC packets whose version we do not support or those packets that
385392f7a3SLiteSpeed Tech * do not belong to an existing connection: we send a reply for each of
395392f7a3SLiteSpeed Tech * these packets, which effectively makes them "requests."
405392f7a3SLiteSpeed Tech */
415392f7a3SLiteSpeed Tech
425392f7a3SLiteSpeed Tech#ifndef LSQUIC_PR_QUEUE_H
435392f7a3SLiteSpeed Tech#define LSQUIC_PR_QUEUE_H 1
445392f7a3SLiteSpeed Tech
455392f7a3SLiteSpeed Techstruct lsquic_conn;
465392f7a3SLiteSpeed Techstruct lsquic_packet_in;
475392f7a3SLiteSpeed Techstruct lsquic_engine_settings;
485392f7a3SLiteSpeed Techstruct pr_queue;
495392f7a3SLiteSpeed Techstruct sockaddr;
505392f7a3SLiteSpeed Tech
515392f7a3SLiteSpeed Techenum packet_req_type {
525392f7a3SLiteSpeed Tech    PACKET_REQ_VERNEG,
535392f7a3SLiteSpeed Tech    PACKET_REQ_PUBRES,
545392f7a3SLiteSpeed Tech    N_PREQ_TYPES,
555392f7a3SLiteSpeed Tech};
565392f7a3SLiteSpeed Tech
575392f7a3SLiteSpeed Techextern const char *const lsquic_preqt2str[N_PREQ_TYPES];
585392f7a3SLiteSpeed Tech
595392f7a3SLiteSpeed Techstruct pr_queue *
60a5fa05f9SDmitri Tikhonovlsquic_prq_create (unsigned max_elems, unsigned max_conns,
615392f7a3SLiteSpeed Tech                const struct lsquic_engine_public *);
625392f7a3SLiteSpeed Tech
635392f7a3SLiteSpeed Techvoid
64a5fa05f9SDmitri Tikhonovlsquic_prq_destroy (struct pr_queue *);
655392f7a3SLiteSpeed Tech
665392f7a3SLiteSpeed Techint
67a5fa05f9SDmitri Tikhonovlsquic_prq_new_req (struct pr_queue *, enum packet_req_type,
685392f7a3SLiteSpeed Tech             const struct lsquic_packet_in *, void *conn_ctx,
695392f7a3SLiteSpeed Tech             const struct sockaddr *local_addr,
705392f7a3SLiteSpeed Tech             const struct sockaddr *peer_addr);
715392f7a3SLiteSpeed Tech
725392f7a3SLiteSpeed Techstruct lsquic_conn *
73a5fa05f9SDmitri Tikhonovlsquic_prq_next_conn (struct pr_queue *);
745392f7a3SLiteSpeed Tech
755392f7a3SLiteSpeed Techint
76a5fa05f9SDmitri Tikhonovlsquic_prq_have_pending (const struct pr_queue *);
775392f7a3SLiteSpeed Tech
787ee41525SDmitri Tikhonovvoid
797ee41525SDmitri Tikhonovlsquic_prq_drop (struct lsquic_conn *);
807ee41525SDmitri Tikhonov
815392f7a3SLiteSpeed Tech#endif
82