Opened 6 years ago
Closed 6 years ago
#1797 closed defect (fixed)
grpc module handles WINDOW_UPDATE improperly on closed streams
| Reported by: | Owned by: | ||
|---|---|---|---|
| Priority: | minor | Milestone: | |
| Component: | other | Version: | 1.15.x |
| Keywords: | grpc | Cc: | |
| uname -a: | Linux 4.15.0-52-generic #56~16.04.1-Ubuntu SMP Thu Jun 6 12:03:31 UTC 2019 x86_64 x86_64 x86_64 GNU/Linux | ||
| nginx -V: |
nginx version: nginx/1.15.6
built by Bazel built by gcc 4.9.4 (Ubuntu 4.9.4-2ubuntu1~12.04) built with OpenSSL 1.1.0 (compatible; BoringSSL) (running with BoringSSL) TLS SNI support enabled configure arguments: --prefix=/etc/nginx --conf-path=/etc/nginx/nginx.conf --error-log-path=/var/log/nginx/error.log --pid-path=/var/run/nginx.pid --lock-path=/var/lock/nginx.lock --user=nginx --group=nginx --http-log-path=/var/log/nginx/access.log --http-client-body-temp-path=/var/lib/nginx/client_temp --http-fastcgi-temp-path=/var/lib/nginx/fastcgi_temp --http-proxy-temp-path=/var/lib/nginx/proxy_temp --http-scgi-temp-path=/var/lib/nginx/scgi_temp --http-uwsgi-temp-path=/var/lib/nginx/uwsgi_temp --with-compat --with-file-aio --with-threads --add-module=@ngx_brotli//:http_brotli_filter --add-module=@ngx_brotli//:http_brotli_static --add-module=@ngx_http_headers_more_filter//:http_headers_more_filter --add-module=@ngx_http_ip_tos_filter//:http_ip_tos_filter --add-module=@ngx_http_lua//:http_lua --add-module=dbx_dials_module --add-module=modules/nginx_upstream_check_module --add-module=modules/ngx_http_upstream_dynamic_module --add-module=ngx_http_streaming_filter --with-http_auth_request_module --with-http_gzip_static_module --with-http_realip_module --with-http_ssl_module --with-http_v2_module --with-openssl=boringssl --with-stream |
||
Description
Current implementation fails the request on receiving WINDOW_UPDATE frame for closed upstream:
upstream sent frame for closed stream 1 while reading response header from upstream, client: 127.0.0.1, server: test, request: "POST /test.RequestIdEcho/StreamStream HTTP/2.0", upstream: "grpcs://127.0.0.1:5015", host: "test_user1"
But it shouldn't per the RFC: https://tools.ietf.org/html/rfc7540#section-5.1:
closed:
The "closed" state is the terminal state.
WINDOW_UPDATE or RST_STREAM frames can be received in this state
for a short period after a DATA or HEADERS frame containing an
END_STREAM flag is sent. Until the remote peer receives and
processes RST_STREAM or the frame bearing the END_STREAM flag, it
might send frames of these types. Endpoints MUST ignore
WINDOW_UPDATE or RST_STREAM frames received in this state, though
endpoints MAY choose to treat frames that arrive a significant
time after sending END_STREAM as a connection error
(Section 5.4.1) of type PROTOCOL_ERROR.
nginx with following patch passes the testcase:
diff --git a/src/http/modules/ngx_http_grpc_module.c b/src/http/modules/ngx_http_grpc_module.c
index e79c3224..d78409dc 100644
--- a/src/http/modules/ngx_http_grpc_module.c
+++ b/src/http/modules/ngx_http_grpc_module.c
@@ -1973,7 +1973,9 @@ ngx_http_grpc_filter(void *data, ssize_t bytes)
}
if (ctx->stream_id && ctx->done
- && ctx->type != NGX_HTTP_V2_RST_STREAM_FRAME)
+ && ctx->type != NGX_HTTP_V2_RST_STREAM_FRAME
+ && ctx->type != NGX_HTTP_V2_WINDOW_UPDATE_FRAME)
+
{
ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
"upstream sent frame for closed stream %ui",
Note:
See TracTickets
for help on using tickets.

Yep, I considered this addition when cooking patch for ticket #1792.
It makes sense for me.