diff --git a/backport-conn-fix-hostname-move-on-connection-reuse.patch b/backport-conn-fix-hostname-move-on-connection-reuse.patch new file mode 100644 index 0000000000000000000000000000000000000000..28a840b32f2c5480c5f99d6310f27b7527620efe --- /dev/null +++ b/backport-conn-fix-hostname-move-on-connection-reuse.patch @@ -0,0 +1,64 @@ +From bf41be6292cf712315815c722aab2653a0ec827f Mon Sep 17 00:00:00 2001 +From: Stefan Eissing +Date: Fri, 10 Oct 2025 09:48:52 +0200 +Subject: [PATCH] conn: fix hostname move on connection reuse + +When reusing a connection, the `host` and `conn_to_host` hostname +structs are moved from the template connection onto the existing one. + +There was a NULLing of a tempplate member missing in `conn_to_host` +which could then lead to a double free. + +Make this struct move into a static function, doing the correct +thing for both `struct hostname` in a connection. + +Reported-by: Joshua Rogers +Closes #18995 + +Conflict:context adapt +Reference:https://github.com/curl/curl/commit/bf41be6292cf712315815c722aab2653a0ec827f +--- + lib/url.c | 20 +++++++++++--------- + 1 file changed, 11 insertions(+), 9 deletions(-) + +diff --git a/lib/url.c b/lib/url.c +index 6a433b09ef..6d69fc11bf 100644 +--- a/lib/url.c ++++ b/lib/url.c +@@ -3286,6 +3286,14 @@ static CURLcode resolve_server(struct Curl_easy *data, + return resolve_fresh(data, conn, async); + } + ++static void url_move_hostname(struct hostname *dest, struct hostname *src) ++{ ++ Curl_safefree(dest->rawalloc); ++ Curl_free_idnconverted_hostname(dest); ++ *dest = *src; ++ memset(src, 0, sizeof(*src)); ++} ++ + /* + * Cleanup the connection `temp`, just allocated for `data`, before using the + * previously `existing` one for `data`. All relevant info is copied over +@@ -3340,15 +3348,9 @@ static void reuse_conn(struct Curl_easy *data, + * used the original hostname in SNI to negotiate? Do we send + * requests for another host through the different SNI? + */ +- Curl_free_idnconverted_hostname(&existing->host); +- Curl_free_idnconverted_hostname(&existing->conn_to_host); +- Curl_safefree(existing->host.rawalloc); +- Curl_safefree(existing->conn_to_host.rawalloc); +- existing->host = temp->host; +- temp->host.rawalloc = NULL; +- temp->host.encalloc = NULL; +- existing->conn_to_host = temp->conn_to_host; +- temp->conn_to_host.rawalloc = NULL; ++ url_move_hostname(&existing->host, &temp->host); ++ url_move_hostname(&existing->conn_to_host, &temp->conn_to_host); ++ + existing->conn_to_port = temp->conn_to_port; + existing->remote_port = temp->remote_port; + Curl_safefree(existing->hostname_resolve); +-- +2.43.0 + diff --git a/backport-h3-fix-query-of-concurrent-streams.patch b/backport-h3-fix-query-of-concurrent-streams.patch new file mode 100644 index 0000000000000000000000000000000000000000..13244cfaa19ffe550ff63deb9e47e2f0e828f216 --- /dev/null +++ b/backport-h3-fix-query-of-concurrent-streams.patch @@ -0,0 +1,47 @@ +From 695eee432fc99eb3c004a160097550f3ffcd52f2 Mon Sep 17 00:00:00 2001 +From: Stefan Eissing +Date: Thu, 10 Jul 2025 13:18:03 +0200 +Subject: [PATCH] h3: fix query of concurrent streams + +Queries gave wrong value or ran into NULL pointers when called at +times when connection filter was not fully initialized. + +Closes #17886 + +Conflict:context adapt +remove file lib/vquic/curl_osslq.c which not introduced in +Reference:https://github.com/curl/curl/commit/695eee432fc99eb3c004a160097550f3ffcd52f2 +--- + lib/http2.c | 2 +- + lib/vquic/curl_quiche.c | 2 +- + 2 files changed, 2 insertions(+), 2 deletions(-) + +diff --git a/lib/http2.c b/lib/http2.c +index 1f65cbdd02..a8f6ae439f 100644 +--- a/lib/http2.c ++++ b/lib/http2.c +@@ -2750,7 +2750,7 @@ static CURLcode cf_h2_query(struct Curl_cfilter *cf, + DEBUGASSERT(pres1); + + CF_DATA_SAVE(save, cf, data); +- if(nghttp2_session_check_request_allowed(ctx->h2) == 0) { ++ if(!ctx->h2 || !nghttp2_session_check_request_allowed(ctx->h2)) { + /* the limit is what we have in use right now */ + effective_max = CONN_INUSE(cf->conn); + } +diff --git a/lib/vquic/curl_quiche.c b/lib/vquic/curl_quiche.c +index 0ac389d541..c4331c46bb 100644 +--- a/lib/vquic/curl_quiche.c ++++ b/lib/vquic/curl_quiche.c +@@ -1516,7 +1516,7 @@ static CURLcode cf_quiche_query(struct Curl_cfilter *cf, + switch(query) { + case CF_QUERY_MAX_CONCURRENT: { + uint64_t max_streams = CONN_INUSE(cf->conn); +- if(!ctx->goaway) { ++ if(!ctx->goaway && ctx->qconn) { + max_streams += quiche_conn_peer_streams_left_bidi(ctx->qconn); + } + *pres1 = (max_streams > INT_MAX)? INT_MAX : (int)max_streams; +-- +2.43.0 + diff --git a/backport-krb5_gssapi-fix-memory-leak-on-error-path.patch b/backport-krb5_gssapi-fix-memory-leak-on-error-path.patch new file mode 100644 index 0000000000000000000000000000000000000000..0adfb407920b5a300ab934a8516f460c41f4ad34 --- /dev/null +++ b/backport-krb5_gssapi-fix-memory-leak-on-error-path.patch @@ -0,0 +1,32 @@ +From 2c6505e0ef9c0368e9acbef5662eb15e43328b65 Mon Sep 17 00:00:00 2001 +From: Daniel Stenberg +Date: Thu, 9 Oct 2025 16:51:55 +0200 +Subject: [PATCH] krb5_gssapi: fix memory leak on error path + +If a non-compliant amount of bytes is received, the function would +return error without free. + +Reported-by: Joshua Rogers +Closes #18976 + +Conflict:NA +Reference:https://github.com/curl/curl/commit/2c6505e0ef9c0368e9acbef5662eb15e43328b65 +--- + lib/vauth/krb5_gssapi.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/lib/vauth/krb5_gssapi.c b/lib/vauth/krb5_gssapi.c +index 70144e5514..a414d0a359 100644 +--- a/lib/vauth/krb5_gssapi.c ++++ b/lib/vauth/krb5_gssapi.c +@@ -225,6 +225,7 @@ CURLcode Curl_auth_create_gssapi_security_message(struct Curl_easy *data, + /* Not 4 octets long so fail as per RFC4752 Section 3.1 */ + if(output_token.length != 4) { + infof(data, "GSSAPI handshake failure (invalid security data)"); ++ gss_release_buffer(&unused_status, &output_token); + return CURLE_BAD_CONTENT_ENCODING; + } + +-- +2.43.0 + diff --git a/backport-libssh-fix-readdir-issues.patch b/backport-libssh-fix-readdir-issues.patch new file mode 100644 index 0000000000000000000000000000000000000000..c47a87489d092244774ae20dd008585622211db1 --- /dev/null +++ b/backport-libssh-fix-readdir-issues.patch @@ -0,0 +1,58 @@ +From ac8271d020848bca7da0976bd4eeb57a0bb4178e Mon Sep 17 00:00:00 2001 +From: Eshan Kelkar +Date: Tue, 8 Jul 2025 12:42:29 +0530 +Subject: [PATCH] libssh: fix readdir issues + +Signed-off-by: Eshan Kelkar +Closes #17856 + +Conflict:context adapt +remove comment which not suits for current context +myssh_to(data, sshc, SSH_SFTP_CLOSE); => state(data, SSH_SFTP_CLOSE); +Reference:https://github.com/curl/curl/commit/ac8271d020848bca7da0976bd4eeb57a0bb4178e +--- + lib/vssh/libssh.c | 7 ++++--- + 1 file changed, 4 insertions(+), 3 deletions(-) + +diff --git a/lib/vssh/libssh.c b/lib/vssh/libssh.c +index c5044b2..c06c72a 100644 +--- a/lib/vssh/libssh.c ++++ b/lib/vssh/libssh.c +@@ -1506,7 +1506,7 @@ static CURLcode myssh_statemach_act(struct Curl_easy *data, bool *block) + break; + } + else { +- failf(data, "Could not open remote file for reading: %s", ++ failf(data, "Could not open remote directory for reading: %s", + ssh_get_error(sshc->ssh_session)); + MOVE_TO_SFTP_CLOSE_STATE(); + break; +@@ -1519,7 +1519,7 @@ static CURLcode myssh_statemach_act(struct Curl_easy *data, bool *block) + + sshc->readdir_link_attrs = sftp_lstat(sshc->sftp_session, + sshc->readdir_linkPath); +- if(sshc->readdir_link_attrs == 0) { ++ if(!sshc->readdir_link_attrs) { + failf(data, "Could not read symlink for reading: %s", + ssh_get_error(sshc->ssh_session)); + MOVE_TO_SFTP_CLOSE_STATE(); +@@ -1529,7 +1529,7 @@ static CURLcode myssh_statemach_act(struct Curl_easy *data, bool *block) + if(!sshc->readdir_link_attrs->name) { + sshc->readdir_tmp = sftp_readlink(sshc->sftp_session, + sshc->readdir_linkPath); +- if(!sshc->readdir_filename) ++ if(!sshc->readdir_tmp) + sshc->readdir_len = 0; + else + sshc->readdir_len = strlen(sshc->readdir_tmp); +@@ -1546,6 +1546,7 @@ static CURLcode myssh_statemach_act(struct Curl_easy *data, bool *block) + + if(Curl_dyn_addf(&sshc->readdir_buf, " -> %s", + sshc->readdir_filename)) { ++ state(data, SSH_SFTP_CLOSE); + sshc->actualcode = CURLE_OUT_OF_MEMORY; + break; + } +-- +2.43.0 + diff --git a/backport-libssh-properly-free-sftp_attributes.patch b/backport-libssh-properly-free-sftp_attributes.patch new file mode 100644 index 0000000000000000000000000000000000000000..07f5b2011436778bc054471244fb980e512cf977 --- /dev/null +++ b/backport-libssh-properly-free-sftp_attributes.patch @@ -0,0 +1,37 @@ +From b42f226b94409defd7487347b543911f18eb1468 Mon Sep 17 00:00:00 2001 +From: x2018 +Date: Mon, 17 Nov 2025 18:36:42 +0800 +Subject: [PATCH] libssh: properly free sftp_attributes + +Closes #19564 + +Conflict:context adapt +Reference:https://github.com/curl/curl/commit/b42f226b94409defd7487347b543911f18eb1468 +--- + lib/vssh/libssh.c | 5 ++--- + 1 file changed, 2 insertions(+), 3 deletions(-) + +diff --git a/lib/vssh/libssh.c b/lib/vssh/libssh.c +index 8653c4901d..9428a20a5f 100644 +--- a/lib/vssh/libssh.c ++++ b/lib/vssh/libssh.c +@@ -1137,14 +1137,13 @@ static CURLcode myssh_statemach_act(struct Curl_easy *data, bool *block) + attrs = sftp_stat(sshc->sftp_session, protop->path); + if(attrs) { + curl_off_t size = attrs->size; ++ sftp_attributes_free(attrs); + if(size < 0) { + failf(data, "Bad file size (%" CURL_FORMAT_CURL_OFF_T ")", size); + MOVE_TO_ERROR_STATE(CURLE_BAD_DOWNLOAD_RESUME); + break; + } +- data->state.resume_from = attrs->size; +- +- sftp_attributes_free(attrs); ++ data->state.resume_from = size; + } + else { + data->state.resume_from = 0; +-- +2.43.0 + diff --git a/backport-noproxy-fix-the-IPV6-network-mask-pattern-match.patch b/backport-noproxy-fix-the-IPV6-network-mask-pattern-match.patch new file mode 100644 index 0000000000000000000000000000000000000000..85e6406d75769cddf297115718142b2d8a8dc379 --- /dev/null +++ b/backport-noproxy-fix-the-IPV6-network-mask-pattern-match.patch @@ -0,0 +1,36 @@ +From 1a3a5cb72038a0b70cb5721e9762734f1691aa6d Mon Sep 17 00:00:00 2001 +From: Daniel Stenberg +Date: Mon, 6 Oct 2025 16:53:27 +0200 +Subject: [PATCH] noproxy: fix the IPV6 network mask pattern match + +It would mismatch if the network prefix length with was not divisible by +8. + +Extended test 1614 to verify + +Reported-by: Stanislav Fort + +Closes #18891 + +Conflict:remove change of test file tests/unit/unit1614.c which requires too many adapt +Reference:https://github.com/curl/curl/commit/1a3a5cb72038a0b70cb5721e9762734f1691aa6d +--- + lib/noproxy.c | 2 +- + 1 files changed, 1 insertions(+), 1 deletion(-) + +diff --git a/lib/noproxy.c b/lib/noproxy.c +index 2983fa4a3a..20a335993d 100644 +--- a/lib/noproxy.c ++++ b/lib/noproxy.c +@@ -99,7 +99,7 @@ UNITTEST bool Curl_cidr6_match(const char *ipv6, + return FALSE; + if(bytes && memcmp(address, check, bytes)) + return FALSE; +- if(rest && !((address[bytes] ^ check[bytes]) & (0xff << (8 - rest)))) ++ if(rest && ((address[bytes] ^ check[bytes]) & (0xff << (8 - rest)))) + return FALSE; + + return TRUE; +-- +2.43.0 + diff --git a/backport-openldap-fix-memory-leak-in-error-path.patch b/backport-openldap-fix-memory-leak-in-error-path.patch new file mode 100644 index 0000000000000000000000000000000000000000..9a803c4b1c27212810f3f2b54759c03eab33ab5b --- /dev/null +++ b/backport-openldap-fix-memory-leak-in-error-path.patch @@ -0,0 +1,39 @@ +From d35bdfa8f28d646166592f607b8100b6c60be0f0 Mon Sep 17 00:00:00 2001 +From: Daniel Stenberg +Date: Thu, 9 Oct 2025 22:50:01 +0200 +Subject: [PATCH] openldap: fix memory-leak in error path + +The 'ber' pointer could escape a free if an early error occurred. + +Reported-by: Joshua Rogers +Closes #18985 + +Conflict:context adapt +Reference:https://github.com/curl/curl/commit/d35bdfa8f28d646166592f607b8100b6c60be0f0 +--- + lib/openldap.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/lib/openldap.c b/lib/openldap.c +index 72cfdc7039..92364e3e77 100644 +--- a/lib/openldap.c ++++ b/lib/openldap.c +@@ -1216,7 +1216,6 @@ static ssize_t oldap_recv(struct Curl_easy *data, int sockindex, char *buf, + break; + } + +- ber_free(ber, 0); + + if(!result) + result = client_write(data, STRCONST("\n"), NULL, 0, NULL, 0); +@@ -1225,6 +1224,7 @@ static ssize_t oldap_recv(struct Curl_easy *data, int sockindex, char *buf, + break; + } + ++ ber_free(ber, 0); + ldap_msgfree(msg); + *err = result; + return result? -1: 0; +-- +2.43.0 + diff --git a/backport-openssl-fix-a-potential-memory-leak-of-params_cert.patch b/backport-openssl-fix-a-potential-memory-leak-of-params_cert.patch new file mode 100644 index 0000000000000000000000000000000000000000..15f72485b4c8cd9b8e6420fc52317f014a1fc3cc --- /dev/null +++ b/backport-openssl-fix-a-potential-memory-leak-of-params_cert.patch @@ -0,0 +1,28 @@ +From 22b8a6430dca99b4db7170fd02b2041f538fd1bd Mon Sep 17 00:00:00 2001 +From: x2018 +Date: Mon, 17 Nov 2025 14:12:14 +0800 +Subject: [PATCH] openssl: fix a potential memory leak of params.cert + +Closes #19560 + +Conflict:context adapt +Reference:https://github.com/curl/curl/commit/22b8a6430dca99b4db7170fd02b2041f538fd1bd +--- + lib/vtls/openssl.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/lib/vtls/openssl.c b/lib/vtls/openssl.c +index 72ca0f6cb3..9b3ca9b5ea 100644 +--- a/lib/vtls/openssl.c ++++ b/lib/vtls/openssl.c +@@ -1214,6 +1214,7 @@ int cert_stuff(struct Curl_easy *data, + failf(data, "unable to set client certificate [%s]", + ossl_strerror(ERR_get_error(), error_buffer, + sizeof(error_buffer))); ++ X509_free(params.cert); + return 0; + } + X509_free(params.cert); /* we don't need the handle any more... */ +-- +2.43.0 + diff --git a/backport-pop3-fix-CAPA-response-termination-detection.patch b/backport-pop3-fix-CAPA-response-termination-detection.patch new file mode 100644 index 0000000000000000000000000000000000000000..650ad850eb2a465656640b25caddc73d808f9e50 --- /dev/null +++ b/backport-pop3-fix-CAPA-response-termination-detection.patch @@ -0,0 +1,48 @@ +From a49e4e3d16991465144558f405b2d7972824abb0 Mon Sep 17 00:00:00 2001 +From: TheBitBrine +Date: Sun, 26 Oct 2025 03:15:07 +0000 +Subject: [PATCH] pop3: fix CAPA response termination detection + +The code was checking if a line starts with '.', which would +incorrectly match capability names starting with dots. Per RFC 2449, +the terminator must be a line containing only a single dot. + +RFC 2449 also explicitly excludes '.' from valid capability name +starting characters, so this is purely theoretical, but the code +should match the spec. + +Changed to check for exact match: line length of 3 with '.\r' or +length 2 with '.\n' to handle both CRLF and LF-only servers. + +(Mistake detected with ZeroPath) + +Fixes #19228 +Reported-by: Joshua Rogers +Closes #19245 + +Conflict:NA +Reference:https://github.com/curl/curl/commit/a49e4e3d16991465144558f405b2d7972824abb0 +--- + lib/pop3.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +diff --git a/lib/pop3.c b/lib/pop3.c +index 2fd496cb31..c6b6ed659c 100644 +--- a/lib/pop3.c ++++ b/lib/pop3.c +@@ -323,8 +323,10 @@ static bool pop3_endofresp(struct Curl_easy *data, struct connectdata *conn, + + /* Are we processing CAPA command responses? */ + if(pop3c->state == POP3_CAPA) { +- /* Do we have the terminating line? */ +- if(len >= 1 && line[0] == '.') ++ /* Do we have the terminating line? Per RFC 2449 this is a line ++ containing only a single dot */ ++ if((len == 3 && line[0] == '.' && line[1] == '\r') || ++ (len == 2 && line[0] == '.' && line[1] == '\n')) + /* Treat the response as a success */ + *resp = '+'; + else +-- +2.43.0 + diff --git a/curl.spec b/curl.spec index 731bbe2090757b59d79cb7129187a6412ad92308..fe20b5222953990efb5d6099e453eccfc8d450e0 100644 --- a/curl.spec +++ b/curl.spec @@ -7,7 +7,7 @@ Name: curl Version: 8.4.0 -Release: 23 +Release: 24 Summary: Curl is used in command lines or scripts to transfer data License: curl URL: https://curl.se/ @@ -58,6 +58,15 @@ Patch49: backport-tool_getparam-clear-argument-only-when-needed.patch Patch50: backport-CVE-2025-9086.patch Patch51: backport-CVE-2025-10148.patch Patch52: backport-CVE-2025-10966.patch +Patch53: backport-libssh-fix-readdir-issues.patch +Patch54: backport-h3-fix-query-of-concurrent-streams.patch +Patch55: backport-noproxy-fix-the-IPV6-network-mask-pattern-match.patch +Patch56: backport-krb5_gssapi-fix-memory-leak-on-error-path.patch +Patch57: backport-openldap-fix-memory-leak-in-error-path.patch +Patch58: backport-conn-fix-hostname-move-on-connection-reuse.patch +Patch59: backport-pop3-fix-CAPA-response-termination-detection.patch +Patch60: backport-libssh-properly-free-sftp_attributes.patch +Patch61: backport-openssl-fix-a-potential-memory-leak-of-params_cert.patch BuildRequires: automake brotli-devel coreutils gcc groff krb5-devel BuildRequires: libidn2-devel libnghttp2-devel libpsl-devel @@ -245,6 +254,20 @@ rm -rf ${RPM_BUILD_ROOT}%{_libdir}/libcurl.la %{_mandir}/man3/* %changelog +* Mon Nov 24 2025 zhouyihang - 8.4.0-24 +- Type:bugfix +- CVE:NA +- SUG:NA +- DESC:libssh: fix readdir issues + h3: fix query of concurrent streams + noproxy: fix the IPV6 network mask pattern match + krb5_gssapi: fix memory leak on error path + openldap: fix memory-leak in error path + conn: fix hostname move on connection reuse + pop3: fix CAPA response termination detection + libssh: properly free sftp_attributes + openssl: fix a potential memory leak of params.cert + * Fri Nov 14 2025 zhouyihang - 8.4.0-23 - Type:CVE - CVE:CVE-2025-10966