commit 72ab415176dafac9c054969b3958b517116becb8
parent 41677cbcbd02f995f5e302ca0ec1de9d96e84d9b
Author: Evgeny Grin (Karlson2k) <k2k@drgrin.dev>
Date: Fri, 13 Jun 2025 21:16:30 +0200
POST parser: accelerate by using memmem() for delimiters
Diffstat:
1 file changed, 90 insertions(+), 0 deletions(-)
diff --git a/src/mhd2/post_parser_funcs.c b/src/mhd2/post_parser_funcs.c
@@ -1469,6 +1469,49 @@ parse_post_mpart (struct MHD_Connection *restrict c,
mhd_assert (0 == p_data->value_off);
mhd_assert (mhd_POST_INVALID_POS == mf->delim_check_start);
mhd_assert (mhd_POST_INVALID_POS == mf->line_start);
+#ifdef HAVE_MEMMEM
+ if (mf->delim.size <= *pdata_size - i)
+ {
+ const char *delim_ptr;
+ if (! bare_lf_as_crlf)
+ delim_ptr = (const char *) memmem (buf + i,
+ *pdata_size - i,
+ mf->delim.data,
+ mf->delim.size);
+ else
+ delim_ptr = (const char *) memmem (buf + i,
+ *pdata_size - i,
+ mf->delim.data + 1,
+ mf->delim.size - 1);
+ if (NULL != delim_ptr)
+ {
+ size_t delim_pos;
+
+ mhd_assert (delim_ptr >= buf + i);
+ mhd_assert (delim_ptr + mf->delim.size - 1 <= buf + *pdata_size);
+
+ delim_pos = (size_t) (delim_ptr - buf);
+
+ mhd_assert (i <= delim_pos);
+
+ if (! bare_lf_as_crlf)
+ {
+ mf->line_start = delim_pos + 2u; /* '2' for CRLF */
+ i = delim_pos + mf->delim.size;
+ }
+ else
+ {
+ mf->line_start = delim_pos + 1u; /* '1' for LF */
+ i = delim_pos + mf->delim.size - 1;
+ }
+ mf->st = mhd_POST_MPART_ST_FIRST_DELIM_FOUND;
+ continue;
+ }
+ i = *pdata_size - mf->delim.size + 1u; /* '+ 1u' to move to then next position */
+ if (! bare_lf_as_crlf)
+ i += 1u;
+ }
+#endif /* HAVE_MEMMEM */
do /* Fast local loop */
{
#ifndef MHD_FAVOR_SMALL_CODE
@@ -1930,6 +1973,53 @@ parse_post_mpart (struct MHD_Connection *restrict c,
mhd_assert (mhd_POST_INVALID_POS == mf->delim_check_start);
mhd_assert (mhd_POST_INVALID_POS == mf->line_start);
mhd_assert (mhd_POST_INVALID_POS != p_data->field_start);
+#ifdef HAVE_MEMMEM
+ if (mf->delim.size <= *pdata_size - i)
+ {
+ const char *delim_ptr;
+ if (! bare_lf_as_crlf)
+ delim_ptr = (const char *) memmem (buf + i,
+ *pdata_size - i,
+ mf->delim.data,
+ mf->delim.size);
+ else
+ delim_ptr = (const char *) memmem (buf + i,
+ *pdata_size - i,
+ mf->delim.data + 1,
+ mf->delim.size - 1);
+ if (NULL != delim_ptr)
+ {
+ size_t delim_pos;
+
+ mhd_assert (delim_ptr >= buf + i);
+ mhd_assert (delim_ptr + mf->delim.size - 1 <= buf + *pdata_size);
+
+ delim_pos = (size_t) (delim_ptr - buf);
+
+ mhd_assert (i <= delim_pos);
+
+ if (! bare_lf_as_crlf)
+ {
+ mf->line_start = delim_pos + 2;
+ i = delim_pos + mf->delim.size;
+ }
+ else
+ {
+ mf->line_start = delim_pos + 1;
+ i = delim_pos + mf->delim.size - 1;
+ if ((delim_pos > i) &&
+ ('\r' == buf[delim_pos - 1]))
+ --delim_pos;
+ }
+ mf->delim_check_start = delim_pos;
+ mf->st = mhd_POST_MPART_ST_DELIM_FOUND;
+ continue;
+ }
+ i = *pdata_size - mf->delim.size + 1u; /* '+ 1u' to move to then next position */
+ if (! bare_lf_as_crlf)
+ i += 1u;
+ }
+#endif /* HAVE_MEMMEM */
do /* Fast local loop */
{
#ifndef MHD_FAVOR_SMALL_CODE