[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[libmicrohttpd] 06/06: Refactored cookies parsing.
From: |
gnunet |
Subject: |
[libmicrohttpd] 06/06: Refactored cookies parsing. |
Date: |
Mon, 19 Dec 2022 16:18:03 +0100 |
This is an automated email from the git hooks/post-receive script.
karlson2k pushed a commit to branch master
in repository libmicrohttpd.
commit 1e7ad3010da7d2be1afe219da0ba84dd129f9c4e
Author: Evgeny Grin (Karlson2k) <k2k@narod.ru>
AuthorDate: Tue Dec 6 23:40:21 2022 +0300
Refactored cookies parsing.
The new code is more compact as duplicated code was removed.
Added testing for various cookies parsing strictness levels.
---
src/microhttpd/connection.c | 299 ++++++++-------------
src/testcurl/Makefile.am | 14 +-
src/testcurl/test_parse_cookies.c | 540 ++++++++++++++++++++++++++++++++++----
3 files changed, 614 insertions(+), 239 deletions(-)
diff --git a/src/microhttpd/connection.c b/src/microhttpd/connection.c
index 960c22db..16c5fb93 100644
--- a/src/microhttpd/connection.c
+++ b/src/microhttpd/connection.c
@@ -2826,146 +2826,6 @@ enum _MHD_ParseCookie
};
-/**
- * Parse the cookies string (see RFC 6265).
- *
- * Parsing may fail if the string is not formed strictly as defined by RFC
6265.
- *
- * @param str the string to parse, without leading whitespaces
- * @param str_len the size of the @a str, not including mandatory
- * zero-termination
- * @param connection the connection to add parsed cookies
- * @return #MHD_PARSE_COOKIE_OK for success, error code otherwise
- */
-static enum _MHD_ParseCookie
-parse_cookies_string_strict (char *str,
- size_t str_len,
- struct MHD_Connection *connection)
-{
- size_t i;
-
- i = 0;
- while (i < str_len)
- {
- size_t name_start;
- size_t name_len;
- size_t value_start;
- size_t value_len;
- bool val_quoted;
- /* 'i' must point to the first char of cookie-name */
- name_start = i;
- /* Find the end of the cookie-name */
- do
- {
- const char l = str[i];
- if (('=' == l) || (' ' == l) || ('\t' == l) || ('"' == l) || (',' == l)
||
- (';' == l) || (0 == l))
- break;
- } while (str_len > ++i);
- if ((str_len == i) || ('=' != str[i]) || (name_start == i))
- return MHD_PARSE_COOKIE_MALFORMED; /* Incomplete cookie name */
- name_len = i - name_start;
- /* 'i' must point to the '=' char */
- mhd_assert ('=' == str[i]);
- i++;
- /* 'i' must point to the first char of cookie-value */
- if (str_len == i)
- {
- value_start = 0;
- value_len = 0;
-#ifdef _DEBUG
- val_quoted = false; /* This assignment used in assert */
-#endif
- }
- else
- {
- bool valid_cookie;
- val_quoted = ('"' == str[i]);
- if (val_quoted)
- i++;
- value_start = i;
- /* Find the end of the cookie-value */
- while (str_len > i)
- {
- const char l = str[i];
- if ((';' == l) || ('"' == l) || (' ' == l) || ('\t' == l)
- || (',' == l) || ('\\' == l) || (0 == l))
- break;
- i++;
- }
- value_len = i - value_start;
- if (val_quoted)
- {
- if ((str_len == i) || ('"' != str[i]))
- return MHD_PARSE_COOKIE_MALFORMED; /* Incomplete cookie value, no
closing quote */
- i++;
- }
- if (str_len == i)
- valid_cookie = true;
- else if (';' == str[i])
- valid_cookie = true;
- else if ((' ' == str[i]) || ('\t' == str[i]))
- { /* Optional whitespace at the end of the string? */
- while (str_len > ++i)
- {
- if ((' ' != str[i]) && ('\t' != str[i]))
- break;
- }
- if (str_len == i)
- valid_cookie = true;
- else
- valid_cookie = false;
- }
- else
- valid_cookie = false;
-
- if (! valid_cookie)
- return MHD_PARSE_COOKIE_MALFORMED; /* Garbage at the end of the cookie
value */
- }
- mhd_assert (0 != name_len);
- str[name_start + name_len] = 0; /* Zero-terminate the name */
- if (0 != value_len)
- {
- mhd_assert (0 == str[i] || ';' == str[i]);
- mhd_assert (! val_quoted || ';' == str[i]);
- str[value_start + value_len] = 0; /* Zero-terminate the value */
- if (MHD_NO ==
- MHD_set_connection_value_n_nocheck_ (connection,
- MHD_COOKIE_KIND,
- str + name_start,
- name_len,
- str + value_start,
- value_len))
- return MHD_PARSE_COOKIE_NO_MEMORY;
- }
- else
- {
- if (MHD_NO ==
- MHD_set_connection_value_n_nocheck_ (connection,
- MHD_COOKIE_KIND,
- str + name_start,
- name_len,
- "",
- 0))
- return MHD_PARSE_COOKIE_NO_MEMORY;
- }
- if (str_len > i)
- {
- mhd_assert (0 == str[i] || ';' == str[i]);
- mhd_assert (! val_quoted || ';' == str[i]);
- mhd_assert (';' != str[i] || val_quoted || 0 == value_len);
- i++;
- if (str_len == i)
- return MHD_PARSE_COOKIE_MALFORMED; /* No cookie name after semicolon
*/
- if (' ' != str[i])
- return MHD_PARSE_COOKIE_MALFORMED; /* No space after semicolon */
- i++;
- }
- }
- return MHD_PARSE_COOKIE_OK;
-}
-
-
/**
* Parse the cookies string (see RFC 6265).
*
@@ -2979,12 +2839,22 @@ parse_cookies_string_strict (char *str,
* @return #MHD_PARSE_COOKIE_OK for success, error code otherwise
*/
static enum _MHD_ParseCookie
-parse_cookies_string_lenient (char *str,
- size_t str_len,
- struct MHD_Connection *connection)
+parse_cookies_string (char *str,
+ const size_t str_len,
+ struct MHD_Connection *connection)
{
size_t i;
bool non_strict;
+ /* Skip extra whitespaces and empty cookies */
+ const bool allow_wsp_empty = (0 >= connection->daemon->strict_for_client);
+ /* Allow whitespaces around '=' character */
+ const bool wsp_around_eq = (0 > connection->daemon->strict_for_client);
+ /* Allow whitespaces in quoted cookie value */
+ const bool wsp_in_quoted = (0 >= connection->daemon->strict_for_client);
+ /* Allow tab as space after semicolon between cookies */
+ const bool tab_as_sp = (0 >= connection->daemon->strict_for_client);
+ /* Allow no space after semicolon between cookies */
+ const bool allow_no_space = (0 >= connection->daemon->strict_for_client);
non_strict = false;
i = 0;
@@ -2998,6 +2868,8 @@ parse_cookies_string_lenient (char *str,
/* Skip any whitespaces and empty cookies */
while (' ' == str[i] || '\t' == str[i] || ';' == str[i])
{
+ if (! allow_wsp_empty)
+ return MHD_PARSE_COOKIE_MALFORMED;
non_strict = true;
i++;
if (i == str_len)
@@ -3017,6 +2889,8 @@ parse_cookies_string_lenient (char *str,
/* Skip any whitespaces */
while (str_len > i && (' ' == str[i] || '\t' == str[i]))
{
+ if (! wsp_around_eq)
+ return MHD_PARSE_COOKIE_MALFORMED;
non_strict = true;
i++;
}
@@ -3028,6 +2902,8 @@ parse_cookies_string_lenient (char *str,
/* Skip any whitespaces */
while (str_len > i && (' ' == str[i] || '\t' == str[i]))
{
+ if (! wsp_around_eq)
+ return MHD_PARSE_COOKIE_MALFORMED;
non_strict = true;
i++;
}
@@ -3058,6 +2934,8 @@ parse_cookies_string_lenient (char *str,
{
if (! val_quoted)
break;
+ if (! wsp_in_quoted)
+ return MHD_PARSE_COOKIE_MALFORMED;
non_strict = true;
}
i++;
@@ -3070,10 +2948,19 @@ parse_cookies_string_lenient (char *str,
i++;
}
/* Skip any whitespaces */
- while (str_len > i && (' ' == str[i] || '\t' == str[i]))
+ if ((str_len > i) && ((' ' == str[i]) || ('\t' == str[i])))
{
- non_strict = true;
- i++;
+ do
+ {
+ i++;
+ } while (str_len > i && (' ' == str[i] || '\t' == str[i]));
+ /* Whitespace at the end? */
+ if (str_len > i)
+ {
+ if (! allow_wsp_empty)
+ return MHD_PARSE_COOKIE_MALFORMED;
+ non_strict = true;
+ }
}
if (str_len == i)
valid_cookie = true;
@@ -3118,11 +3005,29 @@ parse_cookies_string_lenient (char *str,
mhd_assert (';' != str[i] || val_quoted || non_strict || 0 == value_len);
i++;
if (str_len == i)
- non_strict = true; /* No cookie name after semicolon */
+ { /* No next cookie after semicolon */
+ if (! allow_wsp_empty)
+ return MHD_PARSE_COOKIE_MALFORMED;
+ non_strict = true;
+ }
else if (' ' != str[i])
- non_strict = true; /* No space after semicolon */
+ {/* No space after semicolon */
+ if (('\t' == str[i]) && tab_as_sp)
+ i++;
+ else if (! allow_no_space)
+ return MHD_PARSE_COOKIE_MALFORMED;
+ non_strict = true;
+ }
else
+ {
i++;
+ if (str_len == i)
+ {
+ if (! allow_wsp_empty)
+ return MHD_PARSE_COOKIE_MALFORMED;
+ non_strict = true;
+ }
+ }
}
}
return non_strict? MHD_PARSE_COOKIE_OK_LAX : MHD_PARSE_COOKIE_OK;
@@ -3141,8 +3046,10 @@ parse_cookie_header (struct MHD_Connection *connection)
const char *hdr;
size_t hdr_len;
char *cpy;
- bool strict_parsing;
size_t i;
+ enum _MHD_ParseCookie parse_res;
+ const struct MHD_HTTP_Req_Header *const saved_tail =
+ connection->rq.headers_received_tail;
if (MHD_NO ==
MHD_lookup_connection_value_n (connection,
@@ -3159,25 +3066,61 @@ parse_cookie_header (struct MHD_Connection *connection)
cpy = MHD_connection_alloc_memory_ (connection,
hdr_len + 1);
if (NULL == cpy)
- return MHD_PARSE_COOKIE_NO_MEMORY;
-
- memcpy (cpy,
- hdr,
- hdr_len);
- cpy[hdr_len] = '\0';
+ parse_res = MHD_PARSE_COOKIE_NO_MEMORY;
+ else
+ {
+ memcpy (cpy,
+ hdr,
+ hdr_len);
+ cpy[hdr_len] = '\0';
+
+ i = 0;
+ /* Skip all initial whitespaces */
+ while (i < hdr_len && (' ' == cpy[i] || '\t' == cpy[i]))
+ i++;
- /* TODO: add individual configuration */
- strict_parsing = (0 < connection->daemon->strict_for_client);
- i = 0;
- /* Skip all initial whitespaces */
- while (i < hdr_len && (' ' == cpy[i] || '\t' == cpy[i]))
- i++;
+ parse_res = parse_cookies_string (cpy + i, hdr_len - i, connection);
+ }
- /* 'i' points to the first non-whitespace char or to the end of the string */
- if (strict_parsing)
- return parse_cookies_string_strict (cpy + i, hdr_len - i, connection);
+ switch (parse_res)
+ {
+ case MHD_PARSE_COOKIE_OK:
+ break;
+ case MHD_PARSE_COOKIE_OK_LAX:
+#ifdef HAVE_MESSAGES
+ if (saved_tail != connection->rq.headers_received_tail)
+ MHD_DLOG (connection->daemon,
+ _ ("The Cookie header has been parsed, but it is not fully "
+ "compliant with the standard.\n"));
+#endif /* HAVE_MESSAGES */
+ break;
+ case MHD_PARSE_COOKIE_MALFORMED:
+#ifdef HAVE_MESSAGES
+ if (saved_tail != connection->rq.headers_received_tail)
+ MHD_DLOG (connection->daemon,
+ _ ("The Cookie header has been only partially parsed as it "
+ "contains malformed data.\n"));
+ else
+ MHD_DLOG (connection->daemon,
+ _ ("The Cookie header has malformed data.\n"));
+#endif /* HAVE_MESSAGES */
+ break;
+ case MHD_PARSE_COOKIE_NO_MEMORY:
+#ifdef HAVE_MESSAGES
+ MHD_DLOG (connection->daemon,
+ _ ("Not enough memory in the connection pool to "
+ "parse client cookies!\n"));
+#endif /* HAVE_MESSAGES */
+ break;
+ default:
+ mhd_assert (0);
+ break;
+ }
+#ifndef HAVE_MESSAGES
+ (void) saved_tail; /* Mute compiler warning */
+#endif /* ! HAVE_MESSAGES */
- return parse_cookies_string_lenient (cpy + i, hdr_len - i, connection);
+ return parse_res;
}
@@ -3946,37 +3889,13 @@ parse_connection_headers (struct MHD_Connection
*connection)
size_t val_len;
#ifdef COOKIE_SUPPORT
- enum _MHD_ParseCookie cookie_res;
-
- cookie_res = parse_cookie_header (connection);
- if (MHD_PARSE_COOKIE_NO_MEMORY == cookie_res)
+ if (MHD_PARSE_COOKIE_NO_MEMORY == parse_cookie_header (connection))
{
-#ifdef HAVE_MESSAGES
- MHD_DLOG (connection->daemon,
- _ ("Not enough memory in pool to parse cookies!\n"));
-#endif
transmit_error_response_static (connection,
MHD_HTTP_REQUEST_HEADER_FIELDS_TOO_LARGE,
REQUEST_TOO_BIG);
return;
}
- else if (MHD_PARSE_COOKIE_OK_LAX == cookie_res)
- {
-#ifdef HAVE_MESSAGES
- MHD_DLOG (connection->daemon,
- _ ("The Cookie header has been parsed, but is not fully "
- "compliant with the standard.\n"));
-#endif
- (void) 0; /* Mute compiler warning */
- }
- else if (MHD_PARSE_COOKIE_MALFORMED == cookie_res)
- {
-#ifdef HAVE_MESSAGES
- MHD_DLOG (connection->daemon,
- _ ("The Cookie header has malformed data.\n"));
-#endif
- (void) 0; /* Mute compiler warning */
- }
#endif /* COOKIE_SUPPORT */
if ( (1 <= connection->daemon->strict_for_client) &&
(MHD_IS_HTTP_VER_1_1_COMPAT (connection->rq.http_ver)) &&
diff --git a/src/testcurl/Makefile.am b/src/testcurl/Makefile.am
index 010ec2ef..0d190f9d 100644
--- a/src/testcurl/Makefile.am
+++ b/src/testcurl/Makefile.am
@@ -144,8 +144,9 @@ check_PROGRAMS = \
if ENABLE_COOKIE
check_PROGRAMS += \
- test_parse_cookies \
- test_parse_cookies_nonstrict
+ test_parse_cookies_strict_p1 \
+ test_parse_cookies_strict_zero \
+ test_parse_cookies_strict_n1
endif
if HEAVY_TESTS
@@ -467,11 +468,14 @@ test_post_SOURCES = \
test_process_headers_SOURCES = \
test_process_headers.c mhd_has_in_name.h
-test_parse_cookies_SOURCES = \
+test_parse_cookies_strict_zero_SOURCES = \
test_parse_cookies.c mhd_has_in_name.h mhd_has_param.h
-test_parse_cookies_nonstrict_SOURCES = \
- $(test_parse_cookies_SOURCES)
+test_parse_cookies_strict_p1_SOURCES = \
+ $(test_parse_cookies_strict_zero_SOURCES)
+
+test_parse_cookies_strict_n1_SOURCES = \
+ $(test_parse_cookies_strict_zero_SOURCES)
test_process_arguments_SOURCES = \
test_process_arguments.c mhd_has_in_name.h
diff --git a/src/testcurl/test_parse_cookies.c
b/src/testcurl/test_parse_cookies.c
index 987ddbf4..308b751e 100644
--- a/src/testcurl/test_parse_cookies.c
+++ b/src/testcurl/test_parse_cookies.c
@@ -189,7 +189,7 @@ _mhdErrorExit_func (const char *errDesc, const char
*funcName, int lineNum)
/* Could be increased to facilitate debugging */
-#define TIMEOUTS_VAL 5
+#define TIMEOUTS_VAL 500000
#define EXPECTED_URI_BASE_PATH "/"
@@ -203,6 +203,9 @@ _mhdErrorExit_func (const char *errDesc, const char
*funcName, int lineNum)
"<html><head><title>libmicrohttpd test page</title></head>" \
"<body>Success!</body></html>"
+#define PAGE_ERROR \
+ "<html><body>Cookies parsing error</body></html>"
+
#ifndef MHD_STATICSTR_LEN_
/**
@@ -234,19 +237,293 @@ struct strct_test_data
{
unsigned int line_num;
const char *header_str;
- unsigned int num_cookies_non_strict;
- unsigned int num_cookies_strict;
+ unsigned int num_cookies_strict_p2; /* Reserved */
+ unsigned int num_cookies_strict_p1;
+ unsigned int num_cookies_strict_zero;
+ unsigned int num_cookies_strict_n1;
struct strct_cookie cookies[5];
};
static const struct strct_test_data test_data[] = {
+ {
+ __LINE__,
+ "name1=value1",
+ 1,
+ 1,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1;",
+ 1,
+ 1,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; ",
+ 0,
+ 1,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "; name1=value1",
+ 0,
+ 0,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ ";name1=value1",
+ 0,
+ 0,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1 ",
+ 1,
+ 1,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1 ;",
+ 0,
+ 0,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1 ; ",
+ 0,
+ 0,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name2=\"value 2\"",
+ 0,
+ 0,
+ 1,
+ 1,
+ {
+ COOKIE_ ("name2", "value 2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1;\tname2=value2",
+ 0,
+ 1,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name1=value1",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2=value2",
+ 2,
+ 2,
+ 2,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
{
__LINE__,
"name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\"; " \
"name5=var_with_=_char",
- 5,
0,
+ 3,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -260,8 +537,10 @@ static const struct strct_test_data test_data[] = {
"name1=var1;name2=var2;name3=;" \
"name4=\"var4 with spaces\";" \
"name5=var_with_=_char",
- 5,
0,
+ 1,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -275,8 +554,10 @@ static const struct strct_test_data test_data[] = {
"name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\"; " \
"name5=var_with_=_char\t \t",
- 5,
0,
+ 1,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -290,8 +571,10 @@ static const struct strct_test_data test_data[] = {
"name1=var1;;name2=var2;;name3=;;" \
"name4=\"var4 with spaces\";;" \
"name5=var_with_=_char;\t \t",
- 5,
0,
+ 1,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -305,14 +588,16 @@ static const struct strct_test_data test_data[] = {
"name3=; name1=var1; name2=var2; " \
"name5=var_with_=_char;" \
"name4=\"var4 with spaces\"",
- 5,
0,
+ 4,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
COOKIE_ ("name3", ""),
- COOKIE_ ("name4", "var4 with spaces"),
- COOKIE_ ("name5", "var_with_=_char")
+ COOKIE_ ("name5", "var_with_=_char"),
+ COOKIE_ ("name4", "var4 with spaces")
}
},
{
@@ -320,14 +605,16 @@ static const struct strct_test_data test_data[] = {
"name2=var2; name1=var1; " \
"name5=var_with_=_char; name3=; " \
"name4=\"var4 with spaces\";",
- 5,
0,
+ 4,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
COOKIE_ ("name3", ""),
- COOKIE_ ("name4", "var4 with spaces"),
- COOKIE_ ("name5", "var_with_=_char")
+ COOKIE_ ("name5", "var_with_=_char"),
+ COOKIE_ ("name4", "var4 with spaces")
}
},
{
@@ -335,14 +622,16 @@ static const struct strct_test_data test_data[] = {
"name2=var2; name1=var1; " \
"name5=var_with_=_char; " \
"name4=\"var4 with spaces\"; name3=",
- 5,
0,
+ 3,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
+ COOKIE_ ("name5", "var_with_=_char"),
COOKIE_ ("name3", ""),
- COOKIE_ ("name4", "var4 with spaces"),
- COOKIE_ ("name5", "var_with_=_char")
+ COOKIE_ ("name4", "var4 with spaces")
}
},
{
@@ -350,8 +639,10 @@ static const struct strct_test_data test_data[] = {
"name2=var2; name1=var1; " \
"name4=\"var4 with spaces\"; " \
"name5=var_with_=_char; name3=;",
- 5,
0,
+ 2,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -365,8 +656,10 @@ static const struct strct_test_data test_data[] = {
";;;;;;;;name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\"; " \
"name5=var_with_=_char",
- 5,
0,
+ 0,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -380,8 +673,10 @@ static const struct strct_test_data test_data[] = {
"name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\"; ; ; ; ; " \
"name5=var_with_=_char",
- 5,
0,
+ 3,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -395,8 +690,10 @@ static const struct strct_test_data test_data[] = {
"name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\"; " \
"name5=var_with_=_char;;;;;;;;",
- 5,
0,
+ 3,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -408,16 +705,18 @@ static const struct strct_test_data test_data[] = {
{
__LINE__,
"name1=var1; name2=var2; " \
- "name4=\"var4 with spaces\"" \
+ "name4=\"var4 with spaces\";" \
"name5=var_with_=_char; ; ; ; ; name3=",
- 5,
0,
+ 2,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
+ COOKIE_ ("name5", "var_with_=_char"),
COOKIE_ ("name3", ""),
- COOKIE_ ("name4", "var4 with spaces"),
- COOKIE_ ("name5", "var_with_=_char")
+ COOKIE_ ("name4", "var4 with spaces")
}
},
{
@@ -425,8 +724,10 @@ static const struct strct_test_data test_data[] = {
"name5=var_with_=_char ;" \
"name1=var1; name2=var2; name3=; " \
"name4=\"var4 with spaces\" ",
- 5,
0,
+ 0,
+ 5,
+ 5,
{
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
@@ -439,14 +740,106 @@ static const struct strct_test_data test_data[] = {
__LINE__,
"name5=var_with_=_char; name4=\"var4 with spaces\";" \
"name1=var1; name2=var2; name3=",
- 5,
0,
+ 1,
+ 5,
+ 5,
{
+ COOKIE_ ("name5", "var_with_=_char"),
COOKIE_ ("name1", "var1"),
COOKIE_ ("name2", "var2"),
COOKIE_ ("name3", ""),
- COOKIE_ ("name4", "var4 with spaces"),
- COOKIE_ ("name5", "var_with_=_char")
+ COOKIE_ ("name4", "var4 with spaces")
+ }
+ },
+ {
+ __LINE__,
+ "name1 = value1",
+ 0,
+ 0,
+ 0,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1\t=\tvalue1",
+ 0,
+ 0,
+ 0,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1\t = \tvalue1",
+ 0,
+ 0,
+ 0,
+ 1,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1 = value1; name2 =\tvalue2",
+ 0,
+ 0,
+ 0,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1=value1; name2 =\tvalue2",
+ 0,
+ 1,
+ 1,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
+ }
+ },
+ {
+ __LINE__,
+ "name1 = value1; name2=value2",
+ 0,
+ 0,
+ 0,
+ 2,
+ {
+ COOKIE_ ("name1", "value1"),
+ COOKIE_ ("name2", "value2"),
+ COOKIE_NULL,
+ COOKIE_NULL,
+ COOKIE_NULL
}
},
{
@@ -454,6 +847,8 @@ static const struct strct_test_data test_data[] = {
"",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -467,6 +862,8 @@ static const struct strct_test_data test_data[] = {
" ",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -480,6 +877,8 @@ static const struct strct_test_data test_data[] = {
"\t",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -493,6 +892,8 @@ static const struct strct_test_data test_data[] = {
"var=,",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -506,6 +907,8 @@ static const struct strct_test_data test_data[] = {
"var=\"\\ \"",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -519,6 +922,8 @@ static const struct strct_test_data test_data[] = {
"var=value space",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -532,6 +937,8 @@ static const struct strct_test_data test_data[] = {
"var=value\ttab",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -545,6 +952,8 @@ static const struct strct_test_data test_data[] = {
"=",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -558,6 +967,8 @@ static const struct strct_test_data test_data[] = {
"====",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -571,6 +982,8 @@ static const struct strct_test_data test_data[] = {
";=",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -584,6 +997,8 @@ static const struct strct_test_data test_data[] = {
"var",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -597,6 +1012,8 @@ static const struct strct_test_data test_data[] = {
"=;",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -610,6 +1027,8 @@ static const struct strct_test_data test_data[] = {
"= ;",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -623,6 +1042,8 @@ static const struct strct_test_data test_data[] = {
";= ;",
0,
0,
+ 0,
+ 0,
{
COOKIE_NULL,
COOKIE_NULL,
@@ -636,7 +1057,10 @@ static const struct strct_test_data test_data[] = {
/* Global parameters */
static int verbose;
static int oneone; /**< If false use HTTP/1.0 for requests*/
-static int use_non_strict;
+static int use_strict_n1;
+static int use_strict_zero;
+static int use_strict_p1;
+static int strict_level;
static void
test_global_init (void)
@@ -700,12 +1124,19 @@ ahcCheck (void *cls,
struct MHD_Response *response;
enum MHD_Result ret;
struct ahc_cls_type *const param = (struct ahc_cls_type *) cls;
- const unsigned int expected_num_cookies =
- use_non_strict ? param->check->num_cookies_non_strict :
- param->check->num_cookies_strict;
+ unsigned int expected_num_cookies;
unsigned int i;
int cookie_failed;
+ if (use_strict_p1)
+ expected_num_cookies = param->check->num_cookies_strict_p1;
+ else if (use_strict_zero)
+ expected_num_cookies = param->check->num_cookies_strict_zero;
+ else if (use_strict_n1)
+ expected_num_cookies = param->check->num_cookies_strict_n1;
+ else
+ externalErrorExit ();
+
if (NULL == param)
mhdErrorExitDesc ("cls parameter is NULL");
@@ -813,7 +1244,17 @@ ahcCheck (void *cls,
cookie_failed = 1;
}
if (cookie_failed)
- return MHD_NO; /* Break connection */
+ {
+ response =
+ MHD_create_response_from_buffer_static (MHD_STATICSTR_LEN_ (PAGE_ERROR),
+ PAGE_ERROR);
+ ret = MHD_queue_response (connection,
+ MHD_HTTP_BAD_REQUEST,
+ response);
+ MHD_destroy_response (response);
+
+ return ret;
+ }
if (&marker != *req_cls)
{
@@ -1057,7 +1498,6 @@ check_result (CURLcode curl_code, CURL *c, long
expected_code,
struct CBC *pcbc)
{
long code;
- unsigned int ret;
if (CURLE_OK != curl_code)
{
@@ -1079,15 +1519,15 @@ check_result (CURLcode curl_code, CURL *c, long
expected_code,
if (CURLE_OK != curl_easy_getinfo (c, CURLINFO_RESPONSE_CODE, &code))
libcurlErrorExit ();
- ret = 1;
if (expected_code != code)
{
- fprintf (stderr, "The response has wrong HTTP code: %ld\tExpected: %ld.\n",
+ fprintf (stderr, "### The response has wrong HTTP code: %ld\t"
+ "Expected: %ld.\n",
code, expected_code);
- ret = 0;
+ return 0;
}
else if (verbose)
- printf ("The response has expected HTTP code: %ld\n", expected_code);
+ printf ("### The response has expected HTTP code: %ld\n", expected_code);
if (pcbc->pos != MHD_STATICSTR_LEN_ (PAGE))
{
@@ -1105,7 +1545,7 @@ check_result (CURLcode curl_code, CURL *c, long
expected_code,
fflush (stderr);
fflush (stdout);
- return ret;
+ return 1;
}
@@ -1125,13 +1565,13 @@ testExternalPolling (void)
if (MHD_NO != MHD_is_feature_supported (MHD_FEATURE_AUTODETECT_BIND_PORT))
port = 0;
else
- port = 1340 + oneone ? 0 : 1 + use_non_strict ? 0 : 2;
+ port = 1340 + oneone ? 0 : 6 + (uint16_t) (1 + strict_level);
d = MHD_start_daemon (MHD_USE_ERROR_LOG,
port, NULL, NULL,
&ahcCheck, &ahc_param,
MHD_OPTION_STRICT_FOR_CLIENT,
- (int) (use_non_strict ? 0 : 1),
+ (int) (strict_level),
MHD_OPTION_END);
if (d == NULL)
return 1;
@@ -1167,13 +1607,13 @@ testExternalPolling (void)
MHD_HTTP_OK, &cbc))
{
if (verbose)
- printf ("Got expected response for the check at line %u.\n",
+ printf ("### Got expected response for the check at line %u.\n",
test_data[i].line_num);
fflush (stdout);
}
else
{
- fprintf (stderr, "FAILED request for the check at line %u.\n",
+ fprintf (stderr, "### FAILED request for the check at line %u.\n",
test_data[i].line_num);
fflush (stderr);
failed = 1;
@@ -1200,7 +1640,19 @@ main (int argc, char *const *argv)
has_param (argc, argv, "-s") ||
has_param (argc, argv, "--silent"));
oneone = ! has_in_name (argv[0], "10");
- use_non_strict = has_in_name (argv[0], "_nonstrict");
+ use_strict_n1 = has_in_name (argv[0], "_strict_n1");
+ use_strict_zero = has_in_name (argv[0], "_strict_zero");
+ use_strict_p1 = has_in_name (argv[0], "_strict_p1");
+ if (1 != ((use_strict_n1 ? 1 : 0) + (use_strict_zero ? 1 : 0)
+ + (use_strict_p1 ? 1 : 0)))
+ return 99;
+
+ if (use_strict_n1)
+ strict_level = -1;
+ else if (use_strict_zero)
+ strict_level = 0;
+ else if (use_strict_p1)
+ strict_level = 1;
test_global_init ();
--
To stop receiving notification emails like this one, please contact
gnunet@gnunet.org.
- [libmicrohttpd] branch master updated (3444792f -> 1e7ad301), gnunet, 2022/12/19
- [libmicrohttpd] 01/06: response.c: added new internal function to avoid repetitive malloc()s, gnunet, 2022/12/19
- [libmicrohttpd] 03/06: parse_http_version(): cosmetics, gnunet, 2022/12/19
- [libmicrohttpd] 05/06: test_parse_cookies: rewritten, gnunet, 2022/12/19
- [libmicrohttpd] 06/06: Refactored cookies parsing.,
gnunet <=
- [libmicrohttpd] 04/06: MHD_get_version_bin(): added new function, gnunet, 2022/12/19
- [libmicrohttpd] 02/06: digestauth: avoid malloc() repeat by using the new function, gnunet, 2022/12/19