xref: /freebsd/crypto/openssl/ssl/quic/qlog_event_helpers.c (revision e7be843b4a162e68651d3911f0357ed464915629)
1 /*
2  * Copyright 2023-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 #include "internal/qlog_event_helpers.h"
11 #include "internal/common.h"
12 #include "internal/packet.h"
13 #include "internal/quic_channel.h"
14 #include "internal/quic_error.h"
15 
ossl_qlog_event_connectivity_connection_started(QLOG * qlog,const QUIC_CONN_ID * init_dcid)16 void ossl_qlog_event_connectivity_connection_started(QLOG *qlog,
17                                                      const QUIC_CONN_ID *init_dcid)
18 {
19 #ifndef OPENSSL_NO_QLOG
20     QLOG_EVENT_BEGIN(qlog, connectivity, connection_started)
21         QLOG_STR("protocol", "quic");
22         QLOG_CID("dst_cid", init_dcid);
23     QLOG_EVENT_END()
24 #endif
25 }
26 
27 #ifndef OPENSSL_NO_QLOG
map_state_to_qlog(uint32_t state,int handshake_complete,int handshake_confirmed)28 static const char *map_state_to_qlog(uint32_t state,
29                                      int handshake_complete,
30                                      int handshake_confirmed)
31 {
32     switch (state) {
33     default:
34     case QUIC_CHANNEL_STATE_IDLE:
35         return NULL;
36 
37     case QUIC_CHANNEL_STATE_ACTIVE:
38         if (handshake_confirmed)
39             return "handshake_confirmed";
40         else if (handshake_complete)
41             return "handshake_complete";
42         else
43             return "attempted";
44 
45     case QUIC_CHANNEL_STATE_TERMINATING_CLOSING:
46         return "closing";
47 
48     case QUIC_CHANNEL_STATE_TERMINATING_DRAINING:
49         return "draining";
50 
51     case QUIC_CHANNEL_STATE_TERMINATED:
52         return "closed";
53     }
54 }
55 #endif
56 
ossl_qlog_event_connectivity_connection_state_updated(QLOG * qlog,uint32_t old_state,uint32_t new_state,int handshake_complete,int handshake_confirmed)57 void ossl_qlog_event_connectivity_connection_state_updated(QLOG *qlog,
58                                                            uint32_t old_state,
59                                                            uint32_t new_state,
60                                                            int handshake_complete,
61                                                            int handshake_confirmed)
62 {
63 #ifndef OPENSSL_NO_QLOG
64     const char *state_s;
65 
66     QLOG_EVENT_BEGIN(qlog, connectivity, connection_state_updated)
67         state_s = map_state_to_qlog(new_state,
68                                     handshake_complete,
69                                     handshake_confirmed);
70 
71         if (state_s != NULL)
72             QLOG_STR("state", state_s);
73     QLOG_EVENT_END()
74 #endif
75 }
76 
77 #ifndef OPENSSL_NO_QLOG
quic_err_to_qlog(uint64_t error_code)78 static const char *quic_err_to_qlog(uint64_t error_code)
79 {
80     switch (error_code) {
81     case OSSL_QUIC_ERR_INTERNAL_ERROR:
82         return "internal_error";
83     case OSSL_QUIC_ERR_CONNECTION_REFUSED:
84         return "connection_refused";
85     case OSSL_QUIC_ERR_FLOW_CONTROL_ERROR:
86         return "flow_control_error";
87     case OSSL_QUIC_ERR_STREAM_LIMIT_ERROR:
88         return "stream_limit_error";
89     case OSSL_QUIC_ERR_STREAM_STATE_ERROR:
90         return "stream_state_error";
91     case OSSL_QUIC_ERR_FINAL_SIZE_ERROR:
92         return "final_size_error";
93     case OSSL_QUIC_ERR_FRAME_ENCODING_ERROR:
94         return "frame_encoding_error";
95     case OSSL_QUIC_ERR_TRANSPORT_PARAMETER_ERROR:
96         return "transport_parameter_error";
97     case OSSL_QUIC_ERR_CONNECTION_ID_LIMIT_ERROR:
98         return "connection_id_limit_error";
99     case OSSL_QUIC_ERR_PROTOCOL_VIOLATION:
100         return "protocol_violation";
101     case OSSL_QUIC_ERR_INVALID_TOKEN:
102         return "invalid_token";
103     case OSSL_QUIC_ERR_APPLICATION_ERROR:
104         return "application_error";
105     case OSSL_QUIC_ERR_CRYPTO_BUFFER_EXCEEDED:
106         return "crypto_buffer_exceeded";
107     case OSSL_QUIC_ERR_KEY_UPDATE_ERROR:
108         return "key_update_error";
109     case OSSL_QUIC_ERR_AEAD_LIMIT_REACHED:
110         return "aead_limit_reached";
111     case OSSL_QUIC_ERR_NO_VIABLE_PATH:
112         return "no_viable_path";
113     default:
114         return NULL;
115     }
116 }
117 #endif
118 
ossl_qlog_event_connectivity_connection_closed(QLOG * qlog,const QUIC_TERMINATE_CAUSE * tcause)119 void ossl_qlog_event_connectivity_connection_closed(QLOG *qlog,
120                                                     const QUIC_TERMINATE_CAUSE *tcause)
121 {
122 #ifndef OPENSSL_NO_QLOG
123     QLOG_EVENT_BEGIN(qlog, connectivity, connection_closed)
124         QLOG_STR("owner", tcause->remote ? "remote" : "local");
125         if (tcause->app) {
126             QLOG_U64("application_code", tcause->error_code);
127         } else {
128             const char *m = quic_err_to_qlog(tcause->error_code);
129             char ce[32];
130 
131             if (tcause->error_code >= OSSL_QUIC_ERR_CRYPTO_ERR_BEGIN
132                 && tcause->error_code <= OSSL_QUIC_ERR_CRYPTO_ERR_END) {
133                 BIO_snprintf(ce, sizeof(ce), "crypto_error_0x%03llx",
134                              (unsigned long long)tcause->error_code);
135                 m = ce;
136             }
137             /* TODO(QLOG FUTURE): Consider adding ERR information in the output. */
138 
139             if (m != NULL)
140                 QLOG_STR("connection_code", m);
141             else
142                 QLOG_U64("connection_code", tcause->error_code);
143         }
144 
145         QLOG_STR_LEN("reason", tcause->reason, tcause->reason_len);
146     QLOG_EVENT_END()
147 #endif
148 }
149 
150 #ifndef OPENSSL_NO_QLOG
quic_pkt_type_to_qlog(uint32_t pkt_type)151 static const char *quic_pkt_type_to_qlog(uint32_t pkt_type)
152 {
153     switch (pkt_type) {
154     case QUIC_PKT_TYPE_INITIAL:
155         return "initial";
156     case QUIC_PKT_TYPE_HANDSHAKE:
157         return "handshake";
158     case QUIC_PKT_TYPE_0RTT:
159         return "0RTT";
160     case QUIC_PKT_TYPE_1RTT:
161         return "1RTT";
162     case QUIC_PKT_TYPE_VERSION_NEG:
163         return "version_negotiation";
164     case QUIC_PKT_TYPE_RETRY:
165         return "retry";
166     default:
167         return "unknown";
168     }
169 }
170 #endif
171 
ossl_qlog_event_recovery_packet_lost(QLOG * qlog,const QUIC_TXPIM_PKT * tpkt)172 void ossl_qlog_event_recovery_packet_lost(QLOG *qlog,
173                                           const QUIC_TXPIM_PKT *tpkt)
174 {
175 #ifndef OPENSSL_NO_QLOG
176     QLOG_EVENT_BEGIN(qlog, recovery, packet_lost)
177         QLOG_BEGIN("header")
178             QLOG_STR("packet_type", quic_pkt_type_to_qlog(tpkt->pkt_type));
179             if (ossl_quic_pkt_type_has_pn(tpkt->pkt_type))
180                 QLOG_U64("packet_number", tpkt->ackm_pkt.pkt_num);
181         QLOG_END()
182     QLOG_EVENT_END()
183 #endif
184 }
185 
186 #ifndef OPENSSL_NO_QLOG
187 # define MAX_ACK_RANGES 32
188 
ignore_res(int x)189 static void ignore_res(int x) {}
190 
191 /*
192  * For logging received packets, we need to parse all the frames in the packet
193  * to log them. We should do this separately to the RXDP code because we want to
194  * log the packet and its contents before we start to actually process it in
195  * case it causes an error. We also in general don't want to do other
196  * non-logging related work in the middle of an event logging transaction.
197  * Reparsing packet data allows us to meet these needs while avoiding the need
198  * to keep around bookkeeping data on what frames were in a packet, etc.
199  *
200  * For logging transmitted packets, we actually reuse the same code and reparse
201  * the outgoing packet's payload. This again has the advantage that we only log
202  * a packet when it is actually queued for transmission (and not if something
203  * goes wrong before then) while avoiding the need to keep around bookkeeping
204  * data on what frames it contained.
205  */
log_frame_actual(QLOG * qlog_instance,PACKET * pkt,size_t * need_skip)206 static int log_frame_actual(QLOG *qlog_instance, PACKET *pkt,
207                             size_t *need_skip)
208 {
209     uint64_t frame_type;
210     OSSL_QUIC_FRAME_ACK ack;
211     OSSL_QUIC_ACK_RANGE ack_ranges[MAX_ACK_RANGES];
212     uint64_t num_ranges, total_ranges;
213     size_t i;
214     PACKET orig_pkt = *pkt;
215 
216     if (!ossl_quic_wire_peek_frame_header(pkt, &frame_type, NULL)) {
217         *need_skip = SIZE_MAX;
218         return 0;
219     }
220 
221     /*
222      * If something goes wrong decoding a frame we cannot log it as that frame
223      * as we need to know how to decode it in order to be able to do so, but in
224      * that case we log it as an unknown frame to assist with diagnosis.
225      */
226     switch (frame_type) {
227     case OSSL_QUIC_FRAME_TYPE_PADDING:
228         QLOG_STR("frame_type", "padding");
229         QLOG_U64("payload_length",
230                  ossl_quic_wire_decode_padding(pkt));
231         break;
232     case OSSL_QUIC_FRAME_TYPE_PING:
233         if (!ossl_quic_wire_decode_frame_ping(pkt))
234             goto unknown;
235 
236         QLOG_STR("frame_type", "ping");
237         break;
238     case OSSL_QUIC_FRAME_TYPE_ACK_WITHOUT_ECN:
239     case OSSL_QUIC_FRAME_TYPE_ACK_WITH_ECN:
240         if (!ossl_quic_wire_peek_frame_ack_num_ranges(pkt, &num_ranges))
241             goto unknown;
242 
243         ack.ack_ranges      = ack_ranges;
244         ack.num_ack_ranges  = OSSL_NELEM(ack_ranges);
245         if (!ossl_quic_wire_decode_frame_ack(pkt, 3, &ack, &total_ranges))
246             goto unknown;
247 
248         QLOG_STR("frame_type", "ack");
249         QLOG_U64("ack_delay", ossl_time2ms(ack.delay_time));
250         if (ack.ecn_present) {
251             QLOG_U64("ect1", ack.ect0);
252             QLOG_U64("ect0", ack.ect1);
253             QLOG_U64("ce", ack.ecnce);
254         }
255         QLOG_BEGIN_ARRAY("acked_ranges");
256         for (i = 0; i < ack.num_ack_ranges; ++i) {
257             QLOG_BEGIN_ARRAY(NULL)
258                 QLOG_U64(NULL, ack.ack_ranges[i].start);
259                 if (ack.ack_ranges[i].end != ack.ack_ranges[i].start)
260                     QLOG_U64(NULL, ack.ack_ranges[i].end);
261             QLOG_END_ARRAY()
262         }
263         QLOG_END_ARRAY()
264         break;
265     case OSSL_QUIC_FRAME_TYPE_RESET_STREAM:
266         {
267             OSSL_QUIC_FRAME_RESET_STREAM f;
268 
269             if (!ossl_quic_wire_decode_frame_reset_stream(pkt, &f))
270                 goto unknown;
271 
272             QLOG_STR("frame_type", "reset_stream");
273             QLOG_U64("stream_id", f.stream_id);
274             QLOG_U64("error_code", f.app_error_code);
275             QLOG_U64("final_size", f.final_size);
276         }
277         break;
278     case OSSL_QUIC_FRAME_TYPE_STOP_SENDING:
279         {
280             OSSL_QUIC_FRAME_STOP_SENDING f;
281 
282             if (!ossl_quic_wire_decode_frame_stop_sending(pkt, &f))
283                 goto unknown;
284 
285             QLOG_STR("frame_type", "stop_sending");
286             QLOG_U64("stream_id", f.stream_id);
287             QLOG_U64("error_code", f.app_error_code);
288         }
289         break;
290     case OSSL_QUIC_FRAME_TYPE_CRYPTO:
291         {
292             OSSL_QUIC_FRAME_CRYPTO f;
293 
294             if (!ossl_quic_wire_decode_frame_crypto(pkt, 1, &f))
295                 goto unknown;
296 
297             QLOG_STR("frame_type", "crypto");
298             QLOG_U64("offset", f.offset);
299             QLOG_U64("payload_length", f.len);
300             *need_skip += (size_t)f.len;
301         }
302         break;
303     case OSSL_QUIC_FRAME_TYPE_STREAM:
304     case OSSL_QUIC_FRAME_TYPE_STREAM_FIN:
305     case OSSL_QUIC_FRAME_TYPE_STREAM_LEN:
306     case OSSL_QUIC_FRAME_TYPE_STREAM_LEN_FIN:
307     case OSSL_QUIC_FRAME_TYPE_STREAM_OFF:
308     case OSSL_QUIC_FRAME_TYPE_STREAM_OFF_FIN:
309     case OSSL_QUIC_FRAME_TYPE_STREAM_OFF_LEN:
310     case OSSL_QUIC_FRAME_TYPE_STREAM_OFF_LEN_FIN:
311         {
312             OSSL_QUIC_FRAME_STREAM f;
313 
314             if (!ossl_quic_wire_decode_frame_stream(pkt, 1, &f))
315                 goto unknown;
316 
317             QLOG_STR("frame_type", "stream");
318             QLOG_U64("stream_id", f.stream_id);
319             QLOG_U64("offset", f.offset);
320             QLOG_U64("payload_length", f.len);
321             QLOG_BOOL("explicit_length", f.has_explicit_len);
322             if (f.is_fin)
323                 QLOG_BOOL("fin", 1);
324             *need_skip = f.has_explicit_len
325                 ? *need_skip + (size_t)f.len : SIZE_MAX;
326         }
327         break;
328     case OSSL_QUIC_FRAME_TYPE_MAX_DATA:
329         {
330             uint64_t x;
331 
332             if (!ossl_quic_wire_decode_frame_max_data(pkt, &x))
333                 goto unknown;
334 
335             QLOG_STR("frame_type", "max_data");
336             QLOG_U64("maximum", x);
337         }
338         break;
339     case OSSL_QUIC_FRAME_TYPE_MAX_STREAMS_BIDI:
340     case OSSL_QUIC_FRAME_TYPE_MAX_STREAMS_UNI:
341         {
342             uint64_t x;
343 
344             if (!ossl_quic_wire_decode_frame_max_streams(pkt, &x))
345                 goto unknown;
346 
347             QLOG_STR("frame_type", "max_streams");
348             QLOG_STR("stream_type",
349                      frame_type == OSSL_QUIC_FRAME_TYPE_MAX_STREAMS_BIDI
350                         ? "bidirectional" : "unidirectional");
351             QLOG_U64("maximum", x);
352         }
353         break;
354     case OSSL_QUIC_FRAME_TYPE_MAX_STREAM_DATA:
355         {
356             uint64_t stream_id, max_data;
357 
358             if (!ossl_quic_wire_decode_frame_max_stream_data(pkt, &stream_id,
359                                                              &max_data))
360                 goto unknown;
361 
362             QLOG_STR("frame_type", "max_stream_data");
363             QLOG_U64("stream_id", stream_id);
364             QLOG_U64("maximum", max_data);
365         }
366         break;
367     case OSSL_QUIC_FRAME_TYPE_PATH_CHALLENGE:
368         {
369             uint64_t challenge;
370 
371             if (!ossl_quic_wire_decode_frame_path_challenge(pkt, &challenge))
372                 goto unknown;
373 
374             QLOG_STR("frame_type", "path_challenge");
375         }
376         break;
377     case OSSL_QUIC_FRAME_TYPE_PATH_RESPONSE:
378         {
379             uint64_t challenge;
380 
381             if (!ossl_quic_wire_decode_frame_path_response(pkt, &challenge))
382                 goto unknown;
383 
384             QLOG_STR("frame_type", "path_response");
385         }
386         break;
387     case OSSL_QUIC_FRAME_TYPE_CONN_CLOSE_APP:
388     case OSSL_QUIC_FRAME_TYPE_CONN_CLOSE_TRANSPORT:
389         {
390             OSSL_QUIC_FRAME_CONN_CLOSE f;
391 
392             if (!ossl_quic_wire_decode_frame_conn_close(pkt, &f))
393                 goto unknown;
394 
395             QLOG_STR("frame_type", "connection_close");
396             QLOG_STR("error_space", f.is_app ? "application" : "transport");
397             QLOG_U64("error_code_value", f.error_code);
398             if (f.is_app)
399                 QLOG_U64("error_code", f.error_code);
400             if (!f.is_app && f.frame_type != 0)
401                 QLOG_U64("trigger_frame_type", f.frame_type);
402             QLOG_STR_LEN("reason", f.reason, f.reason_len);
403         }
404         break;
405     case OSSL_QUIC_FRAME_TYPE_HANDSHAKE_DONE:
406         {
407             if (!ossl_quic_wire_decode_frame_handshake_done(pkt))
408                 goto unknown;
409 
410             QLOG_STR("frame_type", "handshake_done");
411         }
412         break;
413     case OSSL_QUIC_FRAME_TYPE_NEW_CONN_ID:
414         {
415             OSSL_QUIC_FRAME_NEW_CONN_ID f;
416 
417             if (!ossl_quic_wire_decode_frame_new_conn_id(pkt, &f))
418                 goto unknown;
419 
420             QLOG_STR("frame_type", "new_connection_id");
421             QLOG_U64("sequence_number", f.seq_num);
422             QLOG_U64("retire_prior_to", f.retire_prior_to);
423             QLOG_CID("connection_id", &f.conn_id);
424             QLOG_BIN("stateless_reset_token",
425                      f.stateless_reset.token,
426                      sizeof(f.stateless_reset.token));
427         }
428         break;
429     case OSSL_QUIC_FRAME_TYPE_RETIRE_CONN_ID:
430         {
431             uint64_t seq_num;
432 
433             if (!ossl_quic_wire_decode_frame_retire_conn_id(pkt, &seq_num))
434                 goto unknown;
435 
436             QLOG_STR("frame_type", "retire_connection_id");
437             QLOG_U64("sequence_number", seq_num);
438         }
439         break;
440     case OSSL_QUIC_FRAME_TYPE_DATA_BLOCKED:
441         {
442             uint64_t x;
443 
444             if (!ossl_quic_wire_decode_frame_data_blocked(pkt, &x))
445                 goto unknown;
446 
447             QLOG_STR("frame_type", "data_blocked");
448             QLOG_U64("limit", x);
449         }
450         break;
451     case OSSL_QUIC_FRAME_TYPE_STREAM_DATA_BLOCKED:
452         {
453             uint64_t stream_id, x;
454 
455             if (!ossl_quic_wire_decode_frame_stream_data_blocked(pkt,
456                                                                  &stream_id,
457                                                                  &x))
458                 goto unknown;
459 
460             QLOG_STR("frame_type", "stream_data_blocked");
461             QLOG_U64("stream_id", stream_id);
462             QLOG_U64("limit", x);
463         }
464         break;
465     case OSSL_QUIC_FRAME_TYPE_STREAMS_BLOCKED_BIDI:
466     case OSSL_QUIC_FRAME_TYPE_STREAMS_BLOCKED_UNI:
467         {
468             uint64_t x;
469 
470             if (!ossl_quic_wire_decode_frame_streams_blocked(pkt, &x))
471                 goto unknown;
472 
473             QLOG_STR("frame_type", "streams_blocked");
474             QLOG_STR("stream_type",
475                      frame_type == OSSL_QUIC_FRAME_TYPE_STREAMS_BLOCKED_BIDI
476                         ? "bidirectional" : "unidirectional");
477             QLOG_U64("limit", x);
478         }
479         break;
480     case OSSL_QUIC_FRAME_TYPE_NEW_TOKEN:
481         {
482             const unsigned char *token;
483             size_t token_len;
484 
485             if (!ossl_quic_wire_decode_frame_new_token(pkt, &token, &token_len))
486                 goto unknown;
487 
488             QLOG_STR("frame_type", "new_token");
489             QLOG_BEGIN("token");
490                 QLOG_BEGIN("raw");
491                     QLOG_BIN("data", token, token_len);
492                 QLOG_END();
493             QLOG_END();
494         }
495         break;
496     default:
497 unknown:
498         QLOG_STR("frame_type", "unknown");
499         QLOG_U64("frame_type_value", frame_type);
500 
501         /*
502          * Can't continue scanning for frames in this case as the frame length
503          * is unknown. We log the entire body of the rest of the packet payload
504          * as the raw data of the frame.
505          */
506         QLOG_BEGIN("raw");
507             QLOG_BIN("data", PACKET_data(&orig_pkt),
508                      PACKET_remaining(&orig_pkt));
509         QLOG_END();
510         ignore_res(PACKET_forward(pkt, PACKET_remaining(pkt)));
511         break;
512     }
513 
514     return 1;
515 }
516 
log_frame(QLOG * qlog_instance,PACKET * pkt,size_t * need_skip)517 static void log_frame(QLOG *qlog_instance, PACKET *pkt,
518                       size_t *need_skip)
519 {
520     size_t rem_before, rem_after;
521 
522     rem_before = PACKET_remaining(pkt);
523 
524     if (!log_frame_actual(qlog_instance, pkt, need_skip))
525         return;
526 
527     rem_after = PACKET_remaining(pkt);
528     QLOG_U64("length", rem_before - rem_after);
529 }
530 
log_frames(QLOG * qlog_instance,const OSSL_QTX_IOVEC * iovec,size_t num_iovec)531 static int log_frames(QLOG *qlog_instance,
532                       const OSSL_QTX_IOVEC *iovec,
533                       size_t num_iovec)
534 {
535     size_t i;
536     PACKET pkt;
537     size_t need_skip = 0;
538 
539     for (i = 0; i < num_iovec; ++i) {
540         if (!PACKET_buf_init(&pkt, iovec[i].buf, iovec[i].buf_len))
541             return 0;
542 
543         while (PACKET_remaining(&pkt) > 0) {
544             if (need_skip > 0) {
545                 size_t adv = need_skip;
546 
547                 if (adv > PACKET_remaining(&pkt))
548                     adv = PACKET_remaining(&pkt);
549 
550                 if (!PACKET_forward(&pkt, adv))
551                     return 0;
552 
553                 need_skip -= adv;
554                 continue;
555             }
556 
557             QLOG_BEGIN(NULL)
558             {
559                 log_frame(qlog_instance, &pkt, &need_skip);
560             }
561             QLOG_END()
562         }
563     }
564 
565     return 1;
566 }
567 
log_packet(QLOG * qlog_instance,const QUIC_PKT_HDR * hdr,QUIC_PN pn,const OSSL_QTX_IOVEC * iovec,size_t num_iovec,uint64_t datagram_id)568 static void log_packet(QLOG *qlog_instance,
569                        const QUIC_PKT_HDR *hdr,
570                        QUIC_PN pn,
571                        const OSSL_QTX_IOVEC *iovec,
572                        size_t num_iovec,
573                        uint64_t datagram_id)
574 {
575     const char *type_s;
576 
577     QLOG_BEGIN("header")
578         type_s = quic_pkt_type_to_qlog(hdr->type);
579         if (type_s == NULL)
580             type_s = "unknown";
581 
582         QLOG_STR("packet_type", type_s);
583         if (ossl_quic_pkt_type_has_pn(hdr->type))
584             QLOG_U64("packet_number", pn);
585 
586         QLOG_CID("dcid", &hdr->dst_conn_id);
587         if (ossl_quic_pkt_type_has_scid(hdr->type))
588             QLOG_CID("scid", &hdr->src_conn_id);
589 
590         if (hdr->token_len > 0) {
591             QLOG_BEGIN("token")
592                 QLOG_BEGIN("raw")
593                     QLOG_BIN("data", hdr->token, hdr->token_len);
594                 QLOG_END()
595             QLOG_END()
596         }
597         /* TODO(QLOG FUTURE): flags, length */
598     QLOG_END()
599     QLOG_U64("datagram_id", datagram_id);
600 
601     if (ossl_quic_pkt_type_is_encrypted(hdr->type)) {
602         QLOG_BEGIN_ARRAY("frames")
603             log_frames(qlog_instance, iovec, num_iovec);
604         QLOG_END_ARRAY()
605     }
606 }
607 
608 #endif
609 
ossl_qlog_event_transport_packet_sent(QLOG * qlog,const QUIC_PKT_HDR * hdr,QUIC_PN pn,const OSSL_QTX_IOVEC * iovec,size_t num_iovec,uint64_t datagram_id)610 void ossl_qlog_event_transport_packet_sent(QLOG *qlog,
611                                            const QUIC_PKT_HDR *hdr,
612                                            QUIC_PN pn,
613                                            const OSSL_QTX_IOVEC *iovec,
614                                            size_t num_iovec,
615                                            uint64_t datagram_id)
616 {
617 #ifndef OPENSSL_NO_QLOG
618     QLOG_EVENT_BEGIN(qlog, transport, packet_sent)
619         log_packet(qlog, hdr, pn, iovec, num_iovec, datagram_id);
620     QLOG_EVENT_END()
621 #endif
622 }
623 
ossl_qlog_event_transport_packet_received(QLOG * qlog,const QUIC_PKT_HDR * hdr,QUIC_PN pn,const OSSL_QTX_IOVEC * iovec,size_t num_iovec,uint64_t datagram_id)624 void ossl_qlog_event_transport_packet_received(QLOG *qlog,
625                                                const QUIC_PKT_HDR *hdr,
626                                                QUIC_PN pn,
627                                                const OSSL_QTX_IOVEC *iovec,
628                                                size_t num_iovec,
629                                                uint64_t datagram_id)
630 {
631 #ifndef OPENSSL_NO_QLOG
632     QLOG_EVENT_BEGIN(qlog, transport, packet_received)
633         log_packet(qlog, hdr, pn, iovec, num_iovec, datagram_id);
634     QLOG_EVENT_END()
635 #endif
636 }
637