🠰 8.22.0 all changes pending release
Changes in 8.23.0 - October 14 2026
Changes:
- lib: CURL_GLOBAL_WIN32 -> CURL_GLOBAL_WINSOCK
- SMB: drop support
- tool_cb_wrt: inject the no-clobber number before the extension
- tool_cb_wrt: try up to .9999 when no-clobbering
Bugfixes:
- apple-sectrust: check ocsp copy alloc
- apple: shorten versions in `__builtin_available()` calls
- apple: sync hash init calls, add comments
- apple: sync up version guard macro style
- base64: avoid repeated input loads when encoding
- base64: optimize decode lookup table and quantum loop
- build: convert HAS_TIME_T_UNSIGNED to a compile-time check
- build: drop `HTTP_ONLY` option
- capsule: reject a capsule that can never be buffered
- cf-h1-proxy: reset chunk state on new request
- cf-h1-proxy: stricter status line parsing
- cf-https-connect: re-arm the timer for the hard eyeballs timeout
- cf-ngtcp2-cmn: fix possible `-Wdeclaration-after-statement`
- cf-ngtcp2-proxy: check for stream close on rx win update
- cf-ngtcp2-proxy: fix rx flow control
- cf-socket: adjust NO_SYN_RETRANSMISSIONS for older Windows
- cf-socket: clamp keepalive seconds-to-milliseconds conversions
- cfilters: fail a send that reports more written than requested
- clang-tidy: merge nested `if()`s
- cmake/Find*: drop deprecated compatibility config variables
- cmake: enable C++ library for GCC in AWS-LC/BoringSSL static builds
- cmake: link llvm stdc++ lib to AWS-LC/BoringSSL-specific feature detections only
- config2setopts: always set the security options for SCP/SFTP
- config2setopts: rename define for maximum cookie header length
- conncache: avoid evicting connect-only connections
- conncache: never discard a connection still in use
- conncache: remove bundle dest
- connect: do not busy-loop in blocking connect without a timeout
- connect: keep IP info and connect time when connect fails
- connectdata: use less curltime
- cookie: accept and ignore empty property names in Set-Cookie
- cookie: accept and ignore values for 'secure' and 'httponly'
- cookie: accept slightly longer lines in cookie jars
- cookie: cookies for a PSL domain from jar limits tailmatch
- cookie: ignore individual cookie errors when loading
- cpool: do not use admin handle for conn lookup
- cshutdown: make it smaller
- cshutdown: use ptrarray instead of llist
- curl-openssl.m4: sync LibreSSL detection method with rest of forks
- curl_addrinfo: drop redundant parentheses
- curl_easy_send/recv: check pointer arg
- curl_fopen: restore the uid and gid checks
- curl_formadd.md: mention the strlen() for names as well
- curl_multi_perform: doc update
- curl_setup.h: drop compatibility raw C flag `ENABLE_IPV6`
- CURLINFO_EFFECTIVE_URL.md: mention a short lifetime
- CURLOPT*ISSUERCERT*: not verified cryptographically
- CURLOPT_POSTFIELDSIZE.md: improve wording
- CURLOPT_SHARE.md: remove bad explanation for cookie sharing
- CURLOPT_SSL_CTX_FUNCTION.md: client cert caveats
- curlx_fopen: add macro to cast file mode
- cw-out: avoid O(n^2) work while buffering paused output
- cw-out: recheck callbacks for each call
- cw-pause: fix O(N^2) list traversal in cw_pause_flush
- DEPENDENCIES.md: fix release date for valgrind 3.0.0 to 2005-08-03
- DEPRECATE.md: reflect SMB removal
- DEPRECATE: Common Name support in TLS certificates for OpenSSL
- digest: check peer equality for staleness
- digest: fix maximum length quoted value parsing
- digest: parse without storing 'value' in local buffer
- digest: quote the digest-uri param as well
- dnscache/conncache tweaks
- dnscache: check hostname on lookup
- dnscache: compare full hostnames when lookup keys are truncated
- docs: add the missing .html to the URL encode book link
- docs: document and align the blocking situations
- docs: note CAINFO/SSL_VERIFYPEER/SSL_VERIFYSTATUS effect on LDAP
- docs: SSL session import/file updates
- doh: reject undersized HTTPS RDATA
- dynhds: check size overflows
- dynhds: grow header array geometrically
- easy: change event pollset construction
- easy: duplicating a zero byte memory area needs no malloc
- easy: make ca_cache_timeout standalone
- easy: validate buffer pointer in curl_easy_recv and curl_easy_send
- ECH: rework config, add test cases
- escape: polish encoding and decoding for speed
- escape: use hex-pair lookup in curl_easy_escape
- examples: clean up crawler link parsing resources
- fnmatch: replace recursive matcher with iterative greedy algorithm
- formdata: reject a negative content length in curl_formadd
- ftp: require TLS on the data connection for implicit FTPS
- ftp: tighten use_ssl check for conn reuse
- ftp: URL encode filenames when wildcarding
- ftplistparser: no more overwriting set.write_func
- ftplistparser: when wildcarding, skip files with slashes
- ftpserver.pl: fix warnings when running test 804
- getinfo: make sure CURLINFO_EFFECTIVE_URL does not contain creds
- getinfo: make sure CURLINFO_REDIRECT_URL does not contain creds
- getparam: switch off CONNECT headers when using -J
- glob: reduce the number of allocations for URLs that don't need globbing.
- global_init: tidy up, simplify, fix issues
- gnutls: hardening
- GnuTLS: remove our own OCSP signature verification
- gtls: no early return on verify fail
- h3-proxy: teardown fix
- happy eyeballs: bound work from many duplicate/failing addresses
- hash: change key arguments to const
- hash: vary bucket placement across process runs
- headers: avoid O(n^2) rescans in curl_easy_nextheader()
- hsts: cap max-age to two years
- hsts: on load, only remove exact duplicates
- HTTP-CONNECT: do not react to 401 responses
- http2: changes in error handling
- http2: don't send a CURLE_SEND_ERROR after a valid http2 response
- http2: fix reset after 1xx response
- http2: init some callbacks for HTTP/2 push easy handles
- http2: initialize URL handle for server pushes
- http2: limit trailers and headers count
- http2: update a refused stream's error after GOAWAY
- http2: use stream in userdata
- http: abide to close-rules when transfer-encoding off
- http: ignore Proxy-Authenticate unless the response comes from a proxy
- http: only enable Negotiate/NTLM to allowed origins
- http: reject empty header names
- http: reject resumed uploads
- http_aws_sigv4: fix the s3express service name
- http_chunks: accept exactly 17 characters chunk-size
- http_chunks: limit trailers size
- httpsig-key.md: correct the generating Ed25519 keys commands
- httpsrr+ech: check target and port
- if2ip: check interface name case sensitive
- imap: close the connection on premature done instead of finalizing
- imap: compare selected mailbox names case-sensitively
- imap: do size checks using 64-bit math
- inet_pton: reject a colon that ends an IPv6 address
- IPFS.md: replace sunset link, allowlist another one to avoid `mdlinkcheck` hang
- KNOWN_BUGS: drop the curl-config private details entry
- KNOWN_BUGS: drop the empty error buffer entry, it no longer happens
- ldap: base64-encode a non-SAFE DN and reject a control-byte type name
- ldap: tidy up variable scope, merge nested `#if`s
- lib557: exclude three floating point test cases for VS2013 and earlier
- lib: connection shutdown, cleanup code
- lib: make private functions static and remove unused code
- lib: reject internal handles in the multi/easy public API
- lib: replace `CURLX_FILE_MODE()` with `mode_t` cast
- libssh2: match hashed known_hosts entries by host
- libssh2: skip repeat checkp() for already-absent hashed key types
- libssh: work with empty priv_key
- mbedtls: fix ticket handling
- mbedtls: pass correct length for PEM/DER key blobs
- mbedtls: resend length check
- mdlinkcheck: pass `--retry-max-time` to avoid server-controlled long retry times
- mime: bound Curl_mime_duppart() recursion depth
- mime: bound Curl_mime_prepare_headers() recursion depth
- mime: do curl_mime_free() non-recursively
- mprintf: acknowledge %F
- mprintf: avoid scanning strings twice for unbounded %s
- mprintf: make mprintf() and mfprintf() return -1 on error
- mprintf: stage output and emit it in runs
- mprintf: use size_t width for the bare Windows %I modifier
- mqtt: drain queued output before advancing the state machine
- mqtt: remaininglength check for 32-bit systems
- mqttd: work around bogus VS2019 32-bit compiler warning
- mulit_ev: remove socket references on forget
- multi-event: fix timeout of pending transfers
- multi: adjust the cleanup order in multi_done
- multi: is_finished() fix
- multi: reduce struct size with small cleanups
- multi: remove redundant completion message list
- multi: store timeout epoch as whole seconds
- multi_ntfy: fix handling of more than 128 notifications in a batch
- multi_ntfy: recheck callback on dispatch
- multi_ntfy: replace enabled bitset with inline flags
- multihandle: some easy shrinks
- netrc: empty quoted values now produce a valid empty string
- netrc: survive comment-only .netrc file
- ngtcp2: shrink max sendbuf
- ngtcp2: use stream in userdata
- openldap: hand it a dup'd socket, not curl's own
- openssl/gtls: reject CRLfile with native CA store, matching rustls
- openssl: fix OpenSSL v4.1 no-deprecated build
- openssl: hardening
- openssl: support X509 store caching when CApath is configured
- openssl: use non-deprecated API for MD5/MD4
- os400: document curl_formadd_CCSID multi-chunk peculiarity
- os400: restore HAVE_FCHMOD
- os400: use correct free function
- ossl_verifyhost: remove assumption of null-termination of ASN1_STRING.
- output-dir.md: expand on its behavior
- parsedate: find day names, months and time zones faster
- parsedate: remove the unused leading three letters
- parsedate: validate NULL date pointer in curl_getdate
- peer: compare zoneid case sensitive
- peer: parsing a zoneid as number fix
- peer: preserve ipv6 props from "connect-to"
- perf-tests: output two-digital decimals always
- pingpong: add a max loop counter for Curl_pp_readresp
- pingpong: guard sendleft against a send reporting more than requested
- pingpong: schedule server response timeouts for the socket API
- pytest: adjust threshold in test_20_11_crazy_pings for arm64
- pytest: check server status without ssl verify
- pytest: fixture fixes
- pytest: set `PerSourcePenalties no` when sshd supports it
- pytest: silence pytest warnings
- pytest: start all servers early
- retry.md: clarify that the server can override retry delay time
- Revert "setopt: clear the 'custom' CA booleans when set to NULL"
- rtsp: accept a Content-Length body on methods that expected none
- rtsp: do not send a learned session id to another origin
- runtests: add extra room for minimum number of tests in sliced jobs
- runtests: Added runnernums in order to have O(1) lookup
- runtests: unset `CURL_MEMDEBUG` for curl requests made to the CI API
- rustls: break recv loop on empty plain text
- rustls: consume CURLOPT_SSLCERT_BLOB / CURLOPT_SSLKEY_BLOB
- schannel: auto_client_cert conn matching
- schannel: clear borrowed sslContext on close
- schannel: fix `-Wextra-semi-stmt` with clang and extra debug enabled
- schannel: fix compiler warning `-Wstrict-aliasing` in ALPN code
- schannel: fix guard for old MSVC workaround
- schannel: handle empty tokens during renegotiation
- schannel: retain close_notify records across send retries
- sectrust: add guards for rest of Apple OS flavors
- share link: forget connection
- socketpair: fix accept loop
- socketpair: use `pipe2()` on Apple OSes (requires SDK 27)
- socks: support CURLAUTH_ONLY in CURLOPT_SOCKS5_AUTH
- socks: track SOCKS5 authentication per socket, not per connection
- socksd: count connections per test, widen the method2 sentinel
- ssl: dedup ssl_fsslctx
- ssls: validate input arguments in import, export, and unpack
- strparse: speed up number parsing
- sws: fix connection-monitor for connections closed before a request
- telnet: make it work through proxy tunnels
- test 1605: move from unit to libtest
- test/servers.pm: restrict h2/3 port reuse
- test1119, 1167: disable MSYS2 argument conversion
- test1399: improve reliability
- test1679: unset `SSL_CERT_FILE`, use `TESTNUMBER`
- test2007: bump to use SHA256 public key hash (was: MD5)
- test2007: set `MSYS2_ARG_CONV_EXCL` to avoid flaky failures
- test2072: enable on Cygwin/MSYS2
- test428: skip when running on older MSYS2 versions
- test: restore the old test 1609 as 3271
- testcurl.pl: drop support for building c-ares from embedded source tree
- tests/http: use @classmethod when appropriate
- tests: add SFTP connection reuse tests
- tests: clean up Python test code
- tests: fix typos in a comment
- tests: require valgrind 3+ (2007-08-03)
- tftp: verify direction in a few places
- tool: (re)set SSL verification in --libcurl output
- tool: add Unicode and long-filename support to `--create-dir` (Windows)
- tool: buffer headers before remote filename selection
- tool: handling of "synthetic" errors
- tool_doswin: recognize superscript numbers as reserved
- tool_easysrc: reset the handle between --next operations
- tool_getparam: do not print the value of a redacted argument
- tool_getparam: restore --socks5-gssapi-service
- tool_help: guard category[2] access when category is bare "-"
- tool_ipfs: keep the path percent-encoded when rewriting to the gateway
- tool_operate: clear the retry flag when the output file fails
- tool_util: add Unicode support to `tool_execpath()`
- u8_strset, u32_ptrset: fix boundaries handling
- uint-bset: skip unused slots when counting
- uint-table: add remove-max precaution
- unit1399: check microsecond precision across redirects
- unit1664: add workaround for VS2019 16.3 - VS2022 17.4 x64 miscompile
- url: check syntax before applying default-protocol
- url: CURLOPT_INTERFACE fix connection reuse match
- url: match connections without force reuse and candidates
- url: ntlm/negotiate, prohibit connection reuse on follows
- urlapi: make curl_url_dup() copy the guessed_scheme flag
- urlapi: normalize legacy numeric IPv4 hosts set via CURLUPART_HOST
- urlapi: return NULL from curl_url_dup() when given a NULL handle
- urlapi: run the urlparser perf test faster
- urldata: remove conn->given
- urldata: remove ssl_primary_config from easy handle
- urldata: shrink connectdata negotiate states
- vdns: announce resolver start before the HTTPS RR query is sent
- vquic: fix preprocessor check for old Darwin versions
- vquic: use `CURLX_FILE_MODE()` in `Curl_qlogdir()`
- vssh: do not busy-loop in blocking state machine without a timeout
- vtls: fix Curl_cert_hostcheck when the pattern is not a C string
- vtls_scache: remember lock state locally
- warnless: dedupe Intel compiler warning suppression pragmas
- wcurl: import v2026.10.12
- websocket: auto PONG with client reader fix
- websocket: error on EOS with incomplete frame
- wolfssl: remove BIO destroy callback
- ws: check pointer args in curl_ws_recv
- ws: do not auto-pong in raw mode
- x509: stricter parsing