diff options
author | Igor Sysoev <igor@sysoev.ru> | 2005-06-15 22:33:41 +0400 |
---|---|---|
committer | Igor Sysoev <igor@sysoev.ru> | 2005-06-15 22:33:41 +0400 |
commit | b145b067e296fd0c72d764e36db7a97102045b2c (patch) | |
tree | 1604c71100a9ea0dc0be0f848ed7ed9dc7108843 /src/core | |
parent | e08f105e27475ea77f5ceb39fc76d9cb2ba078d1 (diff) |
nginx-0.1.36-RELEASE importrelease-0.1.36
*) Change: if the request header has duplicate the "Host",
"Connection", "Content-Length", or "Authorization" lines, then nginx
now returns the 400 error.
*) Change: the "post_accept_timeout" directive was canceled.
*) Feature: the "default", "af=", "bl=", "deferred", and "bind"
parameters of the "listen" directive.
*) Feature: the FreeBSD accept filters support.
*) Feature: the Linux TCP_DEFER_ACCEPT support.
*) Bugfix: the ngx_http_autoindex_module did not support the file names
in UTF-8.
*) Bugfix: the new log file can be rotated by the -USR1 signal only if
the reconfiguration by the -HUP signal was made twice.
Diffstat (limited to 'src/core')
-rw-r--r-- | src/core/nginx.c | 2 | ||||
-rw-r--r-- | src/core/nginx.h | 2 | ||||
-rw-r--r-- | src/core/ngx_connection.c | 65 | ||||
-rw-r--r-- | src/core/ngx_connection.h | 8 | ||||
-rw-r--r-- | src/core/ngx_cycle.c | 156 | ||||
-rw-r--r-- | src/core/ngx_string.c | 51 | ||||
-rw-r--r-- | src/core/ngx_string.h | 2 |
7 files changed, 242 insertions, 44 deletions
diff --git a/src/core/nginx.c b/src/core/nginx.c index 4a01acdd0..d04d95499 100644 --- a/src/core/nginx.c +++ b/src/core/nginx.c @@ -301,6 +301,8 @@ ngx_add_inherited_sockets(ngx_cycle_t *cycle) return NGX_ERROR; } + ngx_memzero(ls, sizeof(ngx_listening_t)); + ls->fd = (ngx_socket_t) s; } } diff --git a/src/core/nginx.h b/src/core/nginx.h index 94b6da3e0..4e9ff796a 100644 --- a/src/core/nginx.h +++ b/src/core/nginx.h @@ -8,7 +8,7 @@ #define _NGINX_H_INCLUDED_ -#define NGINX_VER "nginx/0.1.35" +#define NGINX_VER "nginx/0.1.36" #define NGINX_VAR "NGINX" #define NGX_NEWPID_EXT ".newbin" diff --git a/src/core/ngx_connection.c b/src/core/ngx_connection.c index ff9c16457..b873db2e8 100644 --- a/src/core/ngx_connection.c +++ b/src/core/ngx_connection.c @@ -62,10 +62,18 @@ ngx_listening_inet_stream_socket(ngx_conf_t *cf, in_addr_t addr, in_port_t port) ngx_int_t ngx_set_inherited_sockets(ngx_cycle_t *cycle) { - size_t len; - ngx_uint_t i; - ngx_listening_t *ls; - struct sockaddr_in *sin; + size_t len; + ngx_uint_t i; + ngx_listening_t *ls; + struct sockaddr_in *sin; +#if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) + socklen_t aflen; + struct accept_filter_arg af; +#endif +#if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) + socklen_t tlen; + int timeout; +#endif ls = cycle->listening.elts; for (i = 0; i < cycle->listening.nelts; i++) { @@ -98,7 +106,6 @@ ngx_set_inherited_sockets(ngx_cycle_t *cycle) ls[i].addr_text_max_len = INET_ADDRSTRLEN; - ls[i].addr_text.data = ngx_palloc(cycle->pool, INET_ADDRSTRLEN - 1 + sizeof(":65535") - 1); if (ls[i].addr_text.data == NULL) { @@ -115,6 +122,54 @@ ngx_set_inherited_sockets(ngx_cycle_t *cycle) ls[i].addr_text.len = ngx_sprintf(ls[i].addr_text.data + len, ":%d", ntohs(sin->sin_port)) - ls[i].addr_text.data; + +#if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) + + ngx_memzero(&af, sizeof(struct accept_filter_arg)); + aflen = sizeof(struct accept_filter_arg); + + if (getsockopt(ls[i].fd, SOL_SOCKET, SO_ACCEPTFILTER, &af, &aflen) + == -1) + { + ngx_log_error(NGX_LOG_NOTICE, cycle->log, ngx_errno, + "getsockopt(SO_ACCEPTFILTER) for %V failed, ignored", + &ls[i].addr_text); + continue; + } + + if (aflen < sizeof(struct accept_filter_arg) || af.af_name[0] == '\0') { + continue; + } + + ls[i].accept_filter = ngx_palloc(cycle->pool, 16); + if (ls[i].accept_filter == NULL) { + return NGX_ERROR; + } + + (void) ngx_cpystrn((u_char *) ls[i].accept_filter, + (u_char *) af.af_name, 16); +#endif + +#if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) + + timeout = 0; + tlen = sizeof(int); + + if (getsockopt(ls[i].fd, IPPROTO_TCP, TCP_DEFER_ACCEPT, &timeout, &tlen) + == -1) + { + ngx_log_error(NGX_LOG_NOTICE, cycle->log, ngx_errno, + "getsockopt(TCP_DEFER_ACCEPT) for %V failed, ignored", + &ls[i].addr_text); + continue; + } + + if (tlen < sizeof(int) || timeout == 0) { + continue; + } + + ls[i].deferred_accept = 1; +#endif } return NGX_OK; diff --git a/src/core/ngx_connection.h b/src/core/ngx_connection.h index 8fb67057c..0224d98dd 100644 --- a/src/core/ngx_connection.h +++ b/src/core/ngx_connection.h @@ -47,11 +47,17 @@ typedef struct { unsigned nonblocking_accept:1; unsigned nonblocking:1; unsigned shared:1; /* shared between threads or processes */ + unsigned addr_ntop:1; + #if (NGX_HAVE_DEFERRED_ACCEPT) unsigned deferred_accept:1; + unsigned delete_deferred:1; + unsigned add_deferred:1; +#ifdef SO_ACCEPTFILTER + char *accept_filter; +#endif #endif - unsigned addr_ntop:1; } ngx_listening_t; diff --git a/src/core/ngx_cycle.c b/src/core/ngx_cycle.c index 3a1c00e65..57806437a 100644 --- a/src/core/ngx_cycle.c +++ b/src/core/ngx_cycle.c @@ -39,18 +39,24 @@ static ngx_str_t error_log = ngx_null_string; ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle) { - void *rv; - ngx_uint_t i, n, failed; - ngx_log_t *log; - ngx_conf_t conf; - ngx_pool_t *pool; - ngx_cycle_t *cycle, **old; - ngx_socket_t fd; - ngx_list_part_t *part; - ngx_open_file_t *file; - ngx_listening_t *ls, *nls; - ngx_core_conf_t *ccf; - ngx_core_module_t *module; + void *rv; + ngx_uint_t i, n, failed; + ngx_log_t *log; + ngx_conf_t conf; + ngx_pool_t *pool; + ngx_cycle_t *cycle, **old; + ngx_socket_t fd; + ngx_list_part_t *part; + ngx_open_file_t *file; + ngx_listening_t *ls, *nls; + ngx_core_conf_t *ccf; + ngx_core_module_t *module; +#if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) + struct accept_filter_arg af; +#endif +#if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) + int timeout; +#endif log = old_cycle->log; @@ -307,7 +313,7 @@ ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle) } if (ngx_cmp_sockaddr(nls[n].sockaddr, ls[i].sockaddr) - == NGX_OK) + == NGX_OK) { fd = ls[i].fd; #if (NGX_WIN32) @@ -330,8 +336,44 @@ ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle) } nls[n].fd = ls[i].fd; - nls[i].remain = 1; + nls[n].remain = 1; ls[i].remain = 1; + +#if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) + + /* + * FreeBSD, except the most recent versions, + * can not remove accept filter + */ + nls[n].deferred_accept = ls[i].deferred_accept; + + if (ls[i].accept_filter && nls[n].accept_filter) { + if (ngx_strcmp(ls[i].accept_filter, + nls[n].accept_filter) != 0) + { + nls[n].delete_deferred = 1; + nls[n].add_deferred = 1; + } + + } else if (ls[i].accept_filter) { + nls[n].delete_deferred = 1; + + } else if (nls[n].accept_filter) { + nls[n].add_deferred = 1; + } +#endif + +#if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) + + if (ls[n].deferred_accept && !nls[n].deferred_accept) { + nls[n].delete_deferred = 1; + + } else if (ls[i].deferred_accept + != nls[n].deferred_accept) + { + nls[n].add_deferred = 1; + } +#endif break; } } @@ -345,6 +387,16 @@ ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle) ls = cycle->listening.elts; for (i = 0; i < cycle->listening.nelts; i++) { ls[i].open = 1; +#if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) + if (ls[i].accept_filter) { + ls[i].add_deferred = 1; + } +#endif +#if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) + if (ls[i].deferred_accept) { + ls[i].add_deferred = 1; + } +#endif } } @@ -352,6 +404,81 @@ ngx_cycle_t *ngx_init_cycle(ngx_cycle_t *old_cycle) if (ngx_open_listening_sockets(cycle) == NGX_ERROR) { failed = 1; } + +#if (NGX_HAVE_DEFERRED_ACCEPT) + + if (!failed) { + ls = cycle->listening.elts; + for (i = 0; i < cycle->listening.nelts; i++) { + +#ifdef SO_ACCEPTFILTER + if (ls[i].delete_deferred) { + if (setsockopt(ls[i].fd, SOL_SOCKET, SO_ACCEPTFILTER, + NULL, 0) == -1) + { + ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, + "setsockopt(SO_ACCEPTFILTER, NULL) " + "for %V failed, ignored", + &ls[i].addr_text); + + if (ls[i].accept_filter) { + ngx_log_error(NGX_LOG_ALERT, log, 0, + "could not change the accept filter " + "to \"%s\" for %V, ignored", + ls[i].accept_filter, &ls[i].addr_text); + } + + continue; + } + + ls[i].deferred_accept = 0; + } + + if (ls[i].add_deferred) { + ngx_memzero(&af, sizeof(struct accept_filter_arg)); + (void) ngx_cpystrn((u_char *) af.af_name, + (u_char *) ls[i].accept_filter, 16); + + if (setsockopt(ls[i].fd, SOL_SOCKET, SO_ACCEPTFILTER, + &af, sizeof(struct accept_filter_arg)) == -1) + { + ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, + "setsockopt(SO_ACCEPTFILTER, \"%s\") " + "for %V failed, ignored", + ls[i].accept_filter, &ls[i].addr_text); + continue; + } + + ls[i].deferred_accept = 1; + } +#endif + +#ifdef TCP_DEFER_ACCEPT + if (ls[i].add_deferred || ls[i].delete_deferred) { + timeout = 0; + + if (ls[i].add_deferred) { + timeout = (int) (ls[i].post_accept_timeout / 1000); + } + + if (setsockopt(ls[i].fd, IPPROTO_TCP, TCP_DEFER_ACCEPT, + &timeout, sizeof(int)) == -1) + { + ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, + "setsockopt(TCP_DEFER_ACCEPT, %d) " + "for %V failed, ignored", + timeout, &ls[i].addr_text); + continue; + } + } + + if (ls[i].add_deferred) { + ls[i].deferred_accept = 1; + } +#endif + } + } +#endif } } @@ -682,6 +809,7 @@ void ngx_reopen_files(ngx_cycle_t *cycle, ngx_uid_t user) break; } part = part->next; + file = part->elts; i = 0; } diff --git a/src/core/ngx_string.c b/src/core/ngx_string.c index acc4bd302..9cbf3c92a 100644 --- a/src/core/ngx_string.c +++ b/src/core/ngx_string.c @@ -728,6 +728,35 @@ ngx_decode_base64(ngx_str_t *dst, ngx_str_t *src) } +size_t +ngx_utf_length(ngx_str_t *utf) +{ + u_char c; + size_t len; + ngx_uint_t i; + + for (len = 0, i = 0; i < utf->len; len++, i++) { + + c = utf->data[i]; + + if (c < 0x80) { + continue; + } + + if (c < 0xC0) { + /* invalid utf */ + return utf->len; + } + + for (c <<= 1; c & 0x80; c <<= 1) { + i++; + } + } + + return len; +} + + uintptr_t ngx_escape_uri(u_char *dst, u_char *src, size_t size, ngx_uint_t type) { @@ -792,30 +821,8 @@ ngx_escape_uri(u_char *dst, u_char *src, size_t size, ngx_uint_t type) 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ }; - /* " ", """, "%", "'", %00-%1F, %7F-%FF */ - - static uint32_t utf[] = - { 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ - - /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ - 0x800000ad, /* 0000 0000 0000 0000 0000 0000 1010 1101 */ - - /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ - 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ - - /* ~}| {zyx wvut srqp onml kjih gfed cba` */ - 0x80000000, /* 1000 0000 0000 0000 0000 0000 0000 0000 */ - - 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ - 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ - 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ - 0x00000000 /* 0000 0000 0000 0000 0000 0000 0000 0000 */ }; - switch (type) { - case NGX_ESCAPE_UTF: - escape = utf; - break; case NGX_ESCAPE_HTML: escape = html; break; diff --git a/src/core/ngx_string.h b/src/core/ngx_string.h index e2e20e1f3..ff21619ae 100644 --- a/src/core/ngx_string.h +++ b/src/core/ngx_string.h @@ -96,11 +96,11 @@ void ngx_md5_text(u_char *text, u_char *md5); void ngx_encode_base64(ngx_str_t *dst, ngx_str_t *src); ngx_int_t ngx_decode_base64(ngx_str_t *dst, ngx_str_t *src); +size_t ngx_utf_length(ngx_str_t *utf); #define NGX_ESCAPE_URI 0 #define NGX_ESCAPE_ARGS 1 #define NGX_ESCAPE_HTML 2 -#define NGX_ESCAPE_UTF 3 uintptr_t ngx_escape_uri(u_char *dst, u_char *src, size_t size, ngx_uint_t type); |