diff --git a/.hgtags b/.hgtags index 58e35ca..04a512b 100644 --- a/.hgtags +++ b/.hgtags @@ -431,3 +431,4 @@ b234199c7ed8a156a6bb98f7ff58302c857c954f release-1.15.2 28b3e17ca7eba1e6a0891afde0e4bc5bcc99c861 release-1.15.3 49d49835653857daa418e68d6cbfed4958c78fca release-1.15.4 f062e43d74fc2578bb100a9e82a953efa1eb9e4e release-1.15.5 +2351853ce6867b6166823bdf94333c0a76633c0a release-1.15.6 diff --git a/docs/xml/nginx/changes.xml b/docs/xml/nginx/changes.xml index dfff0a7..43a21e5 100644 --- a/docs/xml/nginx/changes.xml +++ b/docs/xml/nginx/changes.xml @@ -5,6 +5,70 @@ + + + + +при использовании HTTP/2 клиент мог вызвать +чрезмерное потреблению памяти (CVE-2018-16843) +и ресурсов процессора (CVE-2018-16844). + + +when using HTTP/2 a client might cause +excessive memory consumption (CVE-2018-16843) +and CPU usage (CVE-2018-16844). + + + + + +при обработке специально созданного mp4-файла модулем ngx_http_mp4_module +содержимое памяти рабочего процесса могло быть отправлено клиенту +(CVE-2018-16845). + + +processing of a specially crafted mp4 file with the ngx_http_mp4_module +might result in worker process memory disclosure +(CVE-2018-16845). + + + + + +директивы proxy_socket_keepalive, fastcgi_socket_keepalive, +grpc_socket_keepalive, memcached_socket_keepalive, +scgi_socket_keepalive и uwsgi_socket_keepalive. + + +the "proxy_socket_keepalive", "fastcgi_socket_keepalive", +"grpc_socket_keepalive", "memcached_socket_keepalive", +"scgi_socket_keepalive", and "uwsgi_socket_keepalive" directives. + + + + + +если nginx был собран с OpenSSL 1.1.0, а использовался с OpenSSL 1.1.1, +протокол TLS 1.3 всегда был разрешён. + + +if nginx was built with OpenSSL 1.1.0 and used with OpenSSL 1.1.1, +the TLS 1.3 protocol was always enabled. + + + + + +при работе с gRPC-бэкендами могло расходоваться большое количество памяти. + + +working with gRPC backends might result in excessive memory consumption. + + + + + + diff --git a/src/core/nginx.h b/src/core/nginx.h index d9e4bd9..6e14020 100644 --- a/src/core/nginx.h +++ b/src/core/nginx.h @@ -9,8 +9,8 @@ #define _NGINX_H_INCLUDED_ -#define nginx_version 1015006 -#define NGINX_VERSION "1.15.6" +#define nginx_version 1015007 +#define NGINX_VERSION "1.15.7" #define NGINX_VER "nginx/" NGINX_VERSION " by Hakase" #ifndef NGINX_SERVER diff --git a/src/http/modules/ngx_http_grpc_module.c b/src/http/modules/ngx_http_grpc_module.c index e6e11b0..18478b9 100644 --- a/src/http/modules/ngx_http_grpc_module.c +++ b/src/http/modules/ngx_http_grpc_module.c @@ -78,6 +78,9 @@ typedef struct { ngx_uint_t id; + ngx_uint_t pings; + ngx_uint_t settings; + ssize_t send_window; size_t recv_window; @@ -3584,6 +3587,12 @@ ngx_http_grpc_parse_settings(ngx_http_request_t *r, ngx_http_grpc_ctx_t *ctx, ctx->rest); return NGX_ERROR; } + + if (ctx->free == NULL && ctx->settings++ > 1000) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, 0, + "upstream sent too many settings frames"); + return NGX_ERROR; + } } for (p = b->pos; p < last; p++) { @@ -3736,6 +3745,12 @@ ngx_http_grpc_parse_ping(ngx_http_request_t *r, "upstream sent ping frame with ack flag"); return NGX_ERROR; } + + if (ctx->free == NULL && ctx->pings++ > 1000) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, 0, + "upstream sent too many ping frames"); + return NGX_ERROR; + } } for (p = b->pos; p < last; p++) { diff --git a/src/http/modules/ngx_http_mp4_module.c b/src/http/modules/ngx_http_mp4_module.c index 08a68d0..2a6fafa 100644 --- a/src/http/modules/ngx_http_mp4_module.c +++ b/src/http/modules/ngx_http_mp4_module.c @@ -942,6 +942,13 @@ ngx_http_mp4_read_atom(ngx_http_mp4_file_t *mp4, atom_size = ngx_mp4_get_64value(atom_header + 8); atom_header_size = sizeof(ngx_mp4_atom_header64_t); + if (atom_size < sizeof(ngx_mp4_atom_header64_t)) { + ngx_log_error(NGX_LOG_ERR, mp4->file.log, 0, + "\"%s\" mp4 atom is too small:%uL", + mp4->file.name.data, atom_size); + return NGX_ERROR; + } + } else { ngx_log_error(NGX_LOG_ERR, mp4->file.log, 0, "\"%s\" mp4 atom is too small:%uL", diff --git a/src/http/v2/ngx_http_v2.c b/src/http/v2/ngx_http_v2.c index 876e63c..2d95796 100644 --- a/src/http/v2/ngx_http_v2.c +++ b/src/http/v2/ngx_http_v2.c @@ -664,6 +664,7 @@ ngx_http_v2_handle_connection(ngx_http_v2_connection_t *h2c) h2c->pool = NULL; h2c->free_frames = NULL; + h2c->frames = 0; h2c->free_fake_connections = NULL; #if (NGX_HTTP_SSL) @@ -2905,7 +2906,7 @@ ngx_http_v2_get_frame(ngx_http_v2_connection_t *h2c, size_t length, frame->blocked = 0; - } else { + } else if (h2c->frames < 10000) { pool = h2c->pool ? h2c->pool : h2c->connection->pool; frame = ngx_pcalloc(pool, sizeof(ngx_http_v2_out_frame_t)); @@ -2929,6 +2930,15 @@ ngx_http_v2_get_frame(ngx_http_v2_connection_t *h2c, size_t length, frame->last = frame->first; frame->handler = ngx_http_v2_frame_handler; + + h2c->frames++; + + } else { + ngx_log_error(NGX_LOG_INFO, h2c->connection->log, 0, + "http2 flood detected"); + + h2c->connection->error = 1; + return NULL; } #if (NGX_DEBUG) @@ -4511,12 +4521,19 @@ ngx_http_v2_idle_handler(ngx_event_t *rev) #endif - c->destroyed = 0; - ngx_reusable_connection(c, 0); - h2scf = ngx_http_get_module_srv_conf(h2c->http_connection->conf_ctx, ngx_http_v2_module); + if (h2c->idle++ > 10 * h2scf->max_requests) { + ngx_log_error(NGX_LOG_INFO, h2c->connection->log, 0, + "http2 flood detected"); + ngx_http_v2_finalize_connection(h2c, NGX_HTTP_V2_NO_ERROR); + return; + } + + c->destroyed = 0; + ngx_reusable_connection(c, 0); + h2c->pool = ngx_create_pool(h2scf->pool_size, h2c->connection->log); if (h2c->pool == NULL) { ngx_http_v2_finalize_connection(h2c, NGX_HTTP_V2_INTERNAL_ERROR); diff --git a/src/http/v2/ngx_http_v2.h b/src/http/v2/ngx_http_v2.h index 41086a6..09b2c1d 100644 --- a/src/http/v2/ngx_http_v2.h +++ b/src/http/v2/ngx_http_v2.h @@ -168,6 +168,8 @@ struct ngx_http_v2_connection_s { ngx_http_connection_t *http_connection; ngx_uint_t processing; + ngx_uint_t frames; + ngx_uint_t idle; ngx_uint_t pushing; ngx_uint_t concurrent_pushes;