Roman Arutyunyan
November 25, 2021 09:22AM
# HG changeset patch
# User Roman Arutyunyan <arut@nginx.com>
# Date 1637693300 -10800
# Tue Nov 23 21:48:20 2021 +0300
# Branch quic
# Node ID 3d2354bfa1a2a257b9f73772ad0836585be85a6c
# Parent 5b03ffd757804542daec73188a509b02e6b2c596
QUIC: simplified stream initialization.

After creation, a client stream is added to qc->streams.uninitialized queue.
After initialization it's removed from the queue. If a stream is never
initialized, it is freed in ngx_quic_close_streams(). Stream initializer
is now set as read event handler in stream connection.

Previously qc->streams.uninitialized was used for delayed stream
initialization.

The change makes is possible not to handle separately the case of a new stream
in stream-related frame handlers. It makes these handlers simpler since new
streams and existing streams are now handled by the same code.

diff --git a/src/event/quic/ngx_event_quic_streams.c b/src/event/quic/ngx_event_quic_streams.c
--- a/src/event/quic/ngx_event_quic_streams.c
+++ b/src/event/quic/ngx_event_quic_streams.c
@@ -13,10 +13,9 @@
#define NGX_QUIC_STREAM_GONE (void *) -1


-static ngx_quic_stream_t *ngx_quic_create_client_stream(ngx_connection_t *c,
- uint64_t id);
+static ngx_quic_stream_t *ngx_quic_get_stream(ngx_connection_t *c, uint64_t id);
static ngx_int_t ngx_quic_reject_stream(ngx_connection_t *c, uint64_t id);
-static ngx_int_t ngx_quic_init_stream(ngx_quic_stream_t *qs);
+static void ngx_quic_init_stream_handler(ngx_event_t *ev);
static void ngx_quic_init_streams_handler(ngx_connection_t *c);
static ngx_quic_stream_t *ngx_quic_create_stream(ngx_connection_t *c,
uint64_t id);
@@ -306,21 +305,28 @@ ngx_quic_shutdown_stream(ngx_connection_


static ngx_quic_stream_t *
-ngx_quic_create_client_stream(ngx_connection_t *c, uint64_t id)
+ngx_quic_get_stream(ngx_connection_t *c, uint64_t id)
{
uint64_t min_id;
+ ngx_event_t *rev;
ngx_quic_stream_t *qs;
ngx_quic_connection_t *qc;

- ngx_log_debug1(NGX_LOG_DEBUG_EVENT, c->log, 0,
- "quic stream id:0x%xL is new", id);
+ qc = ngx_quic_get_connection(c);
+
+ qs = ngx_quic_find_stream(&qc->streams.tree, id);

- qc = ngx_quic_get_connection(c);
+ if (qs) {
+ return qs;
+ }

if (qc->shutdown || qc->closing) {
return NGX_QUIC_STREAM_GONE;
}

+ ngx_log_debug1(NGX_LOG_DEBUG_EVENT, c->log, 0,
+ "quic stream id:0x%xL is missing", id);
+
if (id & NGX_QUIC_STREAM_UNIDIRECTIONAL) {

if (id & NGX_QUIC_STREAM_SERVER_INITIATED) {
@@ -377,7 +383,11 @@ ngx_quic_create_client_stream(ngx_connec
* streams of that type with lower-numbered stream IDs also being opened.
*/

- for ( /* void */ ; min_id < id; min_id += 0x04) {
+#if (NGX_SUPPRESS_WARN)
+ qs = NULL;
+#endif
+
+ for ( /* void */ ; min_id <= id; min_id += 0x04) {

qs = ngx_quic_create_stream(c, min_id);

@@ -389,22 +399,17 @@ ngx_quic_create_client_stream(ngx_connec
continue;
}

- if (ngx_quic_init_stream(qs) != NGX_OK) {
- return NULL;
- }
+ ngx_queue_insert_tail(&qc->streams.uninitialized, &qs->queue);

- if (qc->shutdown || qc->closing) {
- return NGX_QUIC_STREAM_GONE;
+ rev = qs->connection->read;
+ rev->handler = ngx_quic_init_stream_handler;
+
+ if (qc->streams.initialized) {
+ ngx_post_event(rev, &ngx_posted_events);
}
}

- qs = ngx_quic_create_stream(c, id);
-
if (qs == NULL) {
- if (ngx_quic_reject_stream(c, id) != NGX_OK) {
- return NULL;
- }
-
return NGX_QUIC_STREAM_GONE;
}

@@ -461,29 +466,20 @@ ngx_quic_reject_stream(ngx_connection_t
}


-static ngx_int_t
-ngx_quic_init_stream(ngx_quic_stream_t *qs)
+static void
+ngx_quic_init_stream_handler(ngx_event_t *ev)
{
- ngx_connection_t *c;
- ngx_quic_connection_t *qc;
-
- qc = ngx_quic_get_connection(qs->parent);
+ ngx_connection_t *c;
+ ngx_quic_stream_t *qs;

- c = qs->connection;
-
- if (!qc->streams.initialized) {
- ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0,
- "quic postpone stream init");
-
- ngx_queue_insert_tail(&qc->streams.uninitialized, &qs->queue);
- return NGX_OK;
- }
+ c = ev->data;
+ qs = c->quic;

ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0, "quic init stream");

- c->listening->handler(c);
+ ngx_queue_remove(&qs->queue);

- return NGX_OK;
+ c->listening->handler(c);
}


@@ -527,16 +523,12 @@ ngx_quic_init_streams_handler(ngx_connec

qc = ngx_quic_get_connection(c);

- while (!ngx_queue_empty(&qc->streams.uninitialized)) {
- q = ngx_queue_head(&qc->streams.uninitialized);
- ngx_queue_remove(q);
-
+ for (q = ngx_queue_head(&qc->streams.uninitialized);
+ q != ngx_queue_sentinel(&qc->streams.uninitialized);
+ q = ngx_queue_next(q))
+ {
qs = ngx_queue_data(q, ngx_quic_stream_t, queue);
-
- ngx_log_debug0(NGX_LOG_DEBUG_EVENT, qs->connection->log, 0,
- "quic init postponed stream");
-
- qs->connection->listening->handler(qs->connection);
+ ngx_post_event(qs->connection->read, &ngx_posted_events);
}

qc->streams.initialized = 1;
@@ -1015,7 +1007,6 @@ ngx_quic_handle_stream_frame(ngx_connect
ngx_quic_frame_t *frame)
{
uint64_t last;
- ngx_pool_t *pool;
ngx_event_t *rev;
ngx_connection_t *sc;
ngx_quic_stream_t *qs;
@@ -1035,39 +1026,14 @@ ngx_quic_handle_stream_frame(ngx_connect
/* no overflow since both values are 62-bit */
last = f->offset + f->length;

- qs = ngx_quic_find_stream(&qc->streams.tree, f->stream_id);
+ qs = ngx_quic_get_stream(c, f->stream_id);

if (qs == NULL) {
- qs = ngx_quic_create_client_stream(c, f->stream_id);
-
- if (qs == NULL) {
- return NGX_ERROR;
- }
-
- if (qs == NGX_QUIC_STREAM_GONE) {
- return NGX_OK;
- }
-
- sc = qs->connection;
+ return NGX_ERROR;
+ }

- if (ngx_quic_control_flow(sc, last) != NGX_OK) {
- goto cleanup;
- }
-
- if (f->fin) {
- sc->read->pending_eof = 1;
- qs->final_size = last;
- }
-
- if (f->offset == 0) {
- sc->read->ready = 1;
- }
-
- if (ngx_quic_order_bufs(c, &qs->in, frame->data, f->offset) != NGX_OK) {
- goto cleanup;
- }
-
- return ngx_quic_init_stream(qs);
+ if (qs == NGX_QUIC_STREAM_GONE) {
+ return NGX_OK;
}

sc = qs->connection;
@@ -1127,15 +1093,6 @@ ngx_quic_handle_stream_frame(ngx_connect
}

return NGX_OK;
-
-cleanup:
-
- pool = sc->pool;
-
- ngx_close_connection(sc);
- ngx_destroy_pool(pool);
-
- return NGX_ERROR;
}


@@ -1212,20 +1169,14 @@ ngx_quic_handle_stream_data_blocked_fram
return NGX_ERROR;
}

- qs = ngx_quic_find_stream(&qc->streams.tree, f->id);
+ qs = ngx_quic_get_stream(c, f->id);

if (qs == NULL) {
- qs = ngx_quic_create_client_stream(c, f->id);
-
- if (qs == NULL) {
- return NGX_ERROR;
- }
+ return NGX_ERROR;
+ }

- if (qs == NGX_QUIC_STREAM_GONE) {
- return NGX_OK;
- }
-
- return ngx_quic_init_stream(qs);
+ if (qs == NGX_QUIC_STREAM_GONE) {
+ return NGX_OK;
}

return ngx_quic_update_max_stream_data(qs->connection);
@@ -1250,24 +1201,14 @@ ngx_quic_handle_max_stream_data_frame(ng
return NGX_ERROR;
}

- qs = ngx_quic_find_stream(&qc->streams.tree, f->id);
+ qs = ngx_quic_get_stream(c, f->id);

if (qs == NULL) {
- qs = ngx_quic_create_client_stream(c, f->id);
-
- if (qs == NULL) {
- return NGX_ERROR;
- }
+ return NGX_ERROR;
+ }

- if (qs == NGX_QUIC_STREAM_GONE) {
- return NGX_OK;
- }
-
- if (f->limit > qs->send_max_data) {
- qs->send_max_data = f->limit;
- }
-
- return ngx_quic_init_stream(qs);
+ if (qs == NGX_QUIC_STREAM_GONE) {
+ return NGX_OK;
}

if (f->limit <= qs->send_max_data) {
@@ -1295,7 +1236,6 @@ ngx_int_t
ngx_quic_handle_reset_stream_frame(ngx_connection_t *c,
ngx_quic_header_t *pkt, ngx_quic_reset_stream_frame_t *f)
{
- ngx_pool_t *pool;
ngx_event_t *rev;
ngx_connection_t *sc;
ngx_quic_stream_t *qs;
@@ -1310,36 +1250,14 @@ ngx_quic_handle_reset_stream_frame(ngx_c
return NGX_ERROR;
}

- qs = ngx_quic_find_stream(&qc->streams.tree, f->id);
+ qs = ngx_quic_get_stream(c, f->id);

if (qs == NULL) {
- qs = ngx_quic_create_client_stream(c, f->id);
-
- if (qs == NULL) {
- return NGX_ERROR;
- }
-
- if (qs == NGX_QUIC_STREAM_GONE) {
- return NGX_OK;
- }
-
- sc = qs->connection;
+ return NGX_ERROR;
+ }

- rev = sc->read;
- rev->error = 1;
- rev->ready = 1;
-
- if (ngx_quic_control_flow(sc, f->final_size) != NGX_OK) {
- goto cleanup;
- }
-
- qs->final_size = f->final_size;
-
- if (ngx_quic_update_flow(sc, qs->final_size) != NGX_OK) {
- goto cleanup;
- }
-
- return ngx_quic_init_stream(qs);
+ if (qs == NGX_QUIC_STREAM_GONE) {
+ return NGX_OK;
}

sc = qs->connection;
@@ -1373,15 +1291,6 @@ ngx_quic_handle_reset_stream_frame(ngx_c
}

return NGX_OK;
-
-cleanup:
-
- pool = sc->pool;
-
- ngx_close_connection(sc);
- ngx_destroy_pool(pool);
-
- return NGX_ERROR;
}


@@ -1389,9 +1298,7 @@ ngx_int_t
ngx_quic_handle_stop_sending_frame(ngx_connection_t *c,
ngx_quic_header_t *pkt, ngx_quic_stop_sending_frame_t *f)
{
- ngx_pool_t *pool;
ngx_event_t *wev;
- ngx_connection_t *sc;
ngx_quic_stream_t *qs;
ngx_quic_connection_t *qc;

@@ -1404,31 +1311,14 @@ ngx_quic_handle_stop_sending_frame(ngx_c
return NGX_ERROR;
}

- qs = ngx_quic_find_stream(&qc->streams.tree, f->id);
+ qs = ngx_quic_get_stream(c, f->id);

if (qs == NULL) {
- qs = ngx_quic_create_client_stream(c, f->id);
-
- if (qs == NULL) {
- return NGX_ERROR;
- }
-
- if (qs == NGX_QUIC_STREAM_GONE) {
- return NGX_OK;
- }
+ return NGX_ERROR;
+ }

- sc = qs->connection;
-
- if (ngx_quic_reset_stream(sc, f->error_code) != NGX_OK) {
- pool = sc->pool;
-
- ngx_close_connection(sc);
- ngx_destroy_pool(pool);
-
- return NGX_ERROR;
- }
-
- return ngx_quic_init_stream(qs);
+ if (qs == NGX_QUIC_STREAM_GONE) {
+ return NGX_OK;
}

if (ngx_quic_reset_stream(qs->connection, f->error_code) != NGX_OK) {
_______________________________________________
nginx-devel mailing list
nginx-devel@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-devel
Subject Author Views Posted

[PATCH 0 of 3] Misc QUIC stream patches

Roman Arutyunyan 379 November 25, 2021 09:22AM

[PATCH 1 of 3] QUIC: post stream events instead of calling their handlers

Roman Arutyunyan 92 November 25, 2021 09:22AM

Re: [PATCH 1 of 3] QUIC: post stream events instead of calling their handlers

Sergey Kandaurov 153 December 06, 2021 07:38AM

Re: [PATCH 1 of 3] QUIC: post stream events instead of calling their handlers

Roman Arutyunyan 99 December 13, 2021 07:20AM

[PATCH 2 of 3] QUIC: simplified stream initialization

Roman Arutyunyan 223 November 25, 2021 09:22AM

Re: [PATCH 2 of 3] QUIC: simplified stream initialization

Sergey Kandaurov 96 December 10, 2021 09:02AM

[PATCH 3 of 3] QUIC: stream recv shutdown support

Roman Arutyunyan 144 November 25, 2021 09:22AM

Re: [PATCH 3 of 3] QUIC: stream recv shutdown support

Roman Arutyunyan 333 November 26, 2021 08:12AM

Re: [PATCH 3 of 3] QUIC: stream recv shutdown support

Vladimir Homutov 121 December 10, 2021 02:40AM

Re: [PATCH 3 of 3] QUIC: stream recv shutdown support

Roman Arutyunyan 77 December 13, 2021 07:04AM

Re: [PATCH 3 of 3] QUIC: stream recv shutdown support

Vladimir Homutov 92 December 13, 2021 08:26AM



Sorry, you do not have permission to post/reply in this forum.

Online Users

Guests: 280
Record Number of Users: 8 on April 13, 2023
Record Number of Guests: 421 on December 02, 2018
Powered by nginx      Powered by FreeBSD      PHP Powered      Powered by MariaDB      ipv6 ready