xref: /freebsd/crypto/openssl/include/internal/quic_record_rx.h (revision 88b8b7f0c4e9948667a2279e78e975a784049cba)
1 /*
2  * Copyright 2022-2025 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 #ifndef OSSL_QUIC_RECORD_RX_H
11 # define OSSL_QUIC_RECORD_RX_H
12 
13 # include <openssl/ssl.h>
14 # include "internal/quic_wire_pkt.h"
15 # include "internal/quic_types.h"
16 # include "internal/quic_predef.h"
17 # include "internal/quic_record_util.h"
18 # include "internal/quic_demux.h"
19 
20 # ifndef OPENSSL_NO_QUIC
21 
22 /*
23  * QUIC Record Layer - RX
24  * ======================
25  */
26 
27 typedef struct ossl_qrx_args_st {
28     OSSL_LIB_CTX   *libctx;
29     const char     *propq;
30 
31     /* Demux which owns the URXEs passed to us. */
32     QUIC_DEMUX     *demux;
33 
34     /* Length of connection IDs used in short-header packets in bytes. */
35     size_t          short_conn_id_len;
36 
37     /*
38      * Maximum number of deferred datagrams buffered at any one time.
39      * Suggested value: 32.
40      */
41     size_t          max_deferred;
42 
43     /* Initial reference PN used for RX. */
44     QUIC_PN         init_largest_pn[QUIC_PN_SPACE_NUM];
45 
46     /* Initial key phase. For debugging use only; always 0 in real use. */
47     unsigned char   init_key_phase_bit;
48 } OSSL_QRX_ARGS;
49 
50 /* Instantiates a new QRX. */
51 OSSL_QRX *ossl_qrx_new(const OSSL_QRX_ARGS *args);
52 
53 /*
54  * Frees the QRX. All packets obtained using ossl_qrx_read_pkt must already
55  * have been released by calling ossl_qrx_release_pkt.
56  *
57  * You do not need to call ossl_qrx_remove_dst_conn_id first; this function will
58  * unregister the QRX from the demuxer for all registered destination connection
59  * IDs (DCIDs) automatically.
60  */
61 void ossl_qrx_free(OSSL_QRX *qrx);
62 
63 /* Setters for the msg_callback and msg_callback_arg */
64 void ossl_qrx_set_msg_callback(OSSL_QRX *qrx, ossl_msg_cb msg_callback,
65                                SSL *msg_callback_ssl);
66 void ossl_qrx_set_msg_callback_arg(OSSL_QRX *qrx,
67                                    void *msg_callback_arg);
68 
69 /*
70  * Get the short header connection id len from this qrx
71  */
72 size_t ossl_qrx_get_short_hdr_conn_id_len(OSSL_QRX *qrx);
73 
74 /*
75  * Secret Management
76  * =================
77  *
78  * A QRX has several encryption levels (Initial, Handshake, 0-RTT, 1-RTT) and
79  * two directions (RX, TX). At any given time, key material is managed for each
80  * (EL, RX/TX) combination.
81  *
82  * Broadly, for a given (EL, RX/TX), the following state machine is applicable:
83  *
84  *   WAITING_FOR_KEYS --[Provide]--> HAVE_KEYS --[Discard]--> | DISCARDED |
85  *         \-------------------------------------[Discard]--> |           |
86  *
87  * To transition the RX side of an EL from WAITING_FOR_KEYS to HAVE_KEYS, call
88  * ossl_qrx_provide_secret (for the INITIAL EL, use of
89  * ossl_quic_provide_initial_secret is recommended).
90  *
91  * Once keys have been provisioned for an EL, you call
92  * ossl_qrx_discard_enc_level to transition the EL to the DISCARDED state. You
93  * can also call this function to transition directly to the DISCARDED state
94  * even before any keys have been provisioned for that EL.
95  *
96  * The DISCARDED state is terminal for a given EL; you cannot provide a secret
97  * again for that EL after reaching it.
98  *
99  * Incoming packets cannot be processed and decrypted if they target an EL
100  * not in the HAVE_KEYS state. However, there is a distinction between
101  * the WAITING_FOR_KEYS and DISCARDED states:
102  *
103  *   - In the WAITING_FOR_KEYS state, the QRX assumes keys for the given
104  *     EL will eventually arrive. Therefore, if it receives any packet
105  *     for an EL in this state, it buffers it and tries to process it
106  *     again once the EL reaches HAVE_KEYS.
107  *
108  *   - In the DISCARDED state, the QRX assumes no keys for the given
109  *     EL will ever arrive again. If it receives any packet for an EL
110  *     in this state, it is simply discarded.
111  *
112  * If the user wishes to instantiate a new QRX to replace an old one for
113  * whatever reason, for example to take over for an already established QUIC
114  * connection, it is important that all ELs no longer being used (i.e., INITIAL,
115  * 0-RTT, 1-RTT) are transitioned to the DISCARDED state. Otherwise, the QRX
116  * will assume that keys for these ELs will arrive in future, and will buffer
117  * any received packets for those ELs perpetually. This can be done by calling
118  * ossl_qrx_discard_enc_level for all non-1-RTT ELs immediately after
119  * instantiating the QRX.
120  *
121  * The INITIAL EL is not setup automatically when the QRX is instantiated. This
122  * allows the caller to instead discard it immediately after instantiation of
123  * the QRX if it is not needed, for example if the QRX is being instantiated to
124  * take over handling of an existing connection which has already passed the
125  * INITIAL phase. This avoids the unnecessary derivation of INITIAL keys where
126  * they are not needed. In the ordinary case, ossl_quic_provide_initial_secret
127  * should be called immediately after instantiation.
128  */
129 
130 /*
131  * Provides a secret to the QRX, which arises due to an encryption level change.
132  * enc_level is a QUIC_ENC_LEVEL_* value. To initialise the INITIAL encryption
133  * level, it is recommended to use ossl_quic_provide_initial_secret instead.
134  *
135  * You should seek to call this function for a given EL before packets of that
136  * EL arrive and are processed by the QRX. However, if packets have already
137  * arrived for a given EL, the QRX will defer processing of them and perform
138  * processing of them when this function is eventually called for the EL in
139  * question.
140  *
141  * suite_id is a QRL_SUITE_* value which determines the AEAD function used for
142  * the QRX.
143  *
144  * The secret passed is used directly to derive the "quic key", "quic iv" and
145  * "quic hp" values.
146  *
147  * secret_len is the length of the secret buffer in bytes. The buffer must be
148  * sized correctly to the chosen suite, else the function fails.
149  *
150  * This function can only be called once for a given EL, except for the INITIAL
151  * EL, which can need rekeying when a connection retry occurs. Subsequent calls
152  * for non-INITIAL ELs fail, as do calls made after a corresponding call to
153  * ossl_qrx_discard_enc_level for that EL. The secret for a non-INITIAL EL
154  * cannot be changed after it is set because QUIC has no facility for
155  * introducing additional key material after an EL is setup. QUIC key updates
156  * are managed semi-automatically by the QRX but do require some caller handling
157  * (see below).
158  *
159  * md is for internal use and should be NULL.
160  *
161  * Returns 1 on success or 0 on failure.
162  */
163 int ossl_qrx_provide_secret(OSSL_QRX              *qrx,
164                             uint32_t               enc_level,
165                             uint32_t               suite_id,
166                             EVP_MD                *md,
167                             const unsigned char   *secret,
168                             size_t                 secret_len);
169 
170 /*
171  * Utility function to update the pn space from a src to a dst qrx.
172  * Occasionally we use a temporary qrx to do packet validation on quic frames
173  * that are not yet associated with a channel, and in the event a validation is
174  * successful AND we allocate a new qrx for the newly created channel, we need
175  * to migrate the largest_pn values recorded in the tmp qrx to the channel qrx.
176  * If we don't then PN decoding fails in cases where the initial PN is a large value.
177  * This function does that migration for us
178  */
179 void ossl_qrx_update_pn_space(OSSL_QRX *src, OSSL_QRX *dst);
180 
181 /*
182  * Informs the QRX that it can now discard key material for a given EL. The QRX
183  * will no longer be able to process incoming packets received at that
184  * encryption level. This function is idempotent and succeeds if the EL has
185  * already been discarded.
186  *
187  * Returns 1 on success and 0 on failure.
188  */
189 int ossl_qrx_discard_enc_level(OSSL_QRX *qrx, uint32_t enc_level);
190 
191 /*
192  * Packet Reception
193  * ================
194  */
195 
196 /* Information about a received packet. */
197 struct ossl_qrx_pkt_st {
198     /*
199      * Points to a logical representation of the decoded QUIC packet header. The
200      * data and len fields point to the decrypted QUIC payload (i.e., to a
201      * sequence of zero or more (potentially malformed) frames to be decoded).
202      */
203     QUIC_PKT_HDR       *hdr;
204 
205     /*
206      * Address the packet was received from. If this is not available for this
207      * packet, this field is NULL (but this can only occur for manually injected
208      * packets).
209      */
210     const BIO_ADDR     *peer;
211 
212     /*
213      * Local address the packet was sent to. If this is not available for this
214      * packet, this field is NULL.
215      */
216     const BIO_ADDR     *local;
217 
218     /*
219      * This is the length of the datagram which contained this packet. Note that
220      * the datagram may have contained other packets than this. The intended use
221      * for this is so that the user can enforce minimum datagram sizes (e.g. for
222      * datagrams containing INITIAL packets), as required by RFC 9000.
223      */
224     size_t              datagram_len;
225 
226     /* The PN which was decoded for the packet, if the packet has a PN field. */
227     QUIC_PN             pn;
228 
229     /*
230      * Time the packet was received, or ossl_time_zero() if the demuxer is not
231      * using a now() function.
232      */
233     OSSL_TIME           time;
234 
235     /* The QRX which was used to receive the packet. */
236     OSSL_QRX            *qrx;
237 
238     /*
239      * The key epoch the packet was received with. Always 0 for non-1-RTT
240      * packets.
241      */
242     uint64_t            key_epoch;
243 
244     /*
245      * This monotonically increases with each datagram received.
246      * It is for diagnostic use only.
247      */
248     uint64_t            datagram_id;
249 };
250 
251 /*
252  * Tries to read a new decrypted packet from the QRX.
253  *
254  * On success, *pkt points to a OSSL_QRX_PKT structure. The structure should be
255  * freed when no longer needed by calling ossl_qrx_pkt_release(). The structure
256  * is refcounted; to gain extra references, call ossl_qrx_pkt_up_ref(). This
257  * will cause a corresponding number of calls to ossl_qrx_pkt_release() to be
258  * ignored.
259  *
260  * The resources referenced by (*pkt)->hdr, (*pkt)->hdr->data and (*pkt)->peer
261  * have the same lifetime as *pkt.
262  *
263  * Returns 1 on success and 0 on failure.
264  */
265 int ossl_qrx_read_pkt(OSSL_QRX *qrx, OSSL_QRX_PKT **pkt);
266 
267 /*
268  * Decrement the reference count for the given packet and frees it if the
269  * reference count drops to zero. No-op if pkt is NULL.
270  */
271 void ossl_qrx_pkt_release(OSSL_QRX_PKT *pkt);
272 
273 /*
274  * Like ossl_qrx_pkt_release, but just ensures that the refcount is dropped
275  * on this qrx_pkt, and ensure its not on any list
276  */
277 void ossl_qrx_pkt_orphan(OSSL_QRX_PKT *pkt);
278 
279 /* Increments the reference count for the given packet. */
280 void ossl_qrx_pkt_up_ref(OSSL_QRX_PKT *pkt);
281 
282 /*
283  * Returns 1 if there are any already processed (i.e. decrypted) packets waiting
284  * to be read from the QRX.
285  */
286 int ossl_qrx_processed_read_pending(OSSL_QRX *qrx);
287 
288 /*
289  * Returns 1 if there are any unprocessed (i.e. not yet decrypted) packets
290  * waiting to be processed by the QRX. These may or may not result in
291  * successfully decrypted packets once processed. This indicates whether
292  * unprocessed data is buffered by the QRX, not whether any data is available in
293  * a kernel socket buffer.
294  */
295 int ossl_qrx_unprocessed_read_pending(OSSL_QRX *qrx);
296 
297 /*
298  * Returns the number of UDP payload bytes received from the network so far
299  * since the last time this counter was cleared. If clear is 1, clears the
300  * counter and returns the old value.
301  *
302  * The intended use of this is to allow callers to determine how much credit to
303  * add to their anti-amplification budgets. This is reported separately instead
304  * of in the OSSL_QRX_PKT structure so that a caller can apply
305  * anti-amplification credit as soon as a datagram is received, before it has
306  * necessarily read all processed packets contained within that datagram from
307  * the QRX.
308  */
309 uint64_t ossl_qrx_get_bytes_received(OSSL_QRX *qrx, int clear);
310 
311 /*
312  * Sets a callback which is called when a packet is received and being validated
313  * before being queued in the read queue. This is called after packet body
314  * decryption and authentication to prevent exposing side channels. pn_space is
315  * a QUIC_PN_SPACE_* value denoting which PN space the PN belongs to.
316  *
317  * If this callback returns 1, processing continues normally.
318  * If this callback returns 0, the packet is discarded.
319  *
320  * Other packets in the same datagram will still be processed where possible.
321  *
322  * The callback is optional and can be unset by passing NULL for cb.
323  * cb_arg is an opaque value passed to cb.
324  */
325 typedef int (ossl_qrx_late_validation_cb)(QUIC_PN pn, int pn_space,
326                                           void *arg);
327 
328 int ossl_qrx_set_late_validation_cb(OSSL_QRX *qrx,
329                                     ossl_qrx_late_validation_cb *cb,
330                                     void *cb_arg);
331 
332 /*
333  * Forcibly injects a URXE which has been issued by the DEMUX into the QRX for
334  * processing. This can be used to pass a received datagram to the QRX if it
335  * would not be correctly routed to the QRX via standard DCID-based routing; for
336  * example, when handling an incoming Initial packet which is attempting to
337  * establish a new connection.
338  */
339 void ossl_qrx_inject_urxe(OSSL_QRX *qrx, QUIC_URXE *e);
340 void ossl_qrx_inject_pkt(OSSL_QRX *qrx, OSSL_QRX_PKT *pkt);
341 int ossl_qrx_validate_initial_packet(OSSL_QRX *qrx, QUIC_URXE *urxe,
342                                      const QUIC_CONN_ID *dcid);
343 
344 /*
345  * Decryption of 1-RTT packets must be explicitly enabled by calling this
346  * function. This is to comply with the requirement that we not process 1-RTT
347  * packets until the handshake is complete, even if we already have 1-RTT
348  * secrets. Even if a 1-RTT secret is provisioned for the QRX, incoming 1-RTT
349  * packets will be handled as though no key is available until this function is
350  * called. Calling this function will then requeue any such deferred packets for
351  * processing.
352  */
353 void ossl_qrx_allow_1rtt_processing(OSSL_QRX *qrx);
354 
355 /*
356  * Key Update (RX)
357  * ===============
358  *
359  * Key update on the RX side is a largely but not entirely automatic process.
360  *
361  * Key update is initially triggered by receiving a 1-RTT packet with a
362  * different Key Phase value. This could be caused by an attacker in the network
363  * flipping random bits, therefore such a key update is tentative until the
364  * packet payload is successfully decrypted and authenticated by the AEAD with
365  * the 'next' keys. These 'next' keys then become the 'current' keys and the
366  * 'current' keys then become the 'previous' keys. The 'previous' keys must be
367  * kept around temporarily as some packets may still be in flight in the network
368  * encrypted with the old keys. If the old Key Phase value is X and the new Key
369  * Phase Value is Y (where obviously X != Y), this creates an ambiguity as any
370  * new packet received with a KP of X could either be an attempt to initiate yet
371  * another key update right after the last one, or an old packet encrypted
372  * before the key update.
373  *
374  * RFC 9001 provides some guidance on handling this issue:
375  *
376  *   Strategy 1:
377  *      Three keys, disambiguation using packet numbers
378  *
379  *      "A recovered PN that is lower than any PN from the current KP uses the
380  *       previous packet protection keys; a recovered PN that is higher than any
381  *       PN from the current KP requires use of the next packet protection
382  *       keys."
383  *
384  *   Strategy 2:
385  *      Two keys and a timer
386  *
387  *      "Alternatively, endpoints can retain only two sets of packet protection
388  *       keys, swapping previous keys for next after enough time has passed to
389  *       allow for reordering in the network. In this case, the KP bit alone can
390  *       be used to select keys."
391  *
392  * Strategy 2 is more efficient (we can keep fewer cipher contexts around) and
393  * should cover all actually possible network conditions. It also allows a delay
394  * after we make the 'next' keys our 'current' keys before we generate new
395  * 'next' keys, which allows us to mitigate against malicious peers who try to
396  * initiate an excessive number of key updates.
397  *
398  * We therefore model the following state machine:
399  *
400  *
401  *                               PROVISIONED
402  *                     _______________________________
403  *                    |                               |
404  *   UNPROVISIONED  --|---->  NORMAL  <----------\    |------>  DISCARDED
405  *                    |          |               |    |
406  *                    |          |               |    |
407  *                    |          v               |    |
408  *                    |      UPDATING            |    |
409  *                    |          |               |    |
410  *                    |          |               |    |
411  *                    |          v               |    |
412  *                    |       COOLDOWN           |    |
413  *                    |          |               |    |
414  *                    |          |               |    |
415  *                    |          \---------------|    |
416  *                    |_______________________________|
417  *
418  *
419  * The RX starts (once a secret has been provisioned) in the NORMAL state. In
420  * the NORMAL state, the current expected value of the Key Phase bit is
421  * recorded. When a flipped Key Phase bit is detected, the RX attempts to
422  * decrypt and authenticate the received packet with the 'next' keys rather than
423  * the 'current' keys. If (and only if) this authentication is successful, we
424  * move to the UPDATING state. (An attacker in the network could flip
425  * the Key Phase bit randomly, so it is essential we do nothing until AEAD
426  * authentication is complete.)
427  *
428  * In the UPDATING state, we know a key update is occurring and record
429  * the new Key Phase bit value as the newly current value, but we still keep the
430  * old keys around so that we can still process any packets which were still in
431  * flight when the key update was initiated. In the UPDATING state, a
432  * Key Phase bit value different to the current expected value is treated not as
433  * the initiation of another key update, but a reference to our old keys.
434  *
435  * Eventually we will be reasonably sure we are not going to receive any more
436  * packets with the old keys. At this point, we can transition to the COOLDOWN
437  * state. This transition occurs automatically after a certain amount of time;
438  * RFC 9001 recommends it be the PTO interval, which relates to our RTT to the
439  * peer. The duration also SHOULD NOT exceed three times the PTO to assist with
440  * maintaining PFS.
441  *
442  * In the COOLDOWN phase, the old keys have been securely erased and only one
443  * set of keys can be used: the current keys. If a packet is received with a Key
444  * Phase bit value different to the current Key Phase Bit value, this is treated
445  * as a request for a Key Update, but this request is ignored and the packet is
446  * treated as malformed. We do this to allow mitigation against malicious peers
447  * trying to initiate an excessive number of Key Updates. The timeout for the
448  * transition from UPDATING to COOLDOWN is recommended as adequate for
449  * this purpose in itself by the RFC, so the normal additional timeout value for
450  * the transition from COOLDOWN to normal is zero (immediate transition).
451  *
452  * A summary of each state:
453  *
454  *                 Epoch  Exp KP  Uses Keys KS0    KS1    If Non-Expected KP Bit
455  *                 -----  ------  --------- ------ -----  ----------------------
456  *      NORMAL         0  0       Keyset 0  Gen 0  Gen 1  → UPDATING
457  *      UPDATING       1  1       Keyset 1  Gen 0  Gen 1  Use Keyset 0
458  *      COOLDOWN       1  1       Keyset 1  Erased Gen 1  Ignore Packet (*)
459  *
460  *      NORMAL         1  1       Keyset 1  Gen 2  Gen 1  → UPDATING
461  *      UPDATING       2  0       Keyset 0  Gen 2  Gen 1  Use Keyset 1
462  *      COOLDOWN       2  0       Keyset 0  Gen 2  Erased Ignore Packet (*)
463  *
464  * (*) Actually implemented by attempting to decrypt the packet with the
465  *     wrong keys (which ultimately has the same outcome), as recommended
466  *     by RFC 9001 to avoid creating timing channels.
467  *
468  * Note that the key material for the next key generation ("key epoch") is
469  * always kept in the NORMAL state (necessary to avoid side-channel attacks).
470  * This material is derived during the transition from COOLDOWN to NORMAL.
471  *
472  * Note that when a peer initiates a Key Update, we MUST also initiate a Key
473  * Update as per the RFC. The caller is responsible for detecting this condition
474  * and making the necessary calls to the TX side by detecting changes to the
475  * return value of ossl_qrx_get_key_epoch().
476  *
477  * The above states (NORMAL, UPDATING, COOLDOWN) can themselves be
478  * considered substates of the PROVISIONED state. Providing a secret to the QRX
479  * for an EL transitions from UNPROVISIONED, the initial state, to PROVISIONED
480  * (NORMAL). Dropping key material for an EL transitions from whatever the
481  * current substate of the PROVISIONED state is to the DISCARDED state, which is
482  * the terminal state.
483  *
484  * Note that non-1RTT ELs cannot undergo key update, therefore a non-1RTT EL is
485  * always in the NORMAL substate if it is in the PROVISIONED state.
486  */
487 
488 /*
489  * Return the current RX key epoch for the 1-RTT encryption level. This is
490  * initially zero and is incremented by one for every Key Update successfully
491  * signalled by the peer. If the 1-RTT EL has not yet been provisioned or has
492  * been discarded, returns UINT64_MAX.
493  *
494  * A necessary implication of this API is that the least significant bit of the
495  * returned value corresponds to the currently expected Key Phase bit, though
496  * callers are not anticipated to have any need of this information.
497  *
498  * It is not possible for the returned value to overflow, as a QUIC connection
499  * cannot support more than 2**62 packet numbers, and a connection must be
500  * terminated if this limit is reached.
501  *
502  * The caller should use this function to detect when the key epoch has changed
503  * and use it to initiate a key update on the TX side.
504  *
505  * The value returned by this function increments specifically at the transition
506  * from the NORMAL to the UPDATING state discussed above.
507  */
508 uint64_t ossl_qrx_get_key_epoch(OSSL_QRX *qrx);
509 
510 /*
511  * Sets an optional callback which will be called when the key epoch changes.
512  *
513  * The callback is optional and can be unset by passing NULL for cb.
514  * cb_arg is an opaque value passed to cb. pn is the PN of the packet.
515  * Since key update is only supported for 1-RTT packets, the PN is always
516  * in the Application Data PN space.
517 */
518 typedef void (ossl_qrx_key_update_cb)(QUIC_PN pn, void *arg);
519 
520 int ossl_qrx_set_key_update_cb(OSSL_QRX *qrx,
521                                ossl_qrx_key_update_cb *cb, void *cb_arg);
522 
523 /*
524  * Relates to the 1-RTT encryption level. The caller should call this after the
525  * UPDATING state is reached, after a timeout to be determined by the caller.
526  *
527  * This transitions from the UPDATING state to the COOLDOWN state (if
528  * still in the UPDATING state). If normal is 1, then transitions from
529  * the COOLDOWN state to the NORMAL state. Both transitions can be performed at
530  * once if desired.
531  *
532  * If in the normal state, or if in the COOLDOWN state and normal is 0, this is
533  * a no-op and returns 1. Returns 0 if the 1-RTT EL has not been provisioned or
534  * has been dropped.
535  *
536  * It is essential that the caller call this within a few PTO intervals of a key
537  * update occurring (as detected by the caller in a call to
538  * ossl_qrx_key_get_key_epoch()), as otherwise the peer will not be able to
539  * perform a Key Update ever again.
540  */
541 int ossl_qrx_key_update_timeout(OSSL_QRX *qrx, int normal);
542 
543 
544 /*
545  * Key Expiration
546  * ==============
547  */
548 
549 /*
550  * Returns the number of seemingly forged packets which have been received by
551  * the QRX. If this value reaches the value returned by
552  * ossl_qrx_get_max_epoch_forged_pkt_count() for a given EL, all further
553  * received encrypted packets for that EL will be discarded without processing.
554  *
555  * Note that the forged packet limit is for the connection lifetime, thus it is
556  * not reset by a key update. It is suggested that the caller terminate the
557  * connection a reasonable margin before the limit is reached. However, the
558  * exact limit imposed does vary by EL due to the possibility that different ELs
559  * use different AEADs.
560  */
561 uint64_t ossl_qrx_get_cur_forged_pkt_count(OSSL_QRX *qrx);
562 
563 /*
564  * Returns the maximum number of forged packets which the record layer will
565  * permit to be verified using this QRX instance.
566  */
567 uint64_t ossl_qrx_get_max_forged_pkt_count(OSSL_QRX *qrx,
568                                            uint32_t enc_level);
569 
570 # endif
571 
572 #endif
573