mirror of
https://github.com/openssl/openssl.git
synced 2025-01-06 13:26:43 +08:00
QUIC PORT, CHANNEL: Move ticking code into QUIC_PORT
Reviewed-by: Tomas Mraz <tomas@openssl.org> Reviewed-by: Matt Caswell <matt@openssl.org> (Merged from https://github.com/openssl/openssl/pull/22674)
This commit is contained in:
parent
4ed6b48d9d
commit
632b0c7e8c
@ -267,6 +267,13 @@ int ossl_quic_channel_on_new_conn(QUIC_CHANNEL *ch, const BIO_ADDR *peer,
|
||||
const QUIC_CONN_ID *peer_scid,
|
||||
const QUIC_CONN_ID *peer_dcid);
|
||||
|
||||
/* For use by QUIC_PORT. You should not need to call this directly. */
|
||||
void ossl_quic_channel_subtick(QUIC_CHANNEL *ch, QUIC_TICK_RESULT *r,
|
||||
uint32_t flags);
|
||||
|
||||
/* For use by QUIC_PORT only. */
|
||||
void ossl_quic_channel_raise_net_error(QUIC_CHANNEL *ch);
|
||||
|
||||
/*
|
||||
* Queries and Accessors
|
||||
* =====================
|
||||
@ -294,12 +301,6 @@ BIO *ossl_quic_channel_get_net_wbio(QUIC_CHANNEL *ch);
|
||||
int ossl_quic_channel_set_net_rbio(QUIC_CHANNEL *ch, BIO *net_rbio);
|
||||
int ossl_quic_channel_set_net_wbio(QUIC_CHANNEL *ch, BIO *net_wbio);
|
||||
|
||||
/*
|
||||
* Re-poll the network BIOs already set to determine if their support
|
||||
* for polling has changed.
|
||||
*/
|
||||
int ossl_quic_channel_update_poll_descriptors(QUIC_CHANNEL *ch);
|
||||
|
||||
/*
|
||||
* Returns an existing stream by stream ID. Returns NULL if the stream does not
|
||||
* exist.
|
||||
@ -396,9 +397,6 @@ int ossl_quic_channel_has_pending(const QUIC_CHANNEL *ch);
|
||||
/* Force transmission of an ACK-eliciting packet. */
|
||||
int ossl_quic_channel_ping(QUIC_CHANNEL *ch);
|
||||
|
||||
/* For testing use. While enabled, ticking is not performed. */
|
||||
void ossl_quic_channel_set_inhibit_tick(QUIC_CHANNEL *ch, int inhibit);
|
||||
|
||||
/*
|
||||
* These queries exist for diagnostic purposes only. They may roll over.
|
||||
* Do not rely on them for non-testing purposes.
|
||||
|
@ -97,6 +97,10 @@ BIO *ossl_quic_port_get_net_wbio(QUIC_PORT *port);
|
||||
int ossl_quic_port_set_net_rbio(QUIC_PORT *port, BIO *net_rbio);
|
||||
int ossl_quic_port_set_net_wbio(QUIC_PORT *port, BIO *net_wbio);
|
||||
|
||||
/*
|
||||
* Re-poll the network BIOs already set to determine if their support
|
||||
* for polling has changed.
|
||||
*/
|
||||
int ossl_quic_port_update_poll_descriptors(QUIC_PORT *port);
|
||||
|
||||
/* Gets the reactor which can be used to tick/poll on the port. */
|
||||
@ -114,6 +118,20 @@ OSSL_TIME ossl_quic_port_get_time(QUIC_PORT *port);
|
||||
int ossl_quic_port_get_rx_short_dcid_len(const QUIC_PORT *port);
|
||||
int ossl_quic_port_get_tx_init_dcid_len(const QUIC_PORT *port);
|
||||
|
||||
/* For testing use. While enabled, ticking is not performed. */
|
||||
void ossl_quic_port_set_inhibit_tick(QUIC_PORT *port, int inhibit);
|
||||
|
||||
/*
|
||||
* Events
|
||||
* ======
|
||||
*/
|
||||
|
||||
/*
|
||||
* Called if a permanent network error occurs. Terminates all channels
|
||||
* immediately.
|
||||
*/
|
||||
void ossl_quic_port_raise_net_error(QUIC_PORT *port);
|
||||
|
||||
# endif
|
||||
|
||||
#endif
|
||||
|
@ -48,10 +48,8 @@
|
||||
DEFINE_LIST_OF_IMPL(ch, QUIC_CHANNEL);
|
||||
|
||||
static void ch_save_err_state(QUIC_CHANNEL *ch);
|
||||
static void ch_rx_pre(QUIC_CHANNEL *ch);
|
||||
static int ch_rx(QUIC_CHANNEL *ch, int channel_only);
|
||||
static int ch_tx(QUIC_CHANNEL *ch);
|
||||
static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags);
|
||||
static int ch_tick_tls(QUIC_CHANNEL *ch, int channel_only);
|
||||
static void ch_rx_handle_packet(QUIC_CHANNEL *ch, int channel_only);
|
||||
static OSSL_TIME ch_determine_next_tick_deadline(QUIC_CHANNEL *ch);
|
||||
@ -92,7 +90,6 @@ static void ch_on_idle_timeout(QUIC_CHANNEL *ch);
|
||||
static void ch_update_idle(QUIC_CHANNEL *ch);
|
||||
static void ch_update_ping_deadline(QUIC_CHANNEL *ch);
|
||||
static void ch_stateless_reset(QUIC_CHANNEL *ch);
|
||||
static void ch_raise_net_error(QUIC_CHANNEL *ch);
|
||||
static void ch_on_terminating_timeout(QUIC_CHANNEL *ch);
|
||||
static void ch_start_terminating(QUIC_CHANNEL *ch,
|
||||
const QUIC_TERMINATE_CAUSE *tcause,
|
||||
@ -467,8 +464,6 @@ static int ch_init(QUIC_CHANNEL *ch)
|
||||
goto err;
|
||||
|
||||
ch_update_idle(ch);
|
||||
ossl_quic_reactor_init(&ch->rtor, ch_tick, ch,
|
||||
ch_determine_next_tick_deadline(ch));
|
||||
ossl_list_ch_insert_tail(&ch->port->channel_list, ch);
|
||||
ch->on_port_list = 1;
|
||||
return 1;
|
||||
@ -601,7 +596,7 @@ int ossl_quic_channel_set_peer_addr(QUIC_CHANNEL *ch, const BIO_ADDR *peer_addr)
|
||||
|
||||
QUIC_REACTOR *ossl_quic_channel_get_reactor(QUIC_CHANNEL *ch)
|
||||
{
|
||||
return &ch->rtor;
|
||||
return ossl_quic_port_get0_reactor(ch->port);
|
||||
}
|
||||
|
||||
QUIC_STREAM_MAP *ossl_quic_channel_get_qsm(QUIC_CHANNEL *ch)
|
||||
@ -1839,20 +1834,20 @@ err:
|
||||
* at least everything network I/O related. Best effort - not allowed to fail
|
||||
* "loudly".
|
||||
*/
|
||||
static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
void ossl_quic_channel_subtick(QUIC_CHANNEL *ch, QUIC_TICK_RESULT *res,
|
||||
uint32_t flags)
|
||||
{
|
||||
OSSL_TIME now, deadline;
|
||||
QUIC_CHANNEL *ch = arg;
|
||||
int channel_only = (flags & QUIC_REACTOR_TICK_FLAG_CHANNEL_ONLY) != 0;
|
||||
|
||||
/*
|
||||
* When we tick the QUIC connection, we do everything we need to do
|
||||
* periodically. In order, we:
|
||||
* periodically. Network I/O handling will already have been performed
|
||||
* as necessary by the QUIC port. Thus, in order, we:
|
||||
*
|
||||
* - handle any incoming data from the network;
|
||||
* - handle any timer events which are due to fire (ACKM, etc.)
|
||||
* - write any data to the network due to be sent, to the extent
|
||||
* possible;
|
||||
* - handle any packets the DEMUX has queued up for us;
|
||||
* - handle any timer events which are due to fire (ACKM, etc.);
|
||||
* - generate any packets which need to be sent;
|
||||
* - determine the time at which we should next be ticked.
|
||||
*/
|
||||
|
||||
@ -1880,13 +1875,10 @@ static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
}
|
||||
}
|
||||
|
||||
if (!ch->inhibit_tick) {
|
||||
if (!ch->port->inhibit_tick) {
|
||||
/* Handle RXKU timeouts. */
|
||||
ch_rxku_tick(ch);
|
||||
|
||||
/* Handle any incoming data from network. */
|
||||
ch_rx_pre(ch);
|
||||
|
||||
do {
|
||||
/* Process queued incoming packets. */
|
||||
ch->did_tls_tick = 0;
|
||||
@ -1923,7 +1915,7 @@ static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
* Idle timeout differs from normal protocol violation because we do
|
||||
* not send a CONN_CLOSE frame; go straight to TERMINATED.
|
||||
*/
|
||||
if (!ch->inhibit_tick)
|
||||
if (!ch->port->inhibit_tick)
|
||||
ch_on_idle_timeout(ch);
|
||||
|
||||
res->net_read_desired = 0;
|
||||
@ -1932,7 +1924,7 @@ static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
return;
|
||||
}
|
||||
|
||||
if (!ch->inhibit_tick) {
|
||||
if (!ch->port->inhibit_tick) {
|
||||
deadline = ossl_ackm_get_loss_detection_deadline(ch->ackm);
|
||||
if (!ossl_time_is_zero(deadline)
|
||||
&& ossl_time_compare(now, deadline) >= 0)
|
||||
@ -1954,7 +1946,7 @@ static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
ch_update_ping_deadline(ch);
|
||||
}
|
||||
|
||||
/* Write any data to the network due to be sent. */
|
||||
/* Queue any data to be sent for transmission. */
|
||||
ch_tx(ch);
|
||||
|
||||
/* Do stream GC. */
|
||||
@ -1965,14 +1957,13 @@ static void ch_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
res->tick_deadline = ch_determine_next_tick_deadline(ch);
|
||||
|
||||
/*
|
||||
* Always process network input unless we are now terminated.
|
||||
* Although we had not terminated at the beginning of this tick, network
|
||||
* errors in ch_rx_pre() or ch_tx() may have caused us to transition to the
|
||||
* Terminated state.
|
||||
* Always process network input unless we are now terminated. Although we
|
||||
* had not terminated at the beginning of this tick, network errors in
|
||||
* ch_tx() may have caused us to transition to the Terminated state.
|
||||
*/
|
||||
res->net_read_desired = !ossl_quic_channel_is_terminated(ch);
|
||||
|
||||
/* We want to write to the network if we have any in our queue. */
|
||||
/* We want to write to the network if we have any data in our TX queue. */
|
||||
res->net_write_desired
|
||||
= (!ossl_quic_channel_is_terminated(ch)
|
||||
&& ossl_qtx_get_queue_len_datagrams(ch->qtx) > 0);
|
||||
@ -2000,32 +1991,6 @@ static int ch_tick_tls(QUIC_CHANNEL *ch, int channel_only)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Process incoming datagrams, if any. */
|
||||
static void ch_rx_pre(QUIC_CHANNEL *ch)
|
||||
{
|
||||
int ret;
|
||||
|
||||
if (!ch->is_server && !ch->have_sent_any_pkt)
|
||||
return;
|
||||
|
||||
/*
|
||||
* Get DEMUX to BIO_recvmmsg from the network and queue incoming datagrams
|
||||
* to the appropriate QRX instance.
|
||||
*/
|
||||
ret = ossl_quic_demux_pump(ch->port->demux);
|
||||
if (ret == QUIC_DEMUX_PUMP_RES_STATELESS_RESET)
|
||||
ch_stateless_reset(ch);
|
||||
else if (ret == QUIC_DEMUX_PUMP_RES_PERMANENT_FAIL)
|
||||
/*
|
||||
* We don't care about transient failure, but permanent failure means we
|
||||
* should tear down the connection as though a protocol violation
|
||||
* occurred. Skip straight to the Terminating state as there is no point
|
||||
* trying to send CONNECTION_CLOSE frames if the network BIO is not
|
||||
* operating correctly.
|
||||
*/
|
||||
ch_raise_net_error(ch);
|
||||
}
|
||||
|
||||
/* Check incoming forged packet limit and terminate connection if needed. */
|
||||
static void ch_rx_check_forged_pkt_limit(QUIC_CHANNEL *ch)
|
||||
{
|
||||
@ -2508,7 +2473,7 @@ static int ch_tx(QUIC_CHANNEL *ch)
|
||||
case QTX_FLUSH_NET_RES_PERMANENT_FAIL:
|
||||
default:
|
||||
/* Permanent underlying network BIO, start terminating. */
|
||||
ch_raise_net_error(ch);
|
||||
ossl_quic_port_raise_net_error(ch->port);
|
||||
break;
|
||||
}
|
||||
|
||||
@ -2571,91 +2536,14 @@ static OSSL_TIME ch_determine_next_tick_deadline(QUIC_CHANNEL *ch)
|
||||
* =======================================
|
||||
*/
|
||||
|
||||
/* Determines whether we can support a given poll descriptor. */
|
||||
static int validate_poll_descriptor(const BIO_POLL_DESCRIPTOR *d)
|
||||
{
|
||||
if (d->type == BIO_POLL_DESCRIPTOR_TYPE_SOCK_FD && d->value.fd < 0) {
|
||||
ERR_raise(ERR_LIB_SSL, ERR_R_PASSED_INVALID_ARGUMENT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
BIO *ossl_quic_channel_get_net_rbio(QUIC_CHANNEL *ch)
|
||||
{
|
||||
return ch->net_rbio;
|
||||
}
|
||||
|
||||
BIO *ossl_quic_channel_get_net_wbio(QUIC_CHANNEL *ch)
|
||||
{
|
||||
return ch->net_wbio;
|
||||
}
|
||||
|
||||
static int ch_update_poll_desc(QUIC_CHANNEL *ch, BIO *net_bio, int for_write)
|
||||
{
|
||||
BIO_POLL_DESCRIPTOR d = {0};
|
||||
|
||||
if (net_bio == NULL
|
||||
|| (!for_write && !BIO_get_rpoll_descriptor(net_bio, &d))
|
||||
|| (for_write && !BIO_get_wpoll_descriptor(net_bio, &d)))
|
||||
/* Non-pollable BIO */
|
||||
d.type = BIO_POLL_DESCRIPTOR_TYPE_NONE;
|
||||
|
||||
if (!validate_poll_descriptor(&d))
|
||||
return 0;
|
||||
|
||||
if (for_write)
|
||||
ossl_quic_reactor_set_poll_w(&ch->rtor, &d);
|
||||
else
|
||||
ossl_quic_reactor_set_poll_r(&ch->rtor, &d);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int ossl_quic_channel_update_poll_descriptors(QUIC_CHANNEL *ch)
|
||||
{
|
||||
int ok = 1;
|
||||
|
||||
if (!ch_update_poll_desc(ch, ch->net_rbio, /*for_write=*/0))
|
||||
ok = 0;
|
||||
|
||||
if (!ch_update_poll_desc(ch, ch->net_wbio, /*for_write=*/1))
|
||||
ok = 0;
|
||||
|
||||
return ok;
|
||||
}
|
||||
|
||||
/*
|
||||
* QUIC_CHANNEL does not ref any BIO it is provided with, nor is any ref
|
||||
* transferred to it. The caller (i.e., QUIC_CONNECTION) is responsible for
|
||||
* ensuring the BIO lasts until the channel is freed or the BIO is switched out
|
||||
* for another BIO by a subsequent successful call to this function.
|
||||
*/
|
||||
int ossl_quic_channel_set_net_rbio(QUIC_CHANNEL *ch, BIO *net_rbio)
|
||||
{
|
||||
if (ch->net_rbio == net_rbio)
|
||||
return 1;
|
||||
|
||||
if (!ch_update_poll_desc(ch, net_rbio, /*for_write=*/0))
|
||||
return 0;
|
||||
|
||||
ossl_quic_demux_set_bio(ch->port->demux, net_rbio);
|
||||
ch->net_rbio = net_rbio;
|
||||
return 1;
|
||||
return ossl_quic_port_set_net_rbio(ch->port, net_rbio);
|
||||
}
|
||||
|
||||
int ossl_quic_channel_set_net_wbio(QUIC_CHANNEL *ch, BIO *net_wbio)
|
||||
{
|
||||
if (ch->net_wbio == net_wbio)
|
||||
return 1;
|
||||
|
||||
if (!ch_update_poll_desc(ch, net_wbio, /*for_write=*/1))
|
||||
return 0;
|
||||
|
||||
ossl_qtx_set_bio(ch->qtx, net_wbio);
|
||||
ch->net_wbio = net_wbio;
|
||||
return 1;
|
||||
return ossl_quic_port_set_net_wbio(ch->port, net_wbio);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2695,7 +2583,7 @@ int ossl_quic_channel_start(QUIC_CHANNEL *ch)
|
||||
if (!ch_tick_tls(ch, /*channel_only=*/0))
|
||||
return 0;
|
||||
|
||||
ossl_quic_reactor_tick(&ch->rtor, 0); /* best effort */
|
||||
ossl_quic_reactor_tick(ossl_quic_port_get0_reactor(ch->port), 0); /* best effort */
|
||||
return 1;
|
||||
}
|
||||
|
||||
@ -3199,7 +3087,7 @@ static void ch_save_err_state(QUIC_CHANNEL *ch)
|
||||
OSSL_ERR_STATE_save(ch->err_state);
|
||||
}
|
||||
|
||||
static void ch_stateless_reset(QUIC_CHANNEL *ch)
|
||||
static void ossl_unused ch_stateless_reset(QUIC_CHANNEL *ch)
|
||||
{
|
||||
QUIC_TERMINATE_CAUSE tcause = {0};
|
||||
|
||||
@ -3207,7 +3095,7 @@ static void ch_stateless_reset(QUIC_CHANNEL *ch)
|
||||
ch_start_terminating(ch, &tcause, 1);
|
||||
}
|
||||
|
||||
static void ch_raise_net_error(QUIC_CHANNEL *ch)
|
||||
void ossl_quic_channel_raise_net_error(QUIC_CHANNEL *ch)
|
||||
{
|
||||
QUIC_TERMINATE_CAUSE tcause = {0};
|
||||
|
||||
@ -3698,11 +3586,6 @@ int ossl_quic_channel_ping(QUIC_CHANNEL *ch)
|
||||
return 1;
|
||||
}
|
||||
|
||||
void ossl_quic_channel_set_inhibit_tick(QUIC_CHANNEL *ch, int inhibit)
|
||||
{
|
||||
ch->inhibit_tick = (inhibit != 0);
|
||||
}
|
||||
|
||||
uint16_t ossl_quic_channel_get_diag_num_rx_ack(QUIC_CHANNEL *ch)
|
||||
{
|
||||
return ch->diag_num_rx_ack;
|
||||
|
@ -58,15 +58,9 @@ struct quic_channel_st {
|
||||
*/
|
||||
unsigned char *local_transport_params;
|
||||
|
||||
/* Asynchronous I/O reactor. */
|
||||
QUIC_REACTOR rtor;
|
||||
|
||||
/* Our current L4 peer address, if any. */
|
||||
BIO_ADDR cur_peer_addr;
|
||||
|
||||
/* Network-side read and write BIOs. */
|
||||
BIO *net_rbio, *net_wbio;
|
||||
|
||||
/*
|
||||
* Subcomponents of the connection. All of these components are instantiated
|
||||
* and owned by us.
|
||||
@ -442,9 +436,6 @@ struct quic_channel_st {
|
||||
*/
|
||||
unsigned int protocol_error : 1;
|
||||
|
||||
/* Inhibit tick for testing purposes? */
|
||||
unsigned int inhibit_tick : 1;
|
||||
|
||||
/* Are we using addressed mode? */
|
||||
unsigned int addressed_mode : 1;
|
||||
|
||||
|
@ -64,7 +64,7 @@ static int block_until_pred(QUIC_CONNECTION *qc,
|
||||
* Any attempt to block auto-disables tick inhibition as otherwise we will
|
||||
* hang around forever.
|
||||
*/
|
||||
ossl_quic_channel_set_inhibit_tick(qc->ch, 0);
|
||||
ossl_quic_port_set_inhibit_tick(qc->port, 0);
|
||||
|
||||
rtor = ossl_quic_channel_get_reactor(qc->ch);
|
||||
return ossl_quic_reactor_block_until_pred(rtor, pred, pred_arg, flags,
|
||||
@ -856,7 +856,7 @@ static int qc_can_support_blocking_cached(QUIC_CONNECTION *qc)
|
||||
|
||||
static void qc_update_can_support_blocking(QUIC_CONNECTION *qc)
|
||||
{
|
||||
ossl_quic_channel_update_poll_descriptors(qc->ch); /* best effort */
|
||||
ossl_quic_port_update_poll_descriptors(qc->port); /* best effort */
|
||||
}
|
||||
|
||||
static void qc_update_blocking_mode(QUIC_CONNECTION *qc)
|
||||
|
@ -24,6 +24,7 @@ static void port_cleanup(QUIC_PORT *port);
|
||||
static OSSL_TIME get_time(void *arg);
|
||||
static void port_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags);
|
||||
static void port_default_packet_handler(QUIC_URXE *e, void *arg);
|
||||
static void port_rx_pre(QUIC_PORT *port);
|
||||
|
||||
DEFINE_LIST_OF_IMPL(ch, QUIC_CHANNEL);
|
||||
|
||||
@ -217,13 +218,17 @@ int ossl_quic_port_set_net_rbio(QUIC_PORT *port, BIO *net_rbio)
|
||||
|
||||
int ossl_quic_port_set_net_wbio(QUIC_PORT *port, BIO *net_wbio)
|
||||
{
|
||||
QUIC_CHANNEL *ch;
|
||||
|
||||
if (port->net_wbio == net_wbio)
|
||||
return 1;
|
||||
|
||||
if (!port_update_poll_desc(port, net_wbio, /*for_write=*/1))
|
||||
return 0;
|
||||
|
||||
//ossl_qtx_set_bio(port->qtx, net_wbio);
|
||||
LIST_FOREACH(ch, ch, &port->channel_list)
|
||||
ossl_qtx_set_bio(ch->qtx, net_wbio);
|
||||
|
||||
port->net_wbio = net_wbio;
|
||||
return 1;
|
||||
}
|
||||
@ -301,7 +306,49 @@ QUIC_CHANNEL *ossl_quic_port_create_incoming(QUIC_PORT *port, SSL *tls)
|
||||
*/
|
||||
static void port_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags)
|
||||
{
|
||||
/* TODO */
|
||||
QUIC_PORT *port = arg;
|
||||
QUIC_CHANNEL *ch;
|
||||
|
||||
res->net_read_desired = 0;
|
||||
res->net_write_desired = 0;
|
||||
res->tick_deadline = ossl_time_infinite();
|
||||
|
||||
if (!port->inhibit_tick) {
|
||||
/* Handle any incoming data from network. */
|
||||
port_rx_pre(port);
|
||||
|
||||
/* Iterate through all channels and service them. */
|
||||
LIST_FOREACH(ch, ch, &port->channel_list) {
|
||||
QUIC_TICK_RESULT subr = {0};
|
||||
|
||||
ossl_quic_channel_subtick(ch, &subr, flags);
|
||||
ossl_quic_tick_result_merge_into(res, &subr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Process incoming datagrams, if any. */
|
||||
static void port_rx_pre(QUIC_PORT *port)
|
||||
{
|
||||
int ret;
|
||||
|
||||
// TODO !have_sent_any_pkt
|
||||
|
||||
/*
|
||||
* Get DEMUX to BIO_recvmmsg from the network and queue incoming datagrams
|
||||
* to the appropriate QRX instances.
|
||||
*/
|
||||
ret = ossl_quic_demux_pump(port->demux);
|
||||
// TODO: handle ret, stateless reset
|
||||
|
||||
if (ret == QUIC_DEMUX_PUMP_RES_PERMANENT_FAIL)
|
||||
/*
|
||||
* We don't care about transient failure, but permanent failure means we
|
||||
* should tear down the port. All connections skip straight to the
|
||||
* Terminated state as there is no point trying to send CONNECTION_CLOSE
|
||||
* frames if the network BIO is not operating correctly.
|
||||
*/
|
||||
ossl_quic_port_raise_net_error(port);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -336,9 +383,17 @@ static void port_default_packet_handler(QUIC_URXE *e, void *arg)
|
||||
QUIC_PKT_HDR hdr;
|
||||
QUIC_CHANNEL *new_ch = NULL;
|
||||
|
||||
// TODO review this
|
||||
if (port->tserver_ch == NULL)
|
||||
goto undesirable;
|
||||
|
||||
// TODO allow_incoming
|
||||
//if (!ossl_assert(ch->is_server))
|
||||
// goto undesirable;
|
||||
|
||||
//TODO if (ch->state != QUIC_CHANNEL_STATE_IDLE)
|
||||
// goto undesirable;
|
||||
|
||||
/*
|
||||
* We have got a packet for an unknown DCID. This might be an attempt to
|
||||
* open a new connection.
|
||||
@ -395,3 +450,18 @@ static void port_default_packet_handler(QUIC_URXE *e, void *arg)
|
||||
undesirable:
|
||||
ossl_quic_demux_release_urxe(port->demux, e);
|
||||
}
|
||||
|
||||
void ossl_quic_port_set_inhibit_tick(QUIC_PORT *port, int inhibit)
|
||||
{
|
||||
port->inhibit_tick = (inhibit != 0);
|
||||
}
|
||||
|
||||
void ossl_quic_port_raise_net_error(QUIC_PORT *port)
|
||||
{
|
||||
QUIC_CHANNEL *ch;
|
||||
|
||||
// TODO fsm
|
||||
|
||||
LIST_FOREACH(ch, ch, &port->channel_list)
|
||||
ossl_quic_channel_raise_net_error(ch);
|
||||
}
|
||||
|
@ -59,6 +59,9 @@ struct quic_port_st {
|
||||
|
||||
/* Is this port created to support multiple connections? */
|
||||
unsigned int is_multi_conn : 1;
|
||||
|
||||
/* Inhibit tick for testing purposes? */
|
||||
unsigned int inhibit_tick : 1;
|
||||
};
|
||||
|
||||
# endif
|
||||
|
@ -14,6 +14,7 @@
|
||||
#include "internal/quic_ssl.h"
|
||||
#include "internal/quic_error.h"
|
||||
#include "internal/quic_stream_map.h"
|
||||
#include "internal/quic_port.h"
|
||||
#include "testutil.h"
|
||||
#include "helpers/quictestlib.h"
|
||||
#if defined(OPENSSL_THREADS)
|
||||
@ -1594,7 +1595,7 @@ static int run_script_worker(struct helper *h, const struct script_op *script,
|
||||
QUIC_CHANNEL *ch = ossl_quic_conn_get_channel(h->c_conn);
|
||||
SSL_SHUTDOWN_EX_ARGS args = {0};
|
||||
|
||||
ossl_quic_channel_set_inhibit_tick(ch, 0);
|
||||
ossl_quic_port_set_inhibit_tick(ossl_quic_channel_get0_port(ch), 0);
|
||||
|
||||
if (!TEST_ptr(c_tgt))
|
||||
goto out;
|
||||
@ -1918,7 +1919,8 @@ static int run_script_worker(struct helper *h, const struct script_op *script,
|
||||
{
|
||||
QUIC_CHANNEL *ch = ossl_quic_conn_get_channel(h->c_conn);
|
||||
|
||||
ossl_quic_channel_set_inhibit_tick(ch, op->arg1);
|
||||
ossl_quic_port_set_inhibit_tick(ossl_quic_channel_get0_port(ch),
|
||||
op->arg1);
|
||||
}
|
||||
break;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user