diff src/http/ngx_http_request.c @ 72:b31656313b59 NGINX_0_1_36

nginx 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.
author Igor Sysoev <http://sysoev.ru>
date Wed, 15 Jun 2005 00:00:00 +0400
parents 8ad297c88dcb
children 77969b24f355
line wrap: on
line diff
--- a/src/http/ngx_http_request.c
+++ b/src/http/ngx_http_request.c
@@ -22,6 +22,8 @@ static ngx_int_t ngx_http_alloc_large_he
 
 static ngx_int_t ngx_http_process_header_line(ngx_http_request_t *r,
     ngx_table_elt_t *h, ngx_uint_t offset);
+static ngx_int_t ngx_http_process_unique_header_line(ngx_http_request_t *r,
+    ngx_table_elt_t *h, ngx_uint_t offset);
 static ngx_int_t ngx_http_process_cookie(ngx_http_request_t *r,
     ngx_table_elt_t *h, ngx_uint_t offset);
 
@@ -62,10 +64,10 @@ static char *ngx_http_client_errors[] = 
 
 ngx_http_header_t  ngx_http_headers_in[] = {
     { ngx_string("Host"), offsetof(ngx_http_headers_in_t, host),
-                 ngx_http_process_header_line },
+                 ngx_http_process_unique_header_line },
 
     { ngx_string("Connection"), offsetof(ngx_http_headers_in_t, connection),
-                 ngx_http_process_header_line },
+                 ngx_http_process_unique_header_line },
 
     { ngx_string("If-Modified-Since"),
                  offsetof(ngx_http_headers_in_t, if_modified_since),
@@ -79,7 +81,7 @@ ngx_http_header_t  ngx_http_headers_in[]
 
     { ngx_string("Content-Length"),
                  offsetof(ngx_http_headers_in_t, content_length),
-                 ngx_http_process_header_line },
+                 ngx_http_process_unique_header_line },
 
     { ngx_string("Content-Type"),
                  offsetof(ngx_http_headers_in_t, content_type),
@@ -104,7 +106,7 @@ ngx_http_header_t  ngx_http_headers_in[]
 
     { ngx_string("Authorization"),
                  offsetof(ngx_http_headers_in_t, authorization),
-                 ngx_http_process_header_line },
+                 ngx_http_process_unique_header_line },
 
     { ngx_string("Keep-Alive"), offsetof(ngx_http_headers_in_t, keep_alive),
                  ngx_http_process_header_line },
@@ -113,12 +115,6 @@ ngx_http_header_t  ngx_http_headers_in[]
     { ngx_string("X-Forwarded-For"),
                  offsetof(ngx_http_headers_in_t, x_forwarded_for),
                  ngx_http_process_header_line },
-
-    { ngx_string("X-Real-IP"), offsetof(ngx_http_headers_in_t, x_real_ip),
-                 ngx_http_process_header_line },
-
-    { ngx_string("X-URL"), offsetof(ngx_http_headers_in_t, x_url),
-                 ngx_http_process_header_line },
 #endif
 
 #if (NGX_HTTP_HEADERS)
@@ -906,13 +902,13 @@ ngx_http_read_request_header(ngx_http_re
         return n;
     }
 
-    if (!rev->ready) {
-        return NGX_AGAIN;
+    if (rev->ready) {
+        n = r->connection->recv(r->connection, r->header_in->last,
+                                r->header_in->end - r->header_in->last);
+    } else {
+        n = NGX_AGAIN;
     }
 
-    n = r->connection->recv(r->connection, r->header_in->last,
-                            r->header_in->end - r->header_in->last);
-
     if (n == NGX_AGAIN) {
         if (!r->header_timeout_set) {
             cscf = ngx_http_get_module_srv_conf(r, ngx_http_core_module);
@@ -1107,21 +1103,44 @@ ngx_http_process_header_line(ngx_http_re
 
 
 static ngx_int_t
+ngx_http_process_unique_header_line(ngx_http_request_t *r, ngx_table_elt_t *h,
+    ngx_uint_t offset)
+{
+    ngx_table_elt_t  **ph;
+
+    ph = (ngx_table_elt_t **) ((char *) &r->headers_in + offset);
+
+    if (*ph == NULL) {
+        *ph = h;
+        return NGX_OK;
+    }
+
+    ngx_log_error(NGX_LOG_INFO, r->connection->log, 0,
+                  "client sent duplicate header line: \"%V: %V\"",
+                  &h->key, &h->value);
+
+    ngx_http_finalize_request(r, NGX_HTTP_BAD_REQUEST);
+
+    return NGX_ERROR;
+}
+
+
+static ngx_int_t
 ngx_http_process_cookie(ngx_http_request_t *r, ngx_table_elt_t *h,
     ngx_uint_t offset)
 {
     ngx_table_elt_t  **cookie;
 
     cookie = ngx_array_push(&r->headers_in.cookies);
-    if (cookie == NULL) {
-        ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR);
-        ngx_http_close_connection(r->connection);
-        return NGX_ERROR;
+    if (cookie) {
+        *cookie = h;
+        return NGX_OK;
     }
 
-    *cookie = h;
-
-    return NGX_OK;
+    ngx_http_close_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR);
+    ngx_http_close_connection(r->connection);
+
+    return NGX_ERROR;
 }