summaryrefslogtreecommitdiffstats
path: root/ssl
diff options
context:
space:
mode:
authorHugo Landau <hlandau@openssl.org>2023-09-08 12:43:04 +0100
committerHugo Landau <hlandau@openssl.org>2024-02-02 11:49:34 +0000
commit8fbac4d70eff157b081933bee88fabedfec47b0b (patch)
tree7431119ed886984fe2df72cce9028c0904ab964b /ssl
parent4cecbc5400aa2f8172865b368b41c3df50b5a64d (diff)
QLOG: Events: Implement connectivity:connection_state_updated
Reviewed-by: Matt Caswell <matt@openssl.org> Reviewed-by: Neil Horman <nhorman@openssl.org> (Merged from https://github.com/openssl/openssl/pull/22037)
Diffstat (limited to 'ssl')
-rw-r--r--ssl/quic/qlog_event_helpers.c50
-rw-r--r--ssl/quic/quic_channel.c36
2 files changed, 79 insertions, 7 deletions
diff --git a/ssl/quic/qlog_event_helpers.c b/ssl/quic/qlog_event_helpers.c
index 0cbd616096..66157fe444 100644
--- a/ssl/quic/qlog_event_helpers.c
+++ b/ssl/quic/qlog_event_helpers.c
@@ -21,3 +21,53 @@ void ossl_qlog_event_connectivity_connection_started(QLOG *qlog,
QLOG_EVENT_END()
#endif
}
+
+#ifndef OPENSSL_NO_QLOG
+static const char *map_state_to_qlog(uint32_t state,
+ int handshake_complete,
+ int handshake_confirmed)
+{
+ switch (state) {
+ default:
+ case QUIC_CHANNEL_STATE_IDLE:
+ return NULL;
+
+ case QUIC_CHANNEL_STATE_ACTIVE:
+ if (handshake_confirmed)
+ return "handshake_confirmed";
+ else if (handshake_complete)
+ return "handshake_complete";
+ else
+ return "attempted";
+
+ case QUIC_CHANNEL_STATE_TERMINATING_CLOSING:
+ return "closing";
+
+ case QUIC_CHANNEL_STATE_TERMINATING_DRAINING:
+ return "draining";
+
+ case QUIC_CHANNEL_STATE_TERMINATED:
+ return "closed";
+ }
+}
+#endif
+
+void ossl_qlog_event_connectivity_connection_state_updated(QLOG *qlog,
+ uint32_t old_state,
+ uint32_t new_state,
+ int handshake_complete,
+ int handshake_confirmed)
+{
+#ifndef OPENSSL_NO_QLOG
+ const char *state_s;
+
+ QLOG_EVENT_BEGIN(qlog, connectivity, connection_state_updated)
+ state_s = map_state_to_qlog(new_state,
+ handshake_complete,
+ handshake_confirmed);
+
+ if (state_s != NULL)
+ QLOG_STR("state", state_s);
+ QLOG_EVENT_END()
+#endif
+}
diff --git a/ssl/quic/quic_channel.c b/ssl/quic/quic_channel.c
index 5b1610ee40..b11cfe8c69 100644
--- a/ssl/quic/quic_channel.c
+++ b/ssl/quic/quic_channel.c
@@ -101,6 +101,7 @@ static void ch_on_txp_ack_tx(const OSSL_QUIC_FRAME_ACK *ack, uint32_t pn_space,
void *arg);
static void ch_rx_handle_version_neg(QUIC_CHANNEL *ch, OSSL_QRX_PKT *pkt);
static void ch_raise_version_neg_failure(QUIC_CHANNEL *ch);
+static void ch_record_state_transition(QUIC_CHANNEL *ch, uint32_t new_state);
DEFINE_LHASH_OF_EX(QUIC_SRT_ELEM);
@@ -1032,6 +1033,7 @@ static int ch_on_handshake_complete(void *arg)
ossl_quic_tx_packetiser_schedule_handshake_done(ch->txp);
}
+ ch_record_state_transition(ch, ch->state);
return 1;
}
@@ -2423,6 +2425,24 @@ static OSSL_TIME ch_determine_next_tick_deadline(QUIC_CHANNEL *ch)
* QUIC Channel: Lifecycle Events
* ==============================
*/
+
+/*
+ * Record a state transition. This is not necessarily a change to ch->state but
+ * also includes the handshake becoming complete or confirmed, etc.
+ */
+static void ch_record_state_transition(QUIC_CHANNEL *ch, uint32_t new_state)
+{
+ uint32_t old_state = ch->state;
+
+ ch->state = new_state;
+
+ ossl_qlog_event_connectivity_connection_state_updated(ch_get_qlog(ch),
+ old_state,
+ new_state,
+ ch->handshake_complete,
+ ch->handshake_confirmed);
+}
+
int ossl_quic_channel_start(QUIC_CHANNEL *ch)
{
if (ch->is_server)
@@ -2449,7 +2469,7 @@ int ossl_quic_channel_start(QUIC_CHANNEL *ch)
return 0;
/* Change state. */
- ch->state = QUIC_CHANNEL_STATE_ACTIVE;
+ ch_record_state_transition(ch, QUIC_CHANNEL_STATE_ACTIVE);
ch->doing_proactive_ver_neg = 0; /* not currently supported */
ossl_qlog_event_connectivity_connection_started(ch_get_qlog(ch),
@@ -2612,6 +2632,7 @@ int ossl_quic_channel_on_handshake_confirmed(QUIC_CHANNEL *ch)
ch_discard_el(ch, QUIC_ENC_LEVEL_HANDSHAKE);
ch->handshake_confirmed = 1;
+ ch_record_state_transition(ch, ch->state);
ossl_ackm_on_handshake_confirmed(ch->ackm);
return 1;
}
@@ -2711,8 +2732,9 @@ static void ch_start_terminating(QUIC_CHANNEL *ch,
copy_tcause(&ch->terminate_cause, tcause);
if (!force_immediate) {
- ch->state = tcause->remote ? QUIC_CHANNEL_STATE_TERMINATING_DRAINING
- : QUIC_CHANNEL_STATE_TERMINATING_CLOSING;
+ ch_record_state_transition(ch, tcause->remote
+ ? QUIC_CHANNEL_STATE_TERMINATING_DRAINING
+ : QUIC_CHANNEL_STATE_TERMINATING_CLOSING);
/*
* RFC 9000 s. 10.2 Immediate Close
* These states SHOULD persist for at least three times
@@ -2757,7 +2779,7 @@ static void ch_start_terminating(QUIC_CHANNEL *ch,
* closing state if it receives a CONNECTION_CLOSE frame,
* which indicates that the peer is also closing or draining.
*/
- ch->state = QUIC_CHANNEL_STATE_TERMINATING_DRAINING;
+ ch_record_state_transition(ch, QUIC_CHANNEL_STATE_TERMINATING_DRAINING);
break;
@@ -3091,7 +3113,7 @@ void ossl_quic_channel_raise_protocol_error_loc(QUIC_CHANNEL *ch,
*/
static void ch_on_terminating_timeout(QUIC_CHANNEL *ch)
{
- ch->state = QUIC_CHANNEL_STATE_TERMINATED;
+ ch_record_state_transition(ch, QUIC_CHANNEL_STATE_TERMINATED);
}
/*
@@ -3166,7 +3188,7 @@ static void ch_on_idle_timeout(QUIC_CHANNEL *ch)
ch->terminate_cause.error_code = UINT64_MAX;
ch->terminate_cause.frame_type = 0;
- ch->state = QUIC_CHANNEL_STATE_TERMINATED;
+ ch_record_state_transition(ch, QUIC_CHANNEL_STATE_TERMINATED);
}
/* Called when we, as a server, get a new incoming connection. */
@@ -3210,7 +3232,7 @@ int ossl_quic_channel_on_new_conn(QUIC_CHANNEL *ch, const BIO_ADDR *peer,
return 0;
/* Change state. */
- ch->state = QUIC_CHANNEL_STATE_ACTIVE;
+ ch_record_state_transition(ch, QUIC_CHANNEL_STATE_ACTIVE);
ch->doing_proactive_ver_neg = 0; /* not currently supported */
return 1;
}