diff src/http/ngx_http_parse.c @ 28:7ca9bdc82b3f NGINX_0_1_14

nginx 0.1.14 *) Feature: the autoconfiguration directives: --http-client-body-temp-path=PATH, --http-proxy-temp-path=PATH, and --http-fastcgi-temp-path=PATH *) Change: the directory name for the temporary files with the client request body is specified by directive client_body_temp_path, by default it is <prefix>/client_body_temp. *) Feature: the ngx_http_fastcgi_module and the directives: fastcgi_pass, fastcgi_root, fastcgi_index, fastcgi_params, fastcgi_connect_timeout, fastcgi_send_timeout, fastcgi_read_timeout, fastcgi_send_lowat, fastcgi_header_buffer_size, fastcgi_buffers, fastcgi_busy_buffers_size, fastcgi_temp_path, fastcgi_max_temp_file_size, fastcgi_temp_file_write_size, fastcgi_next_upstream, and fastcgi_x_powered_by. *) Bugfix: the "[alert] zero size buf" error; bug appeared in 0.1.3. *) Change: the URI must be specified after the host name in the proxy_pass directive. *) Change: the %3F symbol in the URI was considered as the argument string start. *) Feature: the unix domain sockets support in the ngx_http_proxy_module. *) Feature: the ssl_engine and ssl_ciphers directives. Thanks to Sergey Skvortsov for SSL-accelerator.
author Igor Sysoev <http://sysoev.ru>
date Tue, 18 Jan 2005 00:00:00 +0300
parents 8b6db3bda591
children aab2ea7c0458
line wrap: on
line diff
--- a/src/http/ngx_http_parse.c
+++ b/src/http/ngx_http_parse.c
@@ -34,15 +34,13 @@ ngx_int_t ngx_http_parse_request_line(ng
         sw_major_digit,
         sw_first_minor_digit,
         sw_minor_digit,
-        sw_almost_done,
-        sw_done
+        sw_almost_done
     } state;
 
     state = r->state;
-    p = b->pos;
 
-    while (p < b->last && state < sw_done) {
-        ch = *p++;
+    for (p = b->pos; p < b->last; p++) {
+        ch = *p;
 
         /* gcc 2.95.2 and msvc 6.0 compile this switch as an jump table */
 
@@ -50,7 +48,7 @@ ngx_int_t ngx_http_parse_request_line(ng
 
         /* HTTP methods: GET, HEAD, POST */
         case sw_start:
-            r->request_start = p - 1;
+            r->request_start = p;
 
             if (ch == CR || ch == LF) {
                 break;
@@ -65,19 +63,19 @@ ngx_int_t ngx_http_parse_request_line(ng
 
         case sw_method:
             if (ch == ' ') {
-                r->method_end = p - 1;
+                r->method_end = p;
                 m = r->request_start;
 
-                if (r->method_end - m == 3) {
+                if (p - m == 3) {
 
                     if (m[0] == 'G' && m[1] == 'E' && m[2] == 'T') {
                         r->method = NGX_HTTP_GET;
                     }
 
-                } else if (r->method_end - m == 4) {
+                } else if (p - m == 4) {
 
                     if (m[0] == 'P' && m[1] == 'O'
-                        && m[2] == 'T' && m[3] == 'T')
+                        && m[2] == 'S' && m[3] == 'T')
                     {
                         r->method = NGX_HTTP_POST;
 
@@ -113,14 +111,14 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_spaces_before_uri:
             switch (ch) {
             case '/':
-                r->uri_start = p - 1;
+                r->uri_start = p;
                 state = sw_after_slash_in_uri;
                 break;
             case ' ':
                 break;
             default:
                 if ((ch >= 'A' && ch <= 'Z') || (ch >= 'a' && ch <= 'z')) {
-                    r->schema_start = p - 1;
+                    r->schema_start = p;
                     state = sw_schema;
                     break;
                 }
@@ -131,7 +129,7 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_schema:
             switch (ch) {
             case ':':
-                r->schema_end = p - 1;
+                r->schema_end = p;
                 state = sw_schema_slash;
                 break;
             default:
@@ -155,7 +153,7 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_schema_slash_slash:
             switch (ch) {
             case '/':
-                r->host_start = p - 1;
+                r->host_start = p;
                 state = sw_host;
                 break;
             default:
@@ -166,12 +164,12 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_host:
             switch (ch) {
             case ':':
-                r->host_end = p - 1;
+                r->host_end = p;
                 state = sw_port;
                 break;
             case '/':
-                r->host_end = p - 1;
-                r->uri_start = p - 1;
+                r->host_end = p;
+                r->uri_start = p;
                 state = sw_after_slash_in_uri;
                 break;
             default:
@@ -187,8 +185,8 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_port:
             switch (ch) {
             case '/':
-                r->port_end = p - 1;
-                r->uri_start = p - 1;
+                r->port_end = p;
+                r->uri_start = p;
                 state = sw_after_slash_in_uri;
                 break;
             default:
@@ -203,17 +201,16 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_after_slash_in_uri:
             switch (ch) {
             case CR:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
                 state = sw_almost_done;
                 break;
             case LF:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
-                state = sw_done;
-                break;
+                goto done;
             case ' ':
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 state = sw_http_09;
                 break;
             case '.':
@@ -233,7 +230,7 @@ ngx_int_t ngx_http_parse_request_line(ng
                 r->complex_uri = 1;
                 break;
             case '?':
-                r->args_start = p;
+                r->args_start = p + 1;
                 state = sw_uri;
                 break;
             default:
@@ -246,21 +243,20 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_check_uri:
             switch (ch) {
             case CR:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
                 state = sw_almost_done;
                 break;
             case LF:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
-                state = sw_done;
-                break;
+                goto done;
             case ' ':
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 state = sw_http_09;
                 break;
             case '.':
-                r->uri_ext = p;
+                r->uri_ext = p + 1;
                 break;
 #if (NGX_WIN32)
             case '\\':
@@ -277,7 +273,7 @@ ngx_int_t ngx_http_parse_request_line(ng
                 state = sw_uri;
                 break;
             case '?':
-                r->args_start = p;
+                r->args_start = p + 1;
                 state = sw_uri;
                 break;
             }
@@ -287,17 +283,16 @@ ngx_int_t ngx_http_parse_request_line(ng
         case sw_uri:
             switch (ch) {
             case CR:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
                 state = sw_almost_done;
                 break;
             case LF:
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 r->http_minor = 9;
-                state = sw_done;
-                break;
+                goto done;
             case ' ':
-                r->uri_end = p - 1;
+                r->uri_end = p;
                 state = sw_http_09;
                 break;
             }
@@ -314,9 +309,9 @@ ngx_int_t ngx_http_parse_request_line(ng
                 break;
             case LF:
                 r->http_minor = 9;
-                state = sw_done;
-                break;
+                goto done;
             case 'H':
+                r->http_protocol.data = p;
                 state = sw_http_H;
                 break;
             default:
@@ -406,8 +401,7 @@ ngx_int_t ngx_http_parse_request_line(ng
             }
 
             if (ch == LF) {
-                state = sw_done;
-                break;
+                goto done;
             }
 
             if (ch < '0' || ch > '9') {
@@ -419,42 +413,38 @@ ngx_int_t ngx_http_parse_request_line(ng
 
         /* end of request line */
         case sw_almost_done:
-            r->request_end = p - 2;
+            r->request_end = p - 1;
             switch (ch) {
             case LF:
-                state = sw_done;
-                break;
+                goto done;
             default:
                 return NGX_HTTP_PARSE_INVALID_REQUEST;
             }
             break;
-
-        /* suppress warning */
-        case sw_done:
-            break;
         }
     }
 
     b->pos = p;
+    r->state = state;
 
-    if (state == sw_done) {
-        if (r->request_end == NULL) {
-            r->request_end = p - 1;
-        }
+    return NGX_AGAIN;
 
-        r->http_version = r->http_major * 1000 + r->http_minor;
-        r->state = sw_start;
+done:
+
+    b->pos = p + 1;
 
-        if (r->http_version == 9 && r->method != NGX_HTTP_GET) {
-            return NGX_HTTP_PARSE_INVALID_09_METHOD;
-        }
+    if (r->request_end == NULL) {
+        r->request_end = p;
+    }
 
-        return NGX_OK;
+    r->http_version = r->http_major * 1000 + r->http_minor;
+    r->state = sw_start;
 
-    } else {
-        r->state = state;
-        return NGX_AGAIN;
+    if (r->http_version == 9 && r->method != NGX_HTTP_GET) {
+        return NGX_HTTP_PARSE_INVALID_09_METHOD;
     }
+
+    return NGX_OK;
 }
 
 
@@ -469,16 +459,13 @@ ngx_int_t ngx_http_parse_header_line(ngx
         sw_space_after_value,
         sw_almost_done,
         sw_header_almost_done,
-        sw_ignore_line,
-        sw_done,
-        sw_header_done
+        sw_ignore_line
     } state;
 
     state = r->state;
-    p = b->pos;
 
-    while (p < b->last && state < sw_done) {
-        ch = *p++;
+    for (p = b->pos; p < b->last; p++) {
+        ch = *p;
 
         switch (state) {
 
@@ -486,16 +473,15 @@ ngx_int_t ngx_http_parse_header_line(ngx
         case sw_start:
             switch (ch) {
             case CR:
-                r->header_end = p - 1;
+                r->header_end = p;
                 state = sw_header_almost_done;
                 break;
             case LF:
-                r->header_end = p - 1;
-                state = sw_header_done;
-                break;
+                r->header_end = p;
+                goto header_done;
             default:
                 state = sw_name;
-                r->header_name_start = p - 1;
+                r->header_name_start = p;
 
                 c = (u_char) (ch | 0x20);
                 if (c >= 'a' && c <= 'z') {
@@ -523,7 +509,7 @@ ngx_int_t ngx_http_parse_header_line(ngx
             }
 
             if (ch == ':') {
-                r->header_name_end = p - 1;
+                r->header_name_end = p;
                 state = sw_space_before_value;
                 break;
             }
@@ -539,7 +525,7 @@ ngx_int_t ngx_http_parse_header_line(ngx
             /* IIS may send the duplicate "HTTP/1.1 ..." lines */
             if (ch == '/'
                 && r->proxy
-                && p - r->header_start == 5
+                && p - r->header_start == 4
                 && ngx_strncmp(r->header_start, "HTTP", 4) == 0)
             {
                 state = sw_ignore_line;
@@ -554,15 +540,14 @@ ngx_int_t ngx_http_parse_header_line(ngx
             case ' ':
                 break;
             case CR:
-                r->header_start = r->header_end = p - 1;
+                r->header_start = r->header_end = p;
                 state = sw_almost_done;
                 break;
             case LF:
-                r->header_start = r->header_end = p - 1;
-                state = sw_done;
-                break;
+                r->header_start = r->header_end = p;
+                goto done;
             default:
-                r->header_start = p - 1;
+                r->header_start = p;
                 state = sw_value;
                 break;
             }
@@ -572,17 +557,16 @@ ngx_int_t ngx_http_parse_header_line(ngx
         case sw_value:
             switch (ch) {
             case ' ':
-                r->header_end = p - 1;
+                r->header_end = p;
                 state = sw_space_after_value;
                 break;
             case CR:
-                r->header_end = p - 1;
+                r->header_end = p;
                 state = sw_almost_done;
                 break;
             case LF:
-                r->header_end = p - 1;
-                state = sw_done;
-                break;
+                r->header_end = p;
+                goto done;
             }
             break;
 
@@ -595,8 +579,7 @@ ngx_int_t ngx_http_parse_header_line(ngx
                 state = sw_almost_done;
                 break;
             case LF:
-                state = sw_done;
-                break;
+                goto done;
             default:
                 state = sw_value;
                 break;
@@ -618,8 +601,7 @@ ngx_int_t ngx_http_parse_header_line(ngx
         case sw_almost_done:
             switch (ch) {
             case LF:
-                state = sw_done;
-                break;
+                goto done;
             default:
                 return NGX_HTTP_PARSE_INVALID_HEADER;
             }
@@ -629,34 +611,32 @@ ngx_int_t ngx_http_parse_header_line(ngx
         case sw_header_almost_done:
             switch (ch) {
             case LF:
-                state = sw_header_done;
-                break;
+                goto header_done;
             default:
                 return NGX_HTTP_PARSE_INVALID_HEADER;
             }
             break;
-
-        /* suppress warning */
-        case sw_done:
-        case sw_header_done:
-            break;
         }
     }
 
     b->pos = p;
+    r->state = state;
 
-    if (state == sw_done) {
-        r->state = sw_start;
-        return NGX_OK;
+    return NGX_AGAIN;
+
+done:
+
+    b->pos = p + 1;
+    r->state = sw_start;
 
-    } else if (state == sw_header_done) {
-        r->state = sw_start;
-        return NGX_HTTP_PARSE_HEADER_DONE;
+    return NGX_OK;
+
+header_done:
 
-    } else {
-        r->state = state;
-        return NGX_AGAIN;
-    }
+    b->pos = p + 1;
+    r->state = sw_start;
+
+    return NGX_HTTP_PARSE_HEADER_DONE;
 }
 
 
@@ -677,8 +657,10 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
         sw_quoted_second
     } state, quoted_state;
 
+#if (NGX_SUPPRESS_WARN)
     decoded = '\0';
     quoted_state = sw_usual;
+#endif
 
     state = sw_usual;
     p = r->uri_start;
@@ -688,10 +670,10 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
 
     ch = *p++;
 
-    while (p <= r->uri_end && r->args_start == NULL) {
+    while (p <= r->uri_end) {
 
         /*
-         * we use "ch = *p++" inside the cycle but this operation is safe
+         * we use "ch = *p++" inside the cycle, but this operation is safe,
          * because after the URI there is always at least one charcter:
          * the line feed
          */
@@ -731,7 +713,7 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 break;
             case '?':
                 r->args_start = p;
-                break;
+                goto done;
             case ':':
                 state = sw_colon;
                 *u++ = ch;
@@ -766,6 +748,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 quoted_state = state;
                 state = sw_quoted;
                 break;
+            case '?':
+                r->args_start = p;
+                goto done;
             default:
                 state = sw_usual;
                 *u++ = ch;
@@ -794,6 +779,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 quoted_state = state;
                 state = sw_quoted;
                 break;
+            case '?':
+                r->args_start = p;
+                goto done;
             default:
                 state = sw_usual;
                 *u++ = ch;
@@ -818,6 +806,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 quoted_state = state;
                 state = sw_quoted;
                 break;
+            case '?':
+                r->args_start = p;
+                goto done;
             default:
                 state = sw_usual;
                 *u++ = ch;
@@ -844,6 +835,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 quoted_state = state;
                 state = sw_quoted;
                 break;
+            case '?':
+                r->args_start = p;
+                goto done;
             default:
                 state = sw_usual;
                 *u++ = ch;
@@ -872,6 +866,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
                 quoted_state = state;
                 state = sw_quoted;
                 break;
+            case '?':
+                r->args_start = p;
+                goto done;
 #if (NGX_WIN32)
             case '.':
                 state = sw_dot_dot_dot;
@@ -953,11 +950,9 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
             c = (u_char) (ch | 0x20);
             if (c >= 'a' && c <= 'f') {
                 ch = (u_char) ((decoded << 4) + c - 'a' + 10);
-                if (ch == '%') {
-                    state = sw_usual;
+                if (ch == '?') {
                     *u++ = ch;
                     ch = *p++;
-                    break;
                 }
                 state = quoted_state;
                 break;
@@ -967,6 +962,8 @@ ngx_int_t ngx_http_parse_complex_uri(ngx
         }
     }
 
+done:
+
     r->uri.len = u - r->uri.data;
     r->uri.data[r->uri.len] = '\0';