From b067a341987128fef5d0508b0d25b7749f300ca1 Mon Sep 17 00:00:00 2001 From: Ankur Tyagi Date: Wed, 15 Oct 2025 16:42:44 +1300 Subject: [PATCH] memcached: patch CVE-2023-46853 Details https://nvd.nist.gov/vuln/detail/CVE-2023-46853 Signed-off-by: Ankur Tyagi Signed-off-by: Anuj Mittal --- .../memcached/memcached/CVE-2023-46853.patch | 117 ++++++++++++++++++ .../memcached/memcached_1.6.17.bb | 1 + 2 files changed, 118 insertions(+) create mode 100644 meta-networking/recipes-support/memcached/memcached/CVE-2023-46853.patch diff --git a/meta-networking/recipes-support/memcached/memcached/CVE-2023-46853.patch b/meta-networking/recipes-support/memcached/memcached/CVE-2023-46853.patch new file mode 100644 index 0000000000..cf8aaf467b --- /dev/null +++ b/meta-networking/recipes-support/memcached/memcached/CVE-2023-46853.patch @@ -0,0 +1,117 @@ +From 51c1f144d57379bd77f5b04c462171d26ebc5514 Mon Sep 17 00:00:00 2001 +From: dormando +Date: Wed, 2 Aug 2023 15:45:56 -0700 +Subject: [PATCH] CVE-2023-46853 + +proxy: fix off-by-one if \r is missing + +A bunch of the parser assumed we only had \r\n, but I didn't actually +have that strictness set. Some commands worked and some broke in subtle +ways when just "\n" was being submitted. + +I'm not 100% confident in this change yet so I'm opening a PR to stage +it while I run some more thorough tests. + +CVE: CVE-2023-46853 +Upstream-Status: Backport [https://github.com/memcached/memcached/commit/6987918e9a3094ec4fc8976f01f769f624d790fa] +(cherry picked from commit 6987918e9a3094ec4fc8976f01f769f624d790fa) +Signed-off-by: Ankur Tyagi +--- + proxy.h | 1 + + proxy_request.c | 22 ++++++++++++++++------ + t/proxy.t | 5 +++-- + 3 files changed, 20 insertions(+), 8 deletions(-) + +diff --git a/proxy.h b/proxy.h +index 015c093..29e5175 100644 +--- a/proxy.h ++++ b/proxy.h +@@ -271,6 +271,7 @@ struct mcp_parser_s { + uint8_t keytoken; // because GAT. sigh. also cmds without a key. + uint32_t parsed; // how far into the request we parsed already + uint32_t reqlen; // full length of request buffer. ++ uint32_t endlen; // index to the start of \r\n or \n + int vlen; + uint32_t klen; // length of key. + uint16_t tokens[PARSER_MAX_TOKENS]; // offsets for start of each token +diff --git a/proxy_request.c b/proxy_request.c +index 457e9a1..6351d02 100644 +--- a/proxy_request.c ++++ b/proxy_request.c +@@ -9,7 +9,7 @@ + // where we later scan or directly feed data into API's. + static int _process_tokenize(mcp_parser_t *pr, const size_t max) { + const char *s = pr->request; +- int len = pr->reqlen - 2; ++ int len = pr->endlen; + + // since multigets can be huge, we can't purely judge reqlen against this + // limit, but we also can't index past it since the tokens are shorts. +@@ -93,7 +93,7 @@ static int _process_request_key(mcp_parser_t *pr) { + // Returns the offset for the next key. + size_t _process_request_next_key(mcp_parser_t *pr) { + const char *cur = pr->request + pr->parsed; +- int remain = pr->reqlen - pr->parsed - 2; ++ int remain = pr->endlen - pr->parsed; + + // chew off any leading whitespace. + while (remain) { +@@ -126,7 +126,7 @@ static int _process_request_metaflags(mcp_parser_t *pr, int token) { + return 0; + } + const char *cur = pr->request + pr->tokens[token]; +- const char *end = pr->request + pr->reqlen - 2; ++ const char *end = pr->request + pr->endlen; + + // We blindly convert flags into bits, since the range of possible + // flags is deliberately < 64. +@@ -290,15 +290,25 @@ int process_request(mcp_parser_t *pr, const char *command, size_t cmdlen) { + return -1; + } + +- const char *s = memchr(command, ' ', cmdlen-2); ++ // Commands can end with bare '\n's. Depressingly I intended to be strict ++ // with a \r\n requirement but never did this and need backcompat. ++ // In this case we _know_ \n is at cmdlen because we can't enter this ++ // function otherwise. ++ if (cm[cmdlen-2] == '\r') { ++ pr->endlen = cmdlen - 2; ++ } else { ++ pr->endlen = cmdlen - 1; ++ } ++ ++ const char *s = memchr(command, ' ', pr->endlen); + if (s != NULL) { + cl = s - command; + } else { +- cl = cmdlen - 2; ++ cl = pr->endlen; + } + pr->keytoken = 0; + pr->has_space = false; +- pr->parsed = cl + 1; ++ pr->parsed = cl; + pr->request = command; + pr->reqlen = cmdlen; + int token_max = PARSER_MAX_TOKENS; +diff --git a/t/proxy.t b/t/proxy.t +index 37caa27..af6213a 100644 +--- a/t/proxy.t ++++ b/t/proxy.t +@@ -151,13 +151,14 @@ my $p_sock = $p_srv->sock; + # NOTE: memcached always allowed [\r]\n for single command lines, but payloads + # (set/etc) require exactly \r\n as termination. + # doc/protocol.txt has always specified \r\n for command/response. +-# Proxy is more strict than normal server in this case. ++# Note a bug lead me to believe that the proxy was more strict, we accept any ++# \n or \r\n terminated commands. + { + my $s = $srv[0]->sock; + print $s "version\n"; + like(<$s>, qr/VERSION/, "direct server version cmd with just newline"); + print $p_sock "version\n"; +- like(<$p_sock>, qr/SERVER_ERROR/, "proxy version cmd with just newline"); ++ like(<$p_sock>, qr/VERSION/, "proxy version cmd with just newline"); + print $p_sock "version\r\n"; + like(<$p_sock>, qr/VERSION/, "proxy version cmd with full CRLF"); + } diff --git a/meta-networking/recipes-support/memcached/memcached_1.6.17.bb b/meta-networking/recipes-support/memcached/memcached_1.6.17.bb index b4c1847bf6..bfa1450368 100644 --- a/meta-networking/recipes-support/memcached/memcached_1.6.17.bb +++ b/meta-networking/recipes-support/memcached/memcached_1.6.17.bb @@ -23,6 +23,7 @@ SRC_URI = "http://www.memcached.org/files/${BP}.tar.gz \ file://memcached-add-hugetlbfs-check.patch \ file://0001-Fix-function-protypes.patch \ file://CVE-2023-46852.patch \ + file://CVE-2023-46853.patch \ " SRC_URI[sha256sum] = "2055e373613d8fc21529aff9f0adce3e23b9ce01ba0478d30e7941d9f2bd1224"