From c54353987b21ca2d061b483aa24310ac88885e27 Mon Sep 17 00:00:00 2001 From: Hakase Date: Fri, 19 May 2023 16:40:20 +0900 Subject: [PATCH] Latest update - 9095 --- README | 374 ----------- auto/modules | 14 - auto/options | 3 - src/core/ngx_connection.c | 4 + src/event/ngx_event_udp.c | 6 +- src/event/ngx_event_udp.h | 1 + src/event/quic/ngx_event_quic.h | 2 - src/event/quic/ngx_event_quic_socket.c | 1 + src/event/quic/ngx_event_quic_udp.c | 53 -- src/http/ngx_http.c | 7 - src/http/v3/ngx_http_v3.c | 4 - src/http/v3/ngx_http_v3.h | 13 - src/http/v3/ngx_http_v3_filter_module.c | 685 -------------------- src/http/v3/ngx_http_v3_module.c | 132 +--- src/http/v3/ngx_http_v3_parse.c | 91 +-- src/http/v3/ngx_http_v3_uni.c | 157 ----- src/http/v3/ngx_http_v3_uni.h | 6 - src/stream/ngx_stream.c | 24 - src/stream/ngx_stream.h | 6 - src/stream/ngx_stream_core_module.c | 29 - src/stream/ngx_stream_handler.c | 19 - src/stream/ngx_stream_proxy_module.c | 15 - src/stream/ngx_stream_quic_module.c | 343 ---------- src/stream/ngx_stream_quic_module.h | 20 - src/stream/ngx_stream_ssl_module.c | 31 - src/stream/ngx_stream_write_filter_module.c | 7 +- 26 files changed, 17 insertions(+), 2030 deletions(-) delete mode 100644 README delete mode 100644 src/stream/ngx_stream_quic_module.c delete mode 100644 src/stream/ngx_stream_quic_module.h diff --git a/README b/README deleted file mode 100644 index cde316a..0000000 --- a/README +++ /dev/null @@ -1,374 +0,0 @@ -Experimental QUIC support for nginx ------------------------------------ - -1. Introduction -2. Building from sources -3. Configuration -4. Directives -5. Clients -6. Troubleshooting -7. Contributing -8. Links - -1. Introduction - - This is an experimental QUIC [1] / HTTP/3 [2] support for nginx. - - The code is developed in a separate "quic" branch available - at https://hg.nginx.org/nginx-quic. Currently it is based - on nginx mainline 1.23.x. We merge new nginx releases into - this branch regularly. - - The project code base is under the same BSD license as nginx. - - The code is currently at a beta level of quality, however - there are several production deployments with it. - - NGINX Development Team is working on improving HTTP/3 support to - integrate it into the main NGINX codebase. Thus, expect further - updates of this code, including features, changes in behaviour, - bug fixes, and refactoring. NGINX Development team will be - grateful for any feedback and code submissions. - - Please contact NGINX Development Team via nginx-devel mailing list [3]. - - What works now: - - IETF QUIC version 1 is supported. Internet drafts are no longer supported. - - nginx should be able to respond to HTTP/3 requests over QUIC and - it should be possible to upload and download big files without errors. - - + The handshake completes successfully - + One endpoint can update keys and its peer responds correctly - + 0-RTT data is being received and acted on - + Connection is established using TLS Resume Ticket - + A handshake that includes a Retry packet completes successfully - + Stream data is being exchanged and ACK'ed - + An H3 transaction succeeded - + One or both endpoints insert entries into dynamic table and - subsequently reference them from header blocks - + Version Negotiation packet is sent to client with unknown version - + Lost packets are detected and retransmitted properly - + Clients may migrate to new address - -2. Building from sources - - The build is configured using the configure command. - Refer to http://nginx.org/en/docs/configure.html for details. - - When configuring nginx, it's possible to enable QUIC and HTTP/3 - using the following new configuration options: - - --with-http_v3_module - enable QUIC and HTTP/3 - --with-stream_quic_module - enable QUIC in Stream - - A library that provides QUIC support is recommended to build nginx, there - are several of those available on the market: - + BoringSSL [4] - + LibreSSL [5] - + QuicTLS [6] - - Alternatively, nginx can be configured with OpenSSL compatibility - layer, which emulates BoringSSL QUIC API for OpenSSL. This mode is - enabled by default if native QUIC support is not detected. - 0-RTT is not supported in OpenSSL compatibility mode. - - Clone the NGINX QUIC repository - - $ hg clone -b quic https://hg.nginx.org/nginx-quic - $ cd nginx-quic - - Use the following command to configure nginx with BoringSSL [4] - - $ ./auto/configure --with-debug --with-http_v3_module \ - --with-cc-opt="-I../boringssl/include" \ - --with-ld-opt="-L../boringssl/build/ssl \ - -L../boringssl/build/crypto" - $ make - - Alternatively, nginx can be configured with QuicTLS [6] - - $ ./auto/configure --with-debug --with-http_v3_module \ - --with-cc-opt="-I../quictls/build/include" \ - --with-ld-opt="-L../quictls/build/lib" - - Alternatively, nginx can be configured with a modern version - of LibreSSL [7] - - $ ./auto/configure --with-debug --with-http_v3_module \ - --with-cc-opt="-I../libressl/build/include" \ - --with-ld-opt="-L../libressl/build/lib" - -3. Configuration - - The HTTP "listen" directive got a new option "quic" which enables - QUIC as client transport protocol instead of TCP. - - The Stream "listen" directive got a new option "quic" which enables - QUIC as client transport protocol instead of TCP or plain UDP. - - Along with "quic", it's also possible to specify "reuseport" - option [8] to make it work properly with multiple workers. - - To enable address validation: - - quic_retry on; - - To enable 0-RTT: - - ssl_early_data on; - - To enable GSO (Generic Segmentation Offloading): - - quic_gso on; - - To set host key for various tokens: - - quic_host_key ; - - QUIC requires TLSv1.3 protocol, which is enabled by the default - by "ssl_protocols" directive. - - By default, GSO Linux-specific optimization [10] is disabled. - Enable it in case a corresponding network interface is configured to - support GSO. - - A number of directives were added that configure HTTP/3: - - http3 - http3_hq - http3_stream_buffer_size - http3_max_concurrent_pushes - http3_max_concurrent_streams - http3_push - http3_push_preload - - In http, an additional variable is available: $http3. - The value of $http3 is "h3" for HTTP/3 connections, - "hq" for hq connections, or an empty string otherwise. - - In stream, an additional variable is available: $quic. - The value of $quic is "quic" if QUIC connection is used, - or an empty string otherwise. - -Example configuration: - - http { - log_format quic '$remote_addr - $remote_user [$time_local] ' - '"$request" $status $body_bytes_sent ' - '"$http_referer" "$http_user_agent" "$http3"'; - - access_log logs/access.log quic; - - server { - # for better compatibility it's recommended - # to use the same port for quic and https - listen 8443 quic reuseport; - listen 8443 ssl; - - ssl_certificate certs/example.com.crt; - ssl_certificate_key certs/example.com.key; - - location / { - # required for browsers to direct them into quic port - add_header Alt-Svc 'h3=":8443"; ma=86400'; - } - } - } - -4. Directives - - Syntax: quic_bpf on | off; - Default: quic_bpf off; - Context: main - - Enables routing of QUIC packets using eBPF. - When enabled, this allows to support QUIC connection migration. - The directive is only supported on Linux 5.7+. - - - Syntax: quic_retry on | off; - Default: quic_retry off; - Context: http | stream, server - - Enables the QUIC Address Validation feature. This includes: - - sending a new token in a Retry packet or a NEW_TOKEN frame - - validating a token received in the Initial packet - - - Syntax: quic_gso on | off; - Default: quic_gso off; - Context: http | stream, server - - Enables sending in optimized batch mode using segmentation offloading. - Optimized sending is only supported on Linux featuring UDP_SEGMENT. - - - Syntax: quic_host_key file; - Default: - - Context: http | stream, server - - Specifies a file with the secret key used to encrypt stateless reset and - address validation tokens. By default, a randomly generated key is used. - - - Syntax: quic_active_connection_id_limit number; - Default: quic_active_connection_id_limit 2; - Context: http | stream, server - - Sets the QUIC active_connection_id_limit transport parameter value. - This is the maximum number of connection IDs we are willing to store. - - - Syntax: quic_timeout time; - Default: quic_timeout 60s; - Context: stream, server - - Defines a timeout used to negotiate the QUIC idle timeout. - In the http module, it is taken from the keepalive_timeout directive. - - - Syntax: quic_stream_buffer_size size; - Default: quic_stream_buffer_size 64k; - Context: stream, server - - Syntax: http3_stream_buffer_size size; - Default: http3_stream_buffer_size 64k; - Context: http, server - - Sets buffer size for reading and writing of the QUIC STREAM payload. - The buffer size is used to calculate initial flow control limits - in the following QUIC transport parameters: - - initial_max_data - - initial_max_stream_data_bidi_local - - initial_max_stream_data_bidi_remote - - initial_max_stream_data_uni - - - Syntax: http3_max_concurrent_pushes number; - Default: http3_max_concurrent_pushes 10; - Context: http, server - - Limits the maximum number of concurrent push requests in a connection. - - - Syntax: http3_max_concurrent_streams number; - Default: http3_max_concurrent_streams 128; - Context: http, server - - Sets the maximum number of concurrent HTTP/3 streams in a connection. - - - Syntax: http3_push uri | off; - Default: http3_push off; - Context: http, server, location - - Pre-emptively sends (pushes) a request to the specified uri along with - the response to the original request. Only relative URIs with absolute - path will be processed, for example: - - http3_push /static/css/main.css; - - The uri value can contain variables. - - Several http3_push directives can be specified on the same configuration - level. The off parameter cancels the effect of the http3_push directives - inherited from the previous configuration level. - - - Syntax: http3_push_preload on | off; - Default: http3_push_preload off; - Context: http, server, location - - Enables automatic conversion of preload links specified in the “Link” - response header fields into push requests. - - - Syntax: http3 on | off; - Default: http3 on; - Context: http, server - - Enables HTTP/3 protocol negotiation. - - - Syntax: http3_hq on | off; - Default: http3_hq off; - Context: http, server - - Enables HTTP/0.9 protocol negotiation used in QUIC interoperability tests. - -5. Clients - - * Browsers - - Known to work: Firefox 90+ and Chrome 92+ (QUIC version 1) - - Beware of strange issues: sometimes browser may decide to ignore QUIC - Cache clearing/restart might help. Always check access.log and - error.log to make sure the browser is using HTTP/3 and not TCP https. - - * Console clients - - Known to work: ngtcp2, firefox's neqo and chromium's console clients: - - $ examples/client 127.0.0.1 8443 https://example.com:8443/index.html - - $ ./neqo-client https://127.0.0.1:8443/ - - $ chromium-build/out/my_build/quic_client http://example.com:8443 - - - In case everyhing is right, the access log should show something like: - - 127.0.0.1 - - [24/Apr/2020:11:27:29 +0300] "GET / HTTP/3" 200 805 "-" - "nghttp3/ngtcp2 client" "quic" - - -6. Troubleshooting - - Here are some tips that may help to identify problems: - - + Ensure nginx is built with proper SSL library that supports QUIC - - + Ensure nginx is using the proper SSL library in runtime - (`nginx -V` shows what it's using) - - + Ensure a client is actually sending requests over QUIC - (see "Clients" section about browsers and cache) - - We recommend to start with simple console client like ngtcp2 - to ensure the server is configured properly before trying - with real browsers that may be very picky with certificates, - for example. - - + Build nginx with debug support [9] and check the debug log. - It should contain all details about connection and why it - failed. All related messages contain "quic " prefix and can - be easily filtered out. - - + For a deeper investigation, please enable additional debugging - in src/event/quic/ngx_event_quic_connection.h: - - #define NGX_QUIC_DEBUG_PACKETS - #define NGX_QUIC_DEBUG_FRAMES - #define NGX_QUIC_DEBUG_ALLOC - #define NGX_QUIC_DEBUG_CRYPTO - -7. Contributing - - Please refer to - http://nginx.org/en/docs/contributing_changes.html - -8. Links - - [1] https://datatracker.ietf.org/doc/html/rfc9000 - [2] https://datatracker.ietf.org/doc/html/rfc9114 - [3] https://mailman.nginx.org/mailman/listinfo/nginx-devel - [4] https://boringssl.googlesource.com/boringssl/ - [5] https://www.libressl.org/ - [6] https://github.com/quictls/openssl - [7] https://github.com/libressl-portable/portable/releases/tag/v3.6.0 - [8] https://nginx.org/en/docs/http/ngx_http_core_module.html#listen - [9] https://nginx.org/en/docs/debugging_log.html - [10] http://vger.kernel.org/lpc_net2018_talks/willemdebruijn-lpc2018-udpgso-paper-DRAFT-1.pdf diff --git a/auto/modules b/auto/modules index 31075ff..5eb3acc 100644 --- a/auto/modules +++ b/auto/modules @@ -1079,20 +1079,6 @@ if [ $STREAM != NO ]; then ngx_module_incs= - if [ $STREAM_QUIC = YES ]; then - USE_OPENSSL_QUIC=YES - have=NGX_STREAM_QUIC . auto/have - STREAM_SSL=YES - - ngx_module_name=ngx_stream_quic_module - ngx_module_deps=src/stream/ngx_stream_quic_module.h - ngx_module_srcs=src/stream/ngx_stream_quic_module.c - ngx_module_libs= - ngx_module_link=$STREAM_QUIC - - . auto/module - fi - if [ $STREAM_SSL = YES ]; then USE_OPENSSL=YES have=NGX_STREAM_SSL . auto/have diff --git a/auto/options b/auto/options index 55ee3ec..80d6620 100644 --- a/auto/options +++ b/auto/options @@ -120,7 +120,6 @@ MAIL_SMTP=YES STREAM=NO STREAM_SSL=NO -STREAM_QUIC=NO STREAM_REALIP=NO STREAM_LIMIT_CONN=YES STREAM_ACCESS=YES @@ -326,7 +325,6 @@ use the \"--with-mail_ssl_module\" option instead" --with-stream) STREAM=YES ;; --with-stream=dynamic) STREAM=DYNAMIC ;; --with-stream_ssl_module) STREAM_SSL=YES ;; - --with-stream_quic_module) STREAM_QUIC=YES ;; --with-stream_realip_module) STREAM_REALIP=YES ;; --with-stream_geoip_module) STREAM_GEOIP=YES ;; --with-stream_geoip_module=dynamic) @@ -550,7 +548,6 @@ cat << END --with-stream enable TCP/UDP proxy module --with-stream=dynamic enable dynamic TCP/UDP proxy module --with-stream_ssl_module enable ngx_stream_ssl_module - --with-stream_quic_module enable ngx_stream_quic_module --with-stream_realip_module enable ngx_stream_realip_module --with-stream_geoip_module enable ngx_stream_geoip_module --with-stream_geoip_module=dynamic enable dynamic ngx_stream_geoip_module diff --git a/src/core/ngx_connection.c b/src/core/ngx_connection.c index 5e56839..10f4d9b 100644 --- a/src/core/ngx_connection.c +++ b/src/core/ngx_connection.c @@ -72,6 +72,10 @@ ngx_create_listening(ngx_conf_t *cf, struct sockaddr *sockaddr, ngx_memcpy(ls->addr_text.data, text, len); +#if !(NGX_WIN32) + ngx_rbtree_init(&ls->rbtree, &ls->sentinel, ngx_udp_rbtree_insert_value); +#endif + ls->fd = (ngx_socket_t) -1; ls->type = SOCK_STREAM; diff --git a/src/event/ngx_event_udp.c b/src/event/ngx_event_udp.c index ec86fdf..43fa621 100644 --- a/src/event/ngx_event_udp.c +++ b/src/event/ngx_event_udp.c @@ -417,8 +417,8 @@ ngx_udp_rbtree_insert_value(ngx_rbtree_node_t *temp, udpt = (ngx_udp_connection_t *) temp; ct = udpt->connection; - rc = ngx_cmp_sockaddr(c->sockaddr, c->socklen, - ct->sockaddr, ct->socklen, 1); + rc = ngx_memn2cmp(udp->key.data, udpt->key.data, + udp->key.len, udpt->key.len); if (rc == 0 && c->listening->wildcard) { rc = ngx_cmp_sockaddr(c->local_sockaddr, c->local_socklen, @@ -471,6 +471,8 @@ ngx_insert_udp_connection(ngx_connection_t *c) ngx_crc32_final(hash); udp->node.key = hash; + udp->key.data = (u_char *) c->sockaddr; + udp->key.len = c->socklen; cln = ngx_pool_cleanup_add(c->pool, 0); if (cln == NULL) { diff --git a/src/event/ngx_event_udp.h b/src/event/ngx_event_udp.h index d7a64ee..e5ddf1b 100644 --- a/src/event/ngx_event_udp.h +++ b/src/event/ngx_event_udp.h @@ -27,6 +27,7 @@ struct ngx_udp_connection_s { ngx_rbtree_node_t node; ngx_connection_t *connection; ngx_buf_t *buffer; + ngx_str_t key; }; diff --git a/src/event/quic/ngx_event_quic.h b/src/event/quic/ngx_event_quic.h index 0c68d68..ca15200 100644 --- a/src/event/quic/ngx_event_quic.h +++ b/src/event/quic/ngx_event_quic.h @@ -111,8 +111,6 @@ struct ngx_quic_stream_s { void ngx_quic_recvmsg(ngx_event_t *ev); -void ngx_quic_rbtree_insert_value(ngx_rbtree_node_t *temp, - ngx_rbtree_node_t *node, ngx_rbtree_node_t *sentinel); void ngx_quic_run(ngx_connection_t *c, ngx_quic_conf_t *conf); ngx_connection_t *ngx_quic_open_stream(ngx_connection_t *c, ngx_uint_t bidi); void ngx_quic_finalize_connection(ngx_connection_t *c, ngx_uint_t err, diff --git a/src/event/quic/ngx_event_quic_socket.c b/src/event/quic/ngx_event_quic_socket.c index 6813fcd..6652523 100644 --- a/src/event/quic/ngx_event_quic_socket.c +++ b/src/event/quic/ngx_event_quic_socket.c @@ -179,6 +179,7 @@ ngx_quic_listen(ngx_connection_t *c, ngx_quic_connection_t *qc, qsock->udp.connection = c; qsock->udp.node.key = ngx_crc32_long(id.data, id.len); + qsock->udp.key = id; ngx_rbtree_insert(&c->listening->rbtree, &qsock->udp.node); diff --git a/src/event/quic/ngx_event_quic_udp.c b/src/event/quic/ngx_event_quic_udp.c index 0721ca8..71754a4 100644 --- a/src/event/quic/ngx_event_quic_udp.c +++ b/src/event/quic/ngx_event_quic_udp.c @@ -365,59 +365,6 @@ ngx_quic_close_accepted_connection(ngx_connection_t *c) } -void -ngx_quic_rbtree_insert_value(ngx_rbtree_node_t *temp, - ngx_rbtree_node_t *node, ngx_rbtree_node_t *sentinel) -{ - ngx_int_t rc; - ngx_connection_t *c, *ct; - ngx_rbtree_node_t **p; - ngx_quic_socket_t *qsock, *qsockt; - - for ( ;; ) { - - if (node->key < temp->key) { - - p = &temp->left; - - } else if (node->key > temp->key) { - - p = &temp->right; - - } else { /* node->key == temp->key */ - - qsock = (ngx_quic_socket_t *) node; - c = qsock->udp.connection; - - qsockt = (ngx_quic_socket_t *) temp; - ct = qsockt->udp.connection; - - rc = ngx_memn2cmp(qsock->sid.id, qsockt->sid.id, - qsock->sid.len, qsockt->sid.len); - - if (rc == 0 && c->listening->wildcard) { - rc = ngx_cmp_sockaddr(c->local_sockaddr, c->local_socklen, - ct->local_sockaddr, ct->local_socklen, 1); - } - - p = (rc < 0) ? &temp->left : &temp->right; - } - - if (*p == sentinel) { - break; - } - - temp = *p; - } - - *p = node; - node->parent = temp; - node->left = sentinel; - node->right = sentinel; - ngx_rbt_red(node); -} - - static ngx_connection_t * ngx_quic_lookup_connection(ngx_listening_t *ls, ngx_str_t *key, struct sockaddr *local_sockaddr, socklen_t local_socklen) diff --git a/src/http/ngx_http.c b/src/http/ngx_http.c index 34bfc53..d835f89 100644 --- a/src/http/ngx_http.c +++ b/src/http/ngx_http.c @@ -1883,14 +1883,7 @@ ngx_http_add_listening(ngx_conf_t *cf, ngx_http_conf_addr_t *addr) ls->wildcard = addr->opt.wildcard; #if (NGX_HTTP_V3) - ls->quic = addr->opt.quic; - - if (ls->quic) { - ngx_rbtree_init(&ls->rbtree, &ls->sentinel, - ngx_quic_rbtree_insert_value); - } - #endif return ls; diff --git a/src/http/v3/ngx_http_v3.c b/src/http/v3/ngx_http_v3.c index db0be75..eb86b2d 100644 --- a/src/http/v3/ngx_http_v3.c +++ b/src/http/v3/ngx_http_v3.c @@ -30,11 +30,7 @@ ngx_http_v3_init_session(ngx_connection_t *c) goto failed; } - h3c->max_push_id = (uint64_t) -1; - h3c->goaway_push_id = (uint64_t) -1; - ngx_queue_init(&h3c->blocked); - ngx_queue_init(&h3c->pushing); h3c->keepalive.log = c->log; h3c->keepalive.data = c; diff --git a/src/http/v3/ngx_http_v3.h b/src/http/v3/ngx_http_v3.h index 2c05f08..94b0d3e 100644 --- a/src/http/v3/ngx_http_v3.h +++ b/src/http/v3/ngx_http_v3.h @@ -106,19 +106,11 @@ typedef struct { ngx_flag_t enable_hq; size_t max_table_capacity; ngx_uint_t max_blocked_streams; - ngx_uint_t max_concurrent_pushes; ngx_uint_t max_concurrent_streams; ngx_quic_conf_t quic; } ngx_http_v3_srv_conf_t; -typedef struct { - ngx_flag_t push_preload; - ngx_flag_t push; - ngx_array_t *pushes; -} ngx_http_v3_loc_conf_t; - - struct ngx_http_v3_parse_s { size_t header_limit; ngx_http_v3_parse_headers_t headers; @@ -136,11 +128,6 @@ struct ngx_http_v3_session_s { ngx_queue_t blocked; ngx_uint_t nblocked; - ngx_queue_t pushing; - ngx_uint_t npushing; - uint64_t next_push_id; - uint64_t max_push_id; - uint64_t goaway_push_id; uint64_t next_request_id; off_t total_bytes; diff --git a/src/http/v3/ngx_http_v3_filter_module.c b/src/http/v3/ngx_http_v3_filter_module.c index ad50a07..3077d27 100644 --- a/src/http/v3/ngx_http_v3_filter_module.c +++ b/src/http/v3/ngx_http_v3_filter_module.c @@ -36,17 +36,6 @@ typedef struct { static ngx_int_t ngx_http_v3_header_filter(ngx_http_request_t *r); -static ngx_int_t ngx_http_v3_push_resources(ngx_http_request_t *r, - ngx_chain_t ***out); -static ngx_int_t ngx_http_v3_push_resource(ngx_http_request_t *r, - ngx_str_t *path, ngx_chain_t ***out); -static ngx_int_t ngx_http_v3_create_push_request( - ngx_http_request_t *pr, ngx_str_t *path, uint64_t push_id); -static ngx_int_t ngx_http_v3_set_push_header(ngx_http_request_t *r, - const char *name, ngx_str_t *value); -static void ngx_http_v3_push_request_handler(ngx_event_t *ev); -static ngx_chain_t *ngx_http_v3_create_push_promise(ngx_http_request_t *r, - ngx_str_t *path, uint64_t push_id); static ngx_int_t ngx_http_v3_body_filter(ngx_http_request_t *r, ngx_chain_t *in); static ngx_chain_t *ngx_http_v3_create_trailers(ngx_http_request_t *r, @@ -155,14 +144,6 @@ ngx_http_v3_header_filter(ngx_http_request_t *r) out = NULL; ll = &out; - if ((c->quic->id & NGX_QUIC_STREAM_UNIDIRECTIONAL) == 0 - && r->method != NGX_HTTP_HEAD) - { - if (ngx_http_v3_push_resources(r, &ll) != NGX_OK) { - return NGX_ERROR; - } - } - len = ngx_http_v3_encode_field_section_prefix(NULL, 0, 0, 0); if (r->headers_out.status == NGX_HTTP_OK) { @@ -606,672 +587,6 @@ ngx_http_v3_header_filter(ngx_http_request_t *r) } -static ngx_int_t -ngx_http_v3_push_resources(ngx_http_request_t *r, ngx_chain_t ***out) -{ - u_char *start, *end, *last; - ngx_str_t path; - ngx_int_t rc; - ngx_uint_t i, push; - ngx_table_elt_t *h; - ngx_http_v3_loc_conf_t *h3lcf; - ngx_http_complex_value_t *pushes; - - h3lcf = ngx_http_get_module_loc_conf(r, ngx_http_v3_module); - - if (h3lcf->pushes) { - pushes = h3lcf->pushes->elts; - - for (i = 0; i < h3lcf->pushes->nelts; i++) { - - if (ngx_http_complex_value(r, &pushes[i], &path) != NGX_OK) { - return NGX_ERROR; - } - - if (path.len == 0) { - continue; - } - - if (path.len == 3 && ngx_strncmp(path.data, "off", 3) == 0) { - continue; - } - - rc = ngx_http_v3_push_resource(r, &path, out); - - if (rc == NGX_ERROR) { - return NGX_ERROR; - } - - if (rc == NGX_ABORT) { - return NGX_OK; - } - - /* NGX_OK, NGX_DECLINED */ - } - } - - if (!h3lcf->push_preload) { - return NGX_OK; - } - - for (h = r->headers_out.link; h; h = h->next) { - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, - "http3 parse link: \"%V\"", &h->value); - - start = h->value.data; - end = h->value.data + h->value.len; - - next_link: - - while (start < end && *start == ' ') { start++; } - - if (start == end || *start++ != '<') { - continue; - } - - while (start < end && *start == ' ') { start++; } - - for (last = start; last < end && *last != '>'; last++) { - /* void */ - } - - if (last == start || last == end) { - continue; - } - - path.len = last - start; - path.data = start; - - start = last + 1; - - while (start < end && *start == ' ') { start++; } - - if (start == end) { - continue; - } - - if (*start == ',') { - start++; - goto next_link; - } - - if (*start++ != ';') { - continue; - } - - last = ngx_strlchr(start, end, ','); - - if (last == NULL) { - last = end; - } - - push = 0; - - for ( ;; ) { - - while (start < last && *start == ' ') { start++; } - - if (last - start >= 6 - && ngx_strncasecmp(start, (u_char *) "nopush", 6) == 0) - { - start += 6; - - if (start == last || *start == ' ' || *start == ';') { - push = 0; - break; - } - - goto next_param; - } - - if (last - start >= 11 - && ngx_strncasecmp(start, (u_char *) "rel=preload", 11) == 0) - { - start += 11; - - if (start == last || *start == ' ' || *start == ';') { - push = 1; - } - - goto next_param; - } - - if (last - start >= 4 - && ngx_strncasecmp(start, (u_char *) "rel=", 4) == 0) - { - start += 4; - - while (start < last && *start == ' ') { start++; } - - if (start == last || *start++ != '"') { - goto next_param; - } - - for ( ;; ) { - - while (start < last && *start == ' ') { start++; } - - if (last - start >= 7 - && ngx_strncasecmp(start, (u_char *) "preload", 7) == 0) - { - start += 7; - - if (start < last && (*start == ' ' || *start == '"')) { - push = 1; - break; - } - } - - while (start < last && *start != ' ' && *start != '"') { - start++; - } - - if (start == last) { - break; - } - - if (*start == '"') { - break; - } - - start++; - } - } - - next_param: - - start = ngx_strlchr(start, last, ';'); - - if (start == NULL) { - break; - } - - start++; - } - - if (push) { - while (path.len && path.data[path.len - 1] == ' ') { - path.len--; - } - } - - if (push && path.len - && !(path.len > 1 && path.data[0] == '/' && path.data[1] == '/')) - { - rc = ngx_http_v3_push_resource(r, &path, out); - - if (rc == NGX_ERROR) { - return NGX_ERROR; - } - - if (rc == NGX_ABORT) { - return NGX_OK; - } - - /* NGX_OK, NGX_DECLINED */ - } - - if (last < end) { - start = last + 1; - goto next_link; - } - } - - return NGX_OK; -} - - -static ngx_int_t -ngx_http_v3_push_resource(ngx_http_request_t *r, ngx_str_t *path, - ngx_chain_t ***ll) -{ - uint64_t push_id; - ngx_int_t rc; - ngx_chain_t *cl; - ngx_connection_t *c; - ngx_http_v3_session_t *h3c; - ngx_http_v3_srv_conf_t *h3scf; - - c = r->connection; - h3c = ngx_http_v3_get_session(c); - h3scf = ngx_http_get_module_srv_conf(r, ngx_http_v3_module); - - ngx_log_debug5(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 push \"%V\" pushing:%ui/%ui id:%uL/%L", - path, h3c->npushing, h3scf->max_concurrent_pushes, - h3c->next_push_id, h3c->max_push_id); - - if (!ngx_path_separator(path->data[0])) { - ngx_log_error(NGX_LOG_WARN, c->log, 0, - "non-absolute path \"%V\" not pushed", path); - return NGX_DECLINED; - } - - if (h3c->max_push_id == (uint64_t) -1 - || h3c->next_push_id > h3c->max_push_id) - { - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 abort pushes due to max_push_id"); - return NGX_ABORT; - } - - if (h3c->goaway_push_id != (uint64_t) -1) { - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 abort pushes due to goaway"); - return NGX_ABORT; - } - - if (h3c->npushing >= h3scf->max_concurrent_pushes) { - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 abort pushes due to max_concurrent_pushes"); - return NGX_ABORT; - } - - if (r->headers_in.server.len == 0) { - return NGX_ABORT; - } - - push_id = h3c->next_push_id++; - - rc = ngx_http_v3_create_push_request(r, path, push_id); - if (rc != NGX_OK) { - return rc; - } - - cl = ngx_http_v3_create_push_promise(r, path, push_id); - if (cl == NULL) { - return NGX_ERROR; - } - - for (**ll = cl; **ll; *ll = &(**ll)->next); - - return NGX_OK; -} - - -static ngx_int_t -ngx_http_v3_create_push_request(ngx_http_request_t *pr, ngx_str_t *path, - uint64_t push_id) -{ - ngx_connection_t *c, *pc; - ngx_http_request_t *r; - ngx_http_log_ctx_t *ctx; - ngx_http_connection_t *hc, *phc; - ngx_http_core_srv_conf_t *cscf; - - pc = pr->connection; - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0, - "http3 create push request id:%uL", push_id); - - c = ngx_http_v3_create_push_stream(pc, push_id); - if (c == NULL) { - return NGX_ABORT; - } - -#if (NGX_STAT_STUB) - (void) ngx_atomic_fetch_add(ngx_stat_active, 1); -#endif - - hc = ngx_palloc(c->pool, sizeof(ngx_http_connection_t)); - if (hc == NULL) { - ngx_http_close_connection(c); - return NGX_ERROR; - } - - phc = ngx_http_quic_get_connection(pc); - ngx_memcpy(hc, phc, sizeof(ngx_http_connection_t)); - c->data = hc; - - ctx = ngx_palloc(c->pool, sizeof(ngx_http_log_ctx_t)); - if (ctx == NULL) { - ngx_http_close_connection(c); - return NGX_ERROR; - } - - ctx->connection = c; - ctx->request = NULL; - ctx->current_request = NULL; - - c->log->handler = pc->log->handler; - c->log->data = ctx; - c->log->action = "processing pushed request headers"; - - c->log_error = NGX_ERROR_INFO; - - r = ngx_http_create_request(c); - if (r == NULL) { - ngx_http_close_connection(c); - return NGX_ERROR; - } - - c->data = r; - - ngx_str_set(&r->http_protocol, "HTTP/3.0"); - - r->http_version = NGX_HTTP_VERSION_30; - r->method_name = ngx_http_core_get_method; - r->method = NGX_HTTP_GET; - - cscf = ngx_http_get_module_srv_conf(r, ngx_http_core_module); - - r->header_in = ngx_create_temp_buf(r->pool, - cscf->client_header_buffer_size); - if (r->header_in == NULL) { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - if (ngx_list_init(&r->headers_in.headers, r->pool, 4, - sizeof(ngx_table_elt_t)) - != NGX_OK) - { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - r->headers_in.connection_type = NGX_HTTP_CONNECTION_CLOSE; - - r->schema.data = ngx_pstrdup(r->pool, &pr->schema); - if (r->schema.data == NULL) { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - r->schema.len = pr->schema.len; - - r->uri_start = ngx_pstrdup(r->pool, path); - if (r->uri_start == NULL) { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - r->uri_end = r->uri_start + path->len; - - if (ngx_http_parse_uri(r) != NGX_OK) { - ngx_http_finalize_request(r, NGX_HTTP_BAD_REQUEST); - return NGX_ERROR; - } - - if (ngx_http_process_request_uri(r) != NGX_OK) { - return NGX_ERROR; - } - - if (ngx_http_v3_set_push_header(r, "host", &pr->headers_in.server) - != NGX_OK) - { - return NGX_ERROR; - } - - if (pr->headers_in.accept_encoding) { - if (ngx_http_v3_set_push_header(r, "accept-encoding", - &pr->headers_in.accept_encoding->value) - != NGX_OK) - { - return NGX_ERROR; - } - } - - if (pr->headers_in.accept_language) { - if (ngx_http_v3_set_push_header(r, "accept-language", - &pr->headers_in.accept_language->value) - != NGX_OK) - { - return NGX_ERROR; - } - } - - if (pr->headers_in.user_agent) { - if (ngx_http_v3_set_push_header(r, "user-agent", - &pr->headers_in.user_agent->value) - != NGX_OK) - { - return NGX_ERROR; - } - } - - c->read->handler = ngx_http_v3_push_request_handler; - c->read->handler = ngx_http_v3_push_request_handler; - - ngx_post_event(c->read, &ngx_posted_events); - - return NGX_OK; -} - - -static ngx_int_t -ngx_http_v3_set_push_header(ngx_http_request_t *r, const char *name, - ngx_str_t *value) -{ - u_char *p; - ngx_table_elt_t *h; - ngx_http_header_t *hh; - ngx_http_core_main_conf_t *cmcf; - - ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, - "http3 push header \"%s\": \"%V\"", name, value); - - cmcf = ngx_http_get_module_main_conf(r, ngx_http_core_module); - - p = ngx_pnalloc(r->pool, value->len + 1); - if (p == NULL) { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - ngx_memcpy(p, value->data, value->len); - p[value->len] = '\0'; - - h = ngx_list_push(&r->headers_in.headers); - if (h == NULL) { - ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); - return NGX_ERROR; - } - - h->key.data = (u_char *) name; - h->key.len = ngx_strlen(name); - h->hash = ngx_hash_key(h->key.data, h->key.len); - h->lowcase_key = (u_char *) name; - h->value.data = p; - h->value.len = value->len; - - hh = ngx_hash_find(&cmcf->headers_in_hash, h->hash, - h->lowcase_key, h->key.len); - - if (hh && hh->handler(r, h, hh->offset) != NGX_OK) { - return NGX_ERROR; - } - - return NGX_OK; -} - - -static void -ngx_http_v3_push_request_handler(ngx_event_t *ev) -{ - ngx_connection_t *c; - ngx_http_request_t *r; - - c = ev->data; - r = c->data; - - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0, "http3 push request handler"); - - ngx_http_process_request(r); -} - - -static ngx_chain_t * -ngx_http_v3_create_push_promise(ngx_http_request_t *r, ngx_str_t *path, - uint64_t push_id) -{ - size_t n, len; - ngx_buf_t *b; - ngx_chain_t *hl, *cl; - ngx_http_v3_session_t *h3c; - - h3c = ngx_http_v3_get_session(r->connection); - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, - "http3 create push promise id:%uL", push_id); - - len = ngx_http_v3_encode_varlen_int(NULL, push_id); - - len += ngx_http_v3_encode_field_section_prefix(NULL, 0, 0, 0); - - len += ngx_http_v3_encode_field_ri(NULL, 0, - NGX_HTTP_V3_HEADER_METHOD_GET); - - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_AUTHORITY, - NULL, r->headers_in.server.len); - - if (path->len == 1 && path->data[0] == '/') { - len += ngx_http_v3_encode_field_ri(NULL, 0, - NGX_HTTP_V3_HEADER_PATH_ROOT); - - } else { - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_PATH_ROOT, - NULL, path->len); - } - - if (r->schema.len == 5 && ngx_strncmp(r->schema.data, "https", 5) == 0) { - len += ngx_http_v3_encode_field_ri(NULL, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTPS); - - } else if (r->schema.len == 4 - && ngx_strncmp(r->schema.data, "http", 4) == 0) - { - len += ngx_http_v3_encode_field_ri(NULL, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTP); - - } else { - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTP, - NULL, r->schema.len); - } - - if (r->headers_in.accept_encoding) { - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_ACCEPT_ENCODING, NULL, - r->headers_in.accept_encoding->value.len); - } - - if (r->headers_in.accept_language) { - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_ACCEPT_LANGUAGE, NULL, - r->headers_in.accept_language->value.len); - } - - if (r->headers_in.user_agent) { - len += ngx_http_v3_encode_field_lri(NULL, 0, - NGX_HTTP_V3_HEADER_USER_AGENT, NULL, - r->headers_in.user_agent->value.len); - } - - b = ngx_create_temp_buf(r->pool, len); - if (b == NULL) { - return NULL; - } - - b->last = (u_char *) ngx_http_v3_encode_varlen_int(b->last, push_id); - - b->last = (u_char *) ngx_http_v3_encode_field_section_prefix(b->last, - 0, 0, 0); - - b->last = (u_char *) ngx_http_v3_encode_field_ri(b->last, 0, - NGX_HTTP_V3_HEADER_METHOD_GET); - - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_AUTHORITY, - r->headers_in.server.data, - r->headers_in.server.len); - - if (path->len == 1 && path->data[0] == '/') { - b->last = (u_char *) ngx_http_v3_encode_field_ri(b->last, 0, - NGX_HTTP_V3_HEADER_PATH_ROOT); - - } else { - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_PATH_ROOT, - path->data, path->len); - } - - if (r->schema.len == 5 && ngx_strncmp(r->schema.data, "https", 5) == 0) { - b->last = (u_char *) ngx_http_v3_encode_field_ri(b->last, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTPS); - - } else if (r->schema.len == 4 - && ngx_strncmp(r->schema.data, "http", 4) == 0) - { - b->last = (u_char *) ngx_http_v3_encode_field_ri(b->last, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTP); - - } else { - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_SCHEME_HTTP, - r->schema.data, r->schema.len); - } - - if (r->headers_in.accept_encoding) { - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_ACCEPT_ENCODING, - r->headers_in.accept_encoding->value.data, - r->headers_in.accept_encoding->value.len); - } - - if (r->headers_in.accept_language) { - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_ACCEPT_LANGUAGE, - r->headers_in.accept_language->value.data, - r->headers_in.accept_language->value.len); - } - - if (r->headers_in.user_agent) { - b->last = (u_char *) ngx_http_v3_encode_field_lri(b->last, 0, - NGX_HTTP_V3_HEADER_USER_AGENT, - r->headers_in.user_agent->value.data, - r->headers_in.user_agent->value.len); - } - - cl = ngx_alloc_chain_link(r->pool); - if (cl == NULL) { - return NULL; - } - - cl->buf = b; - cl->next = NULL; - - n = b->last - b->pos; - - h3c->payload_bytes += n; - - len = ngx_http_v3_encode_varlen_int(NULL, NGX_HTTP_V3_FRAME_PUSH_PROMISE) - + ngx_http_v3_encode_varlen_int(NULL, n); - - b = ngx_create_temp_buf(r->pool, len); - if (b == NULL) { - return NULL; - } - - b->last = (u_char *) ngx_http_v3_encode_varlen_int(b->last, - NGX_HTTP_V3_FRAME_PUSH_PROMISE); - b->last = (u_char *) ngx_http_v3_encode_varlen_int(b->last, n); - - hl = ngx_alloc_chain_link(r->pool); - if (hl == NULL) { - return NULL; - } - - hl->buf = b; - hl->next = cl; - - return hl; -} - - static ngx_int_t ngx_http_v3_body_filter(ngx_http_request_t *r, ngx_chain_t *in) { diff --git a/src/http/v3/ngx_http_v3_module.c b/src/http/v3/ngx_http_v3_module.c index 8569f07..875e5f2 100644 --- a/src/http/v3/ngx_http_v3_module.c +++ b/src/http/v3/ngx_http_v3_module.c @@ -18,10 +18,6 @@ static char *ngx_http_v3_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child); static char *ngx_http_quic_host_key(ngx_conf_t *cf, ngx_command_t *cmd, void *conf); -static void *ngx_http_v3_create_loc_conf(ngx_conf_t *cf); -static char *ngx_http_v3_merge_loc_conf(ngx_conf_t *cf, void *parent, - void *child); -static char *ngx_http_v3_push(ngx_conf_t *cf, ngx_command_t *cmd, void *conf); static ngx_command_t ngx_http_v3_commands[] = { @@ -40,13 +36,6 @@ static ngx_command_t ngx_http_v3_commands[] = { offsetof(ngx_http_v3_srv_conf_t, enable_hq), NULL }, - { ngx_string("http3_max_concurrent_pushes"), - NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, - ngx_conf_set_num_slot, - NGX_HTTP_SRV_CONF_OFFSET, - offsetof(ngx_http_v3_srv_conf_t, max_concurrent_pushes), - NULL }, - { ngx_string("http3_max_concurrent_streams"), NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, ngx_conf_set_num_slot, @@ -54,20 +43,6 @@ static ngx_command_t ngx_http_v3_commands[] = { offsetof(ngx_http_v3_srv_conf_t, max_concurrent_streams), NULL }, - { ngx_string("http3_push"), - NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_TAKE1, - ngx_http_v3_push, - NGX_HTTP_LOC_CONF_OFFSET, - 0, - NULL }, - - { ngx_string("http3_push_preload"), - NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_HTTP_LOC_CONF|NGX_CONF_FLAG, - ngx_conf_set_flag_slot, - NGX_HTTP_LOC_CONF_OFFSET, - offsetof(ngx_http_v3_loc_conf_t, push_preload), - NULL }, - { ngx_string("http3_stream_buffer_size"), NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_TAKE1, ngx_conf_set_size_slot, @@ -117,8 +92,8 @@ static ngx_http_module_t ngx_http_v3_module_ctx = { ngx_http_v3_create_srv_conf, /* create server configuration */ ngx_http_v3_merge_srv_conf, /* merge server configuration */ - ngx_http_v3_create_loc_conf, /* create location configuration */ - ngx_http_v3_merge_loc_conf /* merge location configuration */ + NULL, /* create location configuration */ + NULL /* merge location configuration */ }; @@ -224,7 +199,6 @@ ngx_http_v3_create_srv_conf(ngx_conf_t *cf) h3scf->enable = NGX_CONF_UNSET; h3scf->enable_hq = NGX_CONF_UNSET; h3scf->max_table_capacity = NGX_HTTP_V3_MAX_TABLE_CAPACITY; - h3scf->max_concurrent_pushes = NGX_CONF_UNSET_UINT; h3scf->max_concurrent_streams = NGX_CONF_UNSET_UINT; h3scf->quic.stream_buffer_size = NGX_CONF_UNSET_SIZE; @@ -255,9 +229,6 @@ ngx_http_v3_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child) ngx_conf_merge_value(conf->enable_hq, prev->enable_hq, 0); - ngx_conf_merge_uint_value(conf->max_concurrent_pushes, - prev->max_concurrent_pushes, 10); - ngx_conf_merge_uint_value(conf->max_concurrent_streams, prev->max_concurrent_streams, 128); @@ -416,102 +387,3 @@ failed: return NGX_CONF_ERROR; } - - -static void * -ngx_http_v3_create_loc_conf(ngx_conf_t *cf) -{ - ngx_http_v3_loc_conf_t *h3lcf; - - h3lcf = ngx_pcalloc(cf->pool, sizeof(ngx_http_v3_loc_conf_t)); - if (h3lcf == NULL) { - return NULL; - } - - /* - * set by ngx_pcalloc(): - * - * h3lcf->pushes = NULL; - */ - - h3lcf->push_preload = NGX_CONF_UNSET; - h3lcf->push = NGX_CONF_UNSET; - - return h3lcf; -} - - -static char * -ngx_http_v3_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child) -{ - ngx_http_v3_loc_conf_t *prev = parent; - ngx_http_v3_loc_conf_t *conf = child; - - ngx_conf_merge_value(conf->push, prev->push, 1); - - if (conf->push && conf->pushes == NULL) { - conf->pushes = prev->pushes; - } - - ngx_conf_merge_value(conf->push_preload, prev->push_preload, 0); - - return NGX_CONF_OK; -} - - -static char * -ngx_http_v3_push(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) -{ - ngx_http_v3_loc_conf_t *h3lcf = conf; - - ngx_str_t *value; - ngx_http_complex_value_t *cv; - ngx_http_compile_complex_value_t ccv; - - value = cf->args->elts; - - if (ngx_strcmp(value[1].data, "off") == 0) { - - if (h3lcf->pushes) { - return "\"off\" parameter cannot be used with URI"; - } - - if (h3lcf->push == 0) { - return "is duplicate"; - } - - h3lcf->push = 0; - return NGX_CONF_OK; - } - - if (h3lcf->push == 0) { - return "URI cannot be used with \"off\" parameter"; - } - - h3lcf->push = 1; - - if (h3lcf->pushes == NULL) { - h3lcf->pushes = ngx_array_create(cf->pool, 1, - sizeof(ngx_http_complex_value_t)); - if (h3lcf->pushes == NULL) { - return NGX_CONF_ERROR; - } - } - - cv = ngx_array_push(h3lcf->pushes); - if (cv == NULL) { - return NGX_CONF_ERROR; - } - - ngx_memzero(&ccv, sizeof(ngx_http_compile_complex_value_t)); - - ccv.cf = cf; - ccv.value = &value[1]; - ccv.complex_value = cv; - - if (ngx_http_compile_complex_value(&ccv) != NGX_OK) { - return NGX_CONF_ERROR; - } - - return NGX_CONF_OK; -} diff --git a/src/http/v3/ngx_http_v3_parse.c b/src/http/v3/ngx_http_v3_parse.c index 7ea284f..c51a486 100644 --- a/src/http/v3/ngx_http_v3_parse.c +++ b/src/http/v3/ngx_http_v3_parse.c @@ -1159,10 +1159,7 @@ ngx_http_v3_parse_control(ngx_connection_t *c, ngx_http_v3_parse_control_t *st, sw_first_type, sw_type, sw_length, - sw_cancel_push, sw_settings, - sw_max_push_id, - sw_goaway, sw_skip }; @@ -1212,6 +1209,10 @@ ngx_http_v3_parse_control(ngx_connection_t *c, ngx_http_v3_parse_control_t *st, return NGX_HTTP_V3_ERR_FRAME_UNEXPECTED; } + if (st->type == NGX_HTTP_V3_FRAME_CANCEL_PUSH) { + return NGX_HTTP_V3_ERR_ID_ERROR; + } + st->state = sw_length; break; @@ -1233,22 +1234,10 @@ ngx_http_v3_parse_control(ngx_connection_t *c, ngx_http_v3_parse_control_t *st, switch (st->type) { - case NGX_HTTP_V3_FRAME_CANCEL_PUSH: - st->state = sw_cancel_push; - break; - case NGX_HTTP_V3_FRAME_SETTINGS: st->state = sw_settings; break; - case NGX_HTTP_V3_FRAME_MAX_PUSH_ID: - st->state = sw_max_push_id; - break; - - case NGX_HTTP_V3_FRAME_GOAWAY: - st->state = sw_goaway; - break; - default: ngx_log_debug0(NGX_LOG_DEBUG_HTTP, c->log, 0, "http3 parse skip unknown frame"); @@ -1257,30 +1246,6 @@ ngx_http_v3_parse_control(ngx_connection_t *c, ngx_http_v3_parse_control_t *st, break; - case sw_cancel_push: - - ngx_http_v3_parse_start_local(b, &loc, st->length); - - rc = ngx_http_v3_parse_varlen_int(c, &st->vlint, &loc); - - ngx_http_v3_parse_end_local(b, &loc, &st->length); - - if (st->length == 0 && rc == NGX_AGAIN) { - return NGX_HTTP_V3_ERR_FRAME_ERROR; - } - - if (rc != NGX_DONE) { - return rc; - } - - rc = ngx_http_v3_cancel_push(c, st->vlint.value); - if (rc != NGX_OK) { - return rc; - } - - st->state = sw_type; - break; - case sw_settings: ngx_http_v3_parse_start_local(b, &loc, st->length); @@ -1303,54 +1268,6 @@ ngx_http_v3_parse_control(ngx_connection_t *c, ngx_http_v3_parse_control_t *st, break; - case sw_max_push_id: - - ngx_http_v3_parse_start_local(b, &loc, st->length); - - rc = ngx_http_v3_parse_varlen_int(c, &st->vlint, &loc); - - ngx_http_v3_parse_end_local(b, &loc, &st->length); - - if (st->length == 0 && rc == NGX_AGAIN) { - return NGX_HTTP_V3_ERR_FRAME_ERROR; - } - - if (rc != NGX_DONE) { - return rc; - } - - rc = ngx_http_v3_set_max_push_id(c, st->vlint.value); - if (rc != NGX_OK) { - return rc; - } - - st->state = sw_type; - break; - - case sw_goaway: - - ngx_http_v3_parse_start_local(b, &loc, st->length); - - rc = ngx_http_v3_parse_varlen_int(c, &st->vlint, &loc); - - ngx_http_v3_parse_end_local(b, &loc, &st->length); - - if (st->length == 0 && rc == NGX_AGAIN) { - return NGX_HTTP_V3_ERR_FRAME_ERROR; - } - - if (rc != NGX_DONE) { - return rc; - } - - rc = ngx_http_v3_goaway(c, st->vlint.value); - if (rc != NGX_OK) { - return rc; - } - - st->state = sw_type; - break; - case sw_skip: rc = ngx_http_v3_parse_skip(b, &st->length); diff --git a/src/http/v3/ngx_http_v3_uni.c b/src/http/v3/ngx_http_v3_uni.c index 22ddaf3..2fc5b07 100644 --- a/src/http/v3/ngx_http_v3_uni.c +++ b/src/http/v3/ngx_http_v3_uni.c @@ -16,19 +16,10 @@ typedef struct { } ngx_http_v3_uni_stream_t; -typedef struct { - ngx_queue_t queue; - uint64_t id; - ngx_connection_t *connection; - ngx_uint_t *npushing; -} ngx_http_v3_push_t; - - static void ngx_http_v3_close_uni_stream(ngx_connection_t *c); static void ngx_http_v3_uni_read_handler(ngx_event_t *rev); static void ngx_http_v3_uni_dummy_read_handler(ngx_event_t *wev); static void ngx_http_v3_uni_dummy_write_handler(ngx_event_t *wev); -static void ngx_http_v3_push_cleanup(void *data); static ngx_connection_t *ngx_http_v3_get_uni_stream(ngx_connection_t *c, ngx_uint_t type); @@ -316,78 +307,6 @@ ngx_http_v3_uni_dummy_write_handler(ngx_event_t *wev) } -ngx_connection_t * -ngx_http_v3_create_push_stream(ngx_connection_t *c, uint64_t push_id) -{ - u_char *p, buf[NGX_HTTP_V3_VARLEN_INT_LEN * 2]; - size_t n; - ngx_connection_t *sc; - ngx_pool_cleanup_t *cln; - ngx_http_v3_push_t *push; - ngx_http_v3_session_t *h3c; - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 create push stream id:%uL", push_id); - - sc = ngx_quic_open_stream(c, 0); - if (sc == NULL) { - goto failed; - } - - p = buf; - p = (u_char *) ngx_http_v3_encode_varlen_int(p, NGX_HTTP_V3_STREAM_PUSH); - p = (u_char *) ngx_http_v3_encode_varlen_int(p, push_id); - n = p - buf; - - h3c = ngx_http_v3_get_session(c); - h3c->total_bytes += n; - - if (sc->send(sc, buf, n) != (ssize_t) n) { - goto failed; - } - - cln = ngx_pool_cleanup_add(sc->pool, sizeof(ngx_http_v3_push_t)); - if (cln == NULL) { - goto failed; - } - - h3c->npushing++; - - cln->handler = ngx_http_v3_push_cleanup; - - push = cln->data; - push->id = push_id; - push->connection = sc; - push->npushing = &h3c->npushing; - - ngx_queue_insert_tail(&h3c->pushing, &push->queue); - - return sc; - -failed: - - ngx_log_error(NGX_LOG_ERR, c->log, 0, "failed to create push stream"); - - ngx_http_v3_finalize_connection(c, NGX_HTTP_V3_ERR_STREAM_CREATION_ERROR, - "failed to create push stream"); - if (sc) { - ngx_http_v3_close_uni_stream(sc); - } - - return NULL; -} - - -static void -ngx_http_v3_push_cleanup(void *data) -{ - ngx_http_v3_push_t *push = data; - - ngx_queue_remove(&push->queue); - (*push->npushing)--; -} - - static ngx_connection_t * ngx_http_v3_get_uni_stream(ngx_connection_t *c, ngx_uint_t type) { @@ -693,82 +612,6 @@ failed: } -ngx_int_t -ngx_http_v3_set_max_push_id(ngx_connection_t *c, uint64_t max_push_id) -{ - ngx_http_v3_session_t *h3c; - - h3c = ngx_http_v3_get_session(c); - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 MAX_PUSH_ID:%uL", max_push_id); - - if (h3c->max_push_id != (uint64_t) -1 && max_push_id < h3c->max_push_id) { - return NGX_HTTP_V3_ERR_ID_ERROR; - } - - h3c->max_push_id = max_push_id; - - return NGX_OK; -} - - -ngx_int_t -ngx_http_v3_goaway(ngx_connection_t *c, uint64_t push_id) -{ - ngx_http_v3_session_t *h3c; - - h3c = ngx_http_v3_get_session(c); - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->log, 0, "http3 GOAWAY:%uL", push_id); - - h3c->goaway_push_id = push_id; - - return NGX_OK; -} - - -ngx_int_t -ngx_http_v3_cancel_push(ngx_connection_t *c, uint64_t push_id) -{ - ngx_queue_t *q; - ngx_http_request_t *r; - ngx_http_v3_push_t *push; - ngx_http_v3_session_t *h3c; - - h3c = ngx_http_v3_get_session(c); - - ngx_log_debug1(NGX_LOG_DEBUG_HTTP, c->log, 0, - "http3 CANCEL_PUSH:%uL", push_id); - - if (push_id >= h3c->next_push_id) { - return NGX_HTTP_V3_ERR_ID_ERROR; - } - - for (q = ngx_queue_head(&h3c->pushing); - q != ngx_queue_sentinel(&h3c->pushing); - q = ngx_queue_next(q)) - { - push = (ngx_http_v3_push_t *) q; - - if (push->id != push_id) { - continue; - } - - r = push->connection->data; - - ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, - "http3 cancel push"); - - ngx_http_finalize_request(r, NGX_HTTP_CLOSE); - - break; - } - - return NGX_OK; -} - - ngx_int_t ngx_http_v3_cancel_stream(ngx_connection_t *c, ngx_uint_t stream_id) { diff --git a/src/http/v3/ngx_http_v3_uni.h b/src/http/v3/ngx_http_v3_uni.h index 8c1eb99..911e153 100644 --- a/src/http/v3/ngx_http_v3_uni.h +++ b/src/http/v3/ngx_http_v3_uni.h @@ -17,12 +17,6 @@ void ngx_http_v3_init_uni_stream(ngx_connection_t *c); ngx_int_t ngx_http_v3_register_uni_stream(ngx_connection_t *c, uint64_t type); -ngx_connection_t *ngx_http_v3_create_push_stream(ngx_connection_t *c, - uint64_t push_id); -ngx_int_t ngx_http_v3_set_max_push_id(ngx_connection_t *c, - uint64_t max_push_id); -ngx_int_t ngx_http_v3_goaway(ngx_connection_t *c, uint64_t push_id); -ngx_int_t ngx_http_v3_cancel_push(ngx_connection_t *c, uint64_t push_id); ngx_int_t ngx_http_v3_cancel_stream(ngx_connection_t *c, ngx_uint_t stream_id); ngx_int_t ngx_http_v3_send_settings(ngx_connection_t *c); diff --git a/src/stream/ngx_stream.c b/src/stream/ngx_stream.c index 4c41af1..3304c84 100644 --- a/src/stream/ngx_stream.c +++ b/src/stream/ngx_stream.c @@ -518,24 +518,6 @@ ngx_stream_optimize_servers(ngx_conf_t *cf, ngx_array_t *ports) ls->reuseport = addr[i].opt.reuseport; #endif -#if (NGX_STREAM_QUIC) - - ls->quic = addr[i].opt.quic; - - if (ls->quic) { - ngx_rbtree_init(&ls->rbtree, &ls->sentinel, - ngx_quic_rbtree_insert_value); - } - -#endif - -#if !(NGX_WIN32) - if (!ls->quic) { - ngx_rbtree_init(&ls->rbtree, &ls->sentinel, - ngx_udp_rbtree_insert_value); - } -#endif - stport = ngx_palloc(cf->pool, sizeof(ngx_stream_port_t)); if (stport == NULL) { return NGX_CONF_ERROR; @@ -593,9 +575,6 @@ ngx_stream_add_addrs(ngx_conf_t *cf, ngx_stream_port_t *stport, addrs[i].conf.ctx = addr[i].opt.ctx; #if (NGX_STREAM_SSL) addrs[i].conf.ssl = addr[i].opt.ssl; -#endif -#if (NGX_STREAM_QUIC) - addrs[i].conf.quic = addr[i].opt.quic; #endif addrs[i].conf.proxy_protocol = addr[i].opt.proxy_protocol; addrs[i].conf.addr_text = addr[i].opt.addr_text; @@ -631,9 +610,6 @@ ngx_stream_add_addrs6(ngx_conf_t *cf, ngx_stream_port_t *stport, addrs6[i].conf.ctx = addr[i].opt.ctx; #if (NGX_STREAM_SSL) addrs6[i].conf.ssl = addr[i].opt.ssl; -#endif -#if (NGX_STREAM_QUIC) - addrs6[i].conf.quic = addr[i].opt.quic; #endif addrs6[i].conf.proxy_protocol = addr[i].opt.proxy_protocol; addrs6[i].conf.addr_text = addr[i].opt.addr_text; diff --git a/src/stream/ngx_stream.h b/src/stream/ngx_stream.h index 8cc95a3..46c3622 100644 --- a/src/stream/ngx_stream.h +++ b/src/stream/ngx_stream.h @@ -16,10 +16,6 @@ #include #endif -#if (NGX_STREAM_QUIC) -#include -#endif - typedef struct ngx_stream_session_s ngx_stream_session_t; @@ -55,7 +51,6 @@ typedef struct { unsigned bind:1; unsigned wildcard:1; unsigned ssl:1; - unsigned quic:1; #if (NGX_HAVE_INET6) unsigned ipv6only:1; #endif @@ -81,7 +76,6 @@ typedef struct { ngx_stream_conf_ctx_t *ctx; ngx_str_t addr_text; unsigned ssl:1; - unsigned quic:1; unsigned proxy_protocol:1; } ngx_stream_addr_conf_t; diff --git a/src/stream/ngx_stream_core_module.c b/src/stream/ngx_stream_core_module.c index 9be1a71..f0b7934 100644 --- a/src/stream/ngx_stream_core_module.c +++ b/src/stream/ngx_stream_core_module.c @@ -760,29 +760,6 @@ ngx_stream_core_listen(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) #endif } - if (ngx_strcmp(value[i].data, "quic") == 0) { -#if (NGX_STREAM_QUIC) - ngx_stream_ssl_conf_t *sslcf; - - sslcf = ngx_stream_conf_get_module_srv_conf(cf, - ngx_stream_ssl_module); - - sslcf->listen = 1; - sslcf->file = cf->conf_file->file.name.data; - sslcf->line = cf->conf_file->line; - - ls->quic = 1; - ls->type = SOCK_DGRAM; - - continue; -#else - ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, - "the \"quic\" parameter requires " - "ngx_stream_quic_module"); - return NGX_CONF_ERROR; -#endif - } - if (ngx_strncmp(value[i].data, "so_keepalive=", 13) == 0) { if (ngx_strcmp(&value[i].data[13], "on") == 0) { @@ -894,12 +871,6 @@ ngx_stream_core_listen(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) } #endif -#if (NGX_STREAM_SSL && NGX_STREAM_QUIC) - if (ls->ssl && ls->quic) { - return "\"ssl\" parameter is incompatible with \"quic\""; - } -#endif - if (ls->so_keepalive) { return "\"so_keepalive\" parameter is incompatible with \"udp\""; } diff --git a/src/stream/ngx_stream_handler.c b/src/stream/ngx_stream_handler.c index 3b95bf8..669b6a1 100644 --- a/src/stream/ngx_stream_handler.c +++ b/src/stream/ngx_stream_handler.c @@ -129,10 +129,6 @@ ngx_stream_init_connection(ngx_connection_t *c) s->ssl = addr_conf->ssl; #endif -#if (NGX_STREAM_QUIC) - s->ssl |= addr_conf->quic; -#endif - if (c->buffer) { s->received += c->buffer->last - c->buffer->pos; } @@ -177,21 +173,6 @@ ngx_stream_init_connection(ngx_connection_t *c) s->start_sec = tp->sec; s->start_msec = tp->msec; -#if (NGX_STREAM_QUIC) - - if (addr_conf->quic) { - ngx_quic_conf_t *qcf; - - if (c->quic == NULL) { - qcf = ngx_stream_get_module_srv_conf(addr_conf->ctx, - ngx_stream_quic_module); - ngx_quic_run(c, qcf); - return; - } - } - -#endif - rev = c->read; rev->handler = ngx_stream_session_handler; diff --git a/src/stream/ngx_stream_proxy_module.c b/src/stream/ngx_stream_proxy_module.c index 20b1adc..ed275c0 100644 --- a/src/stream/ngx_stream_proxy_module.c +++ b/src/stream/ngx_stream_proxy_module.c @@ -1772,21 +1772,6 @@ ngx_stream_proxy_process(ngx_stream_session_t *s, ngx_uint_t from_upstream, if (dst->type == SOCK_STREAM && pscf->half_close && src->read->eof && !u->half_closed && !dst->buffered) { - -#if (NGX_STREAM_QUIC) - if (dst->quic) { - - if (ngx_quic_shutdown_stream(dst, NGX_WRITE_SHUTDOWN) - != NGX_OK) - { - ngx_stream_proxy_finalize(s, - NGX_STREAM_INTERNAL_SERVER_ERROR); - return; - } - - } else -#endif - if (ngx_shutdown_socket(dst->fd, NGX_WRITE_SHUTDOWN) == -1) { ngx_connection_error(c, ngx_socket_errno, ngx_shutdown_socket_n " failed"); diff --git a/src/stream/ngx_stream_quic_module.c b/src/stream/ngx_stream_quic_module.c deleted file mode 100644 index 42f5fe0..0000000 --- a/src/stream/ngx_stream_quic_module.c +++ /dev/null @@ -1,343 +0,0 @@ - -/* - * Copyright (C) Nginx, Inc. - * Copyright (C) Roman Arutyunyan - */ - - -#include -#include -#include - - -static ngx_int_t ngx_stream_variable_quic(ngx_stream_session_t *s, - ngx_stream_variable_value_t *v, uintptr_t data); -static ngx_int_t ngx_stream_quic_add_variables(ngx_conf_t *cf); -static void *ngx_stream_quic_create_srv_conf(ngx_conf_t *cf); -static char *ngx_stream_quic_merge_srv_conf(ngx_conf_t *cf, void *parent, - void *child); -static char *ngx_stream_quic_host_key(ngx_conf_t *cf, ngx_command_t *cmd, - void *conf); - - -static ngx_command_t ngx_stream_quic_commands[] = { - - { ngx_string("quic_timeout"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, - ngx_conf_set_msec_slot, - NGX_STREAM_SRV_CONF_OFFSET, - offsetof(ngx_quic_conf_t, timeout), - NULL }, - - { ngx_string("quic_stream_buffer_size"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, - ngx_conf_set_size_slot, - NGX_STREAM_SRV_CONF_OFFSET, - offsetof(ngx_quic_conf_t, stream_buffer_size), - NULL }, - - { ngx_string("quic_retry"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, - ngx_conf_set_flag_slot, - NGX_STREAM_SRV_CONF_OFFSET, - offsetof(ngx_quic_conf_t, retry), - NULL }, - - { ngx_string("quic_gso"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, - ngx_conf_set_flag_slot, - NGX_STREAM_SRV_CONF_OFFSET, - offsetof(ngx_quic_conf_t, gso_enabled), - NULL }, - - { ngx_string("quic_host_key"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, - ngx_stream_quic_host_key, - NGX_STREAM_SRV_CONF_OFFSET, - 0, - NULL }, - - { ngx_string("quic_active_connection_id_limit"), - NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, - ngx_conf_set_num_slot, - NGX_STREAM_SRV_CONF_OFFSET, - offsetof(ngx_quic_conf_t, active_connection_id_limit), - NULL }, - - ngx_null_command -}; - - -static ngx_stream_module_t ngx_stream_quic_module_ctx = { - ngx_stream_quic_add_variables, /* preconfiguration */ - NULL, /* postconfiguration */ - - NULL, /* create main configuration */ - NULL, /* init main configuration */ - - ngx_stream_quic_create_srv_conf, /* create server configuration */ - ngx_stream_quic_merge_srv_conf, /* merge server configuration */ -}; - - -ngx_module_t ngx_stream_quic_module = { - NGX_MODULE_V1, - &ngx_stream_quic_module_ctx, /* module context */ - ngx_stream_quic_commands, /* module directives */ - NGX_STREAM_MODULE, /* module type */ - NULL, /* init master */ - NULL, /* init module */ - NULL, /* init process */ - NULL, /* init thread */ - NULL, /* exit thread */ - NULL, /* exit process */ - NULL, /* exit master */ - NGX_MODULE_V1_PADDING -}; - - -static ngx_stream_variable_t ngx_stream_quic_vars[] = { - - { ngx_string("quic"), NULL, ngx_stream_variable_quic, 0, 0, 0 }, - - ngx_stream_null_variable -}; - -static ngx_str_t ngx_stream_quic_salt = ngx_string("ngx_quic"); - - -static ngx_int_t -ngx_stream_variable_quic(ngx_stream_session_t *s, - ngx_stream_variable_value_t *v, uintptr_t data) -{ - if (s->connection->quic) { - - v->len = 4; - v->valid = 1; - v->no_cacheable = 1; - v->not_found = 0; - v->data = (u_char *) "quic"; - return NGX_OK; - } - - v->not_found = 1; - - return NGX_OK; -} - - -static ngx_int_t -ngx_stream_quic_add_variables(ngx_conf_t *cf) -{ - ngx_stream_variable_t *var, *v; - - for (v = ngx_stream_quic_vars; v->name.len; v++) { - var = ngx_stream_add_variable(cf, &v->name, v->flags); - if (var == NULL) { - return NGX_ERROR; - } - - var->get_handler = v->get_handler; - var->data = v->data; - } - - return NGX_OK; -} - - -static void * -ngx_stream_quic_create_srv_conf(ngx_conf_t *cf) -{ - ngx_quic_conf_t *conf; - - conf = ngx_pcalloc(cf->pool, sizeof(ngx_quic_conf_t)); - if (conf == NULL) { - return NULL; - } - - /* - * set by ngx_pcalloc(): - * - * conf->host_key = { 0, NULL } - * conf->stream_close_code = 0; - * conf->stream_reject_code_uni = 0; - * conf->stream_reject_code_bidi= 0; - */ - - conf->timeout = NGX_CONF_UNSET_MSEC; - conf->stream_buffer_size = NGX_CONF_UNSET_SIZE; - conf->max_concurrent_streams_bidi = NGX_CONF_UNSET_UINT; - conf->max_concurrent_streams_uni = NGX_CONF_UNSET_UINT; - - conf->retry = NGX_CONF_UNSET; - conf->gso_enabled = NGX_CONF_UNSET; - - conf->active_connection_id_limit = NGX_CONF_UNSET_UINT; - - return conf; -} - - -static char * -ngx_stream_quic_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child) -{ - ngx_quic_conf_t *prev = parent; - ngx_quic_conf_t *conf = child; - - ngx_stream_ssl_conf_t *scf; - - ngx_conf_merge_msec_value(conf->timeout, prev->timeout, 60000); - - ngx_conf_merge_size_value(conf->stream_buffer_size, - prev->stream_buffer_size, - 65536); - - ngx_conf_merge_uint_value(conf->max_concurrent_streams_bidi, - prev->max_concurrent_streams_bidi, 16); - - ngx_conf_merge_uint_value(conf->max_concurrent_streams_uni, - prev->max_concurrent_streams_uni, 3); - - ngx_conf_merge_value(conf->retry, prev->retry, 0); - ngx_conf_merge_value(conf->gso_enabled, prev->gso_enabled, 0); - - ngx_conf_merge_str_value(conf->host_key, prev->host_key, ""); - - ngx_conf_merge_uint_value(conf->active_connection_id_limit, - conf->active_connection_id_limit, - 2); - - if (conf->host_key.len == 0) { - - conf->host_key.len = NGX_QUIC_DEFAULT_HOST_KEY_LEN; - conf->host_key.data = ngx_palloc(cf->pool, conf->host_key.len); - if (conf->host_key.data == NULL) { - return NGX_CONF_ERROR; - } - - if (RAND_bytes(conf->host_key.data, NGX_QUIC_DEFAULT_HOST_KEY_LEN) - <= 0) - { - return NGX_CONF_ERROR; - } - } - - if (ngx_quic_derive_key(cf->log, "av_token_key", - &conf->host_key, &ngx_stream_quic_salt, - conf->av_token_key, NGX_QUIC_AV_KEY_LEN) - != NGX_OK) - { - return NGX_CONF_ERROR; - } - - if (ngx_quic_derive_key(cf->log, "sr_token_key", - &conf->host_key, &ngx_stream_quic_salt, - conf->sr_token_key, NGX_QUIC_SR_KEY_LEN) - != NGX_OK) - { - return NGX_CONF_ERROR; - } - - scf = ngx_stream_conf_get_module_srv_conf(cf, ngx_stream_ssl_module); - conf->ssl = &scf->ssl; - - return NGX_CONF_OK; -} - - -static char * -ngx_stream_quic_host_key(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) -{ - ngx_quic_conf_t *qcf = conf; - - u_char *buf; - size_t size; - ssize_t n; - ngx_str_t *value; - ngx_file_t file; - ngx_file_info_t fi; - - if (qcf->host_key.len) { - return "is duplicate"; - } - - buf = NULL; -#if (NGX_SUPPRESS_WARN) - size = 0; -#endif - - value = cf->args->elts; - - if (ngx_conf_full_name(cf->cycle, &value[1], 1) != NGX_OK) { - return NGX_CONF_ERROR; - } - - ngx_memzero(&file, sizeof(ngx_file_t)); - file.name = value[1]; - file.log = cf->log; - - file.fd = ngx_open_file(file.name.data, NGX_FILE_RDONLY, NGX_FILE_OPEN, 0); - - if (file.fd == NGX_INVALID_FILE) { - ngx_conf_log_error(NGX_LOG_EMERG, cf, ngx_errno, - ngx_open_file_n " \"%V\" failed", &file.name); - return NGX_CONF_ERROR; - } - - if (ngx_fd_info(file.fd, &fi) == NGX_FILE_ERROR) { - ngx_conf_log_error(NGX_LOG_CRIT, cf, ngx_errno, - ngx_fd_info_n " \"%V\" failed", &file.name); - goto failed; - } - - size = ngx_file_size(&fi); - - if (size == 0) { - ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, - "\"%V\" zero key size", &file.name); - goto failed; - } - - buf = ngx_pnalloc(cf->pool, size); - if (buf == NULL) { - goto failed; - } - - n = ngx_read_file(&file, buf, size, 0); - - if (n == NGX_ERROR) { - ngx_conf_log_error(NGX_LOG_CRIT, cf, ngx_errno, - ngx_read_file_n " \"%V\" failed", &file.name); - goto failed; - } - - if ((size_t) n != size) { - ngx_conf_log_error(NGX_LOG_CRIT, cf, 0, - ngx_read_file_n " \"%V\" returned only " - "%z bytes instead of %uz", &file.name, n, size); - goto failed; - } - - qcf->host_key.data = buf; - qcf->host_key.len = n; - - if (ngx_close_file(file.fd) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ALERT, cf->log, ngx_errno, - ngx_close_file_n " \"%V\" failed", &file.name); - } - - return NGX_CONF_OK; - -failed: - - if (ngx_close_file(file.fd) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ALERT, cf->log, ngx_errno, - ngx_close_file_n " \"%V\" failed", &file.name); - } - - if (buf) { - ngx_explicit_memzero(buf, size); - } - - return NGX_CONF_ERROR; -} diff --git a/src/stream/ngx_stream_quic_module.h b/src/stream/ngx_stream_quic_module.h deleted file mode 100644 index 6ac4d96..0000000 --- a/src/stream/ngx_stream_quic_module.h +++ /dev/null @@ -1,20 +0,0 @@ - -/* - * Copyright (C) Roman Arutyunyan - * Copyright (C) Nginx, Inc. - */ - - -#ifndef _NGX_STREAM_QUIC_H_INCLUDED_ -#define _NGX_STREAM_QUIC_H_INCLUDED_ - - -#include -#include -#include - - -extern ngx_module_t ngx_stream_quic_module; - - -#endif /* _NGX_STREAM_QUIC_H_INCLUDED_ */ diff --git a/src/stream/ngx_stream_ssl_module.c b/src/stream/ngx_stream_ssl_module.c index 564ceca..08642c8 100644 --- a/src/stream/ngx_stream_ssl_module.c +++ b/src/stream/ngx_stream_ssl_module.c @@ -9,10 +9,6 @@ #include #include -#if (NGX_QUIC_OPENSSL_COMPAT) -#include -#endif - typedef ngx_int_t (*ngx_ssl_variable_handler_pt)(ngx_connection_t *c, ngx_pool_t *pool, ngx_str_t *s); @@ -1197,10 +1193,7 @@ ngx_stream_ssl_conf_command_check(ngx_conf_t *cf, void *post, void *data) static ngx_int_t ngx_stream_ssl_init(ngx_conf_t *cf) { - ngx_uint_t i; - ngx_stream_listen_t *listen; ngx_stream_handler_pt *h; - ngx_stream_ssl_conf_t *scf; ngx_stream_core_main_conf_t *cmcf; cmcf = ngx_stream_conf_get_module_main_conf(cf, ngx_stream_core_module); @@ -1212,29 +1205,5 @@ ngx_stream_ssl_init(ngx_conf_t *cf) *h = ngx_stream_ssl_handler; - listen = cmcf->listen.elts; - - for (i = 0; i < cmcf->listen.nelts; i++) { - if (!listen[i].quic) { - continue; - } - - scf = listen[i].ctx->srv_conf[ngx_stream_ssl_module.ctx_index]; - -#if (NGX_QUIC_OPENSSL_COMPAT) - if (ngx_quic_compat_init(cf, scf->ssl.ctx) != NGX_OK) { - return NGX_ERROR; - } -#endif - - if (scf->certificates && !(scf->protocols & NGX_SSL_TLSv1_3)) { - ngx_log_error(NGX_LOG_EMERG, cf->log, 0, - "\"ssl_protocols\" must enable TLSv1.3 for " - "the \"listen ... quic\" directive in %s:%ui", - scf->file, scf->line); - return NGX_ERROR; - } - } - return NGX_OK; } diff --git a/src/stream/ngx_stream_write_filter_module.c b/src/stream/ngx_stream_write_filter_module.c index d8a72f9..07dc7b5 100644 --- a/src/stream/ngx_stream_write_filter_module.c +++ b/src/stream/ngx_stream_write_filter_module.c @@ -277,12 +277,7 @@ ngx_stream_write_filter(ngx_stream_session_t *s, ngx_chain_t *in, *out = chain; if (chain) { - if (c->shared -#if (NGX_STREAM_QUIC) - && c->quic == NULL -#endif - ) - { + if (c->shared) { ngx_log_error(NGX_LOG_ALERT, c->log, 0, "shared connection is busy"); return NGX_ERROR;