You are viewing a plain text version of this content. The canonical link for it is here.
Posted to apreq-cvs@httpd.apache.org by jo...@apache.org on 2009/02/28 08:16:23 UTC

svn commit: r748782 - in /httpd/apreq/trunk: CHANGES acinclude.m4 include/apreq_version.h library/cookie.c library/t/cookie.c

Author: joes
Date: Sat Feb 28 07:16:23 2009
New Revision: 748782

URL: http://svn.apache.org/viewvc?rev=748782&view=rev
Log:
soften up the cookie parser

Modified:
    httpd/apreq/trunk/CHANGES
    httpd/apreq/trunk/acinclude.m4
    httpd/apreq/trunk/include/apreq_version.h
    httpd/apreq/trunk/library/cookie.c
    httpd/apreq/trunk/library/t/cookie.c

Modified: httpd/apreq/trunk/CHANGES
URL: http://svn.apache.org/viewvc/httpd/apreq/trunk/CHANGES?rev=748782&r1=748781&r2=748782&view=diff
==============================================================================
--- httpd/apreq/trunk/CHANGES (original)
+++ httpd/apreq/trunk/CHANGES Sat Feb 28 07:16:23 2009
@@ -3,6 +3,9 @@
 
 @section v2_11 Changes with libapreq2-2.11 (in development)
 
+- C API [joes]
+  Make the cookie parser a little more flexible.
+
 - Interactive CGI module [issac]
   Allow cgi module to interactively prompt for parameters and cookies when
   running a script from the command line and not from a CGI interface

Modified: httpd/apreq/trunk/acinclude.m4
URL: http://svn.apache.org/viewvc/httpd/apreq/trunk/acinclude.m4?rev=748782&r1=748781&r2=748782&view=diff
==============================================================================
--- httpd/apreq/trunk/acinclude.m4 (original)
+++ httpd/apreq/trunk/acinclude.m4 Sat Feb 28 07:16:23 2009
@@ -213,7 +213,7 @@
         if test "x$USE_MAINTAINER_MODE" != "xno"; then
             APR_ADDTO([CFLAGS],[
                       -fno-strict-aliasing
-                      -Werror -Wall -Wmissing-prototypes -Wstrict-prototypes
+                      -Wall -Wmissing-prototypes -Wstrict-prototypes
                       -Wmissing-declarations -Wwrite-strings -Wcast-qual
                       -Wfloat-equal -Wshadow -Wpointer-arith
                       -Wbad-function-cast -Wsign-compare -Waggregate-return

Modified: httpd/apreq/trunk/include/apreq_version.h
URL: http://svn.apache.org/viewvc/httpd/apreq/trunk/include/apreq_version.h?rev=748782&r1=748781&r2=748782&view=diff
==============================================================================
--- httpd/apreq/trunk/include/apreq_version.h (original)
+++ httpd/apreq/trunk/include/apreq_version.h Sat Feb 28 07:16:23 2009
@@ -62,7 +62,7 @@
 #define APREQ_MINOR_VERSION       7
 
 /** patch level */
-#define APREQ_PATCH_VERSION       0
+#define APREQ_PATCH_VERSION       1
 
 /**
  *  This symbol is defined for internal, "development" copies of libapreq.

Modified: httpd/apreq/trunk/library/cookie.c
URL: http://svn.apache.org/viewvc/httpd/apreq/trunk/library/cookie.c?rev=748782&r1=748781&r2=748782&view=diff
==============================================================================
--- httpd/apreq/trunk/library/cookie.c (original)
+++ httpd/apreq/trunk/library/cookie.c Sat Feb 28 07:16:23 2009
@@ -168,29 +168,52 @@
                       const char **v, apr_size_t *vlen, unsigned unquote)
 {
     const char *hdr, *key, *val;
-
+    int nlen_set = 0;
     hdr = *data;
 
     while (apr_isspace(*hdr) || *hdr == '=')
         ++hdr;
 
-    key = strchr(hdr, '=');
+    key = hdr;
+    *n = hdr;
 
-    if (key == NULL)
-        return APREQ_ERROR_NOTOKEN;
+ scan_name:
 
-    val = key + 1;
+    switch (*hdr) {
 
-    do --key;
-    while (key > hdr && apr_isspace(*key));
+    case 0:
+    case ';':
+    case ',':
+        if (!nlen_set)
+            *nlen = hdr - key;
+        *v = hdr;
+        *vlen = 0;
+        *data = hdr;
+        return *nlen ? APREQ_ERROR_NOTOKEN : APREQ_ERROR_BADCHAR;
+
+    case '=':
+        if (!nlen_set) {
+            *nlen = hdr - key;
+            nlen_set = 1;
+        }
+        break;
 
-    *n = key;
+    case ' ':
+    case '\t':
+    case '\r':
+    case '\n':
+        if (!nlen_set) {
+            *nlen = hdr - key;
+            nlen_set = 1;
+        }
+        /* fall thru */
 
-    while (key >= hdr && !apr_isspace(*key))
-        --key;
+    default:
+        ++hdr;
+        goto scan_name;
+    }
 
-    *nlen = *n - key;
-    *n = key + 1;
+    val = hdr + 1;
 
     while (apr_isspace(*val))
         ++val;
@@ -231,6 +254,7 @@
             }
         }
         /* bad sequence: no terminating quote found */
+        *data = val;
         return APREQ_ERROR_BADSEQ;
     }
     else {
@@ -266,6 +290,7 @@
 {
     apreq_cookie_t *c;
     unsigned version;
+    apr_status_t rv = APR_SUCCESS;
 
  parse_cookie_header:
 
@@ -276,13 +301,13 @@
         ++hdr;
 
 
-    if (*hdr == '$') {
-        /* XXX cheat: assume "$..." => "$Version" => RFC Cookie header */
+    if (*hdr == '$' && strncasecmp(hdr, "$Version", 8) == 0) {
+        /* XXX cheat: assume "$Version" => RFC Cookie header */
         version = RFC;
     skip_version_string:
         switch (*hdr++) {
         case 0:
-            return APR_SUCCESS;
+            return rv;
         case ',':
             goto parse_cookie_header;
         case ';':
@@ -307,7 +332,7 @@
             if (c != NULL) {
                 ADD_COOKIE(j, c);
             }
-            return APR_SUCCESS;
+            return rv;
 
         case ',':
             ++hdr;
@@ -317,29 +342,35 @@
             goto parse_cookie_header;
 
         case '$':
+            ++hdr;
             if (c == NULL) {
-                return APREQ_ERROR_BADCHAR;
+                rv = APREQ_ERROR_BADCHAR;
+                goto parse_cookie_error;
             }
             else if (version == NETSCAPE) {
-                return APREQ_ERROR_MISMATCH;
+                rv = APREQ_ERROR_MISMATCH;
             }
 
-            ++hdr;
             status = get_pair(p, &hdr, &name, &nlen, &value, &vlen, 1);
-            if (status != APR_SUCCESS)
-                return status;
+            if (status != APR_SUCCESS) {
+                rv = status;
+                goto parse_cookie_error;
+            }
 
             status = apreq_cookie_attr(p, c, name, nlen, value, vlen);
 
             switch (status) {
+
             case APR_ENOTIMPL:
-                /* XXX: skip unrecognized attr?  Not really correct,
-                   but for now, just fall through */
+                rv = APREQ_ERROR_BADATTR;
+                /* fall thru */
 
             case APR_SUCCESS:
                 break;
+
             default:
-                return status;
+                rv = status;
+                goto parse_cookie_error;
             }
 
             break;
@@ -351,8 +382,20 @@
 
             status = get_pair(p, &hdr, &name, &nlen, &value, &vlen, 0);
 
-            if (status != APR_SUCCESS)
-                return status;
+            switch (status) {
+
+            case APREQ_ERROR_NOTOKEN:
+                rv = status;
+                /* fall thru */
+
+            case APR_SUCCESS:
+                break;
+
+            default:
+                c = NULL;
+                rv = status;
+                goto parse_cookie_error;
+            }
 
             c = apreq_cookie_make(p, name, nlen, value, vlen);
             apreq_cookie_tainted_on(c);
@@ -361,8 +404,27 @@
         }
     }
 
-    /* NOT REACHED */
-    return APREQ_ERROR_GENERAL;
+ parse_cookie_error:
+
+    switch (*hdr) {
+
+    case 0:
+        return rv;
+
+    case ',':
+    case ';':
+        if (c != NULL)
+            ADD_COOKIE(j, c);
+        ++hdr;
+        goto parse_cookie_header;
+
+    default:
+        ++hdr;
+        goto parse_cookie_error;
+    }
+
+    /* not reached */
+    return rv;
 }
 
 

Modified: httpd/apreq/trunk/library/t/cookie.c
URL: http://svn.apache.org/viewvc/httpd/apreq/trunk/library/t/cookie.c?rev=748782&r1=748781&r2=748782&view=diff
==============================================================================
--- httpd/apreq/trunk/library/t/cookie.c (original)
+++ httpd/apreq/trunk/library/t/cookie.c Sat Feb 28 07:16:23 2009
@@ -110,8 +110,8 @@
 
     AT_str_eq(apr_table_get(jar, "a"), "1");
 
-    /* ignore wacky cookies that don't have an '=' sign */
-    AT_is_null(apr_table_get(jar, "bad"));
+    /* accept wacky cookies that don't have an '=' sign */
+    AT_not_null(apr_table_get(jar, "bad"));
 
     /* accept wacky cookies that contain multiple '=' */
     AT_str_eq(apr_table_get(jar, "ns"), "foo=1&bar=2");