Serious Security: Learning from curl’s latest bug update

You may not have heard of Curl (or curl, as it is more properly written), but it’s one of those open source toolkits that you’ve almost certainly used anyway, probably very often, without knowing.

The open source world provides numerous tools of this sort – ubiquitous, widely used in software projects all over the globe, but often invisible or hidden under the covers, and therefore not perhaps as well-appreciated as they ought to be.

SQLite, OpenSSL, zlib, FFmpeg, Minix…

…the list of supply-chain components that are built into hardware and software that you use all the time, often under completely different names, is long.

Curl is one of those tools, and as its own website explains, it’s a “command line tool and library for transferring data with URLs (since 1998).”

It’s part of almost every Linux distribution on the planet, including many if not most embedded IoT devices, which use it to script things like updates and data uploads; it’s shipped with Apple’s macOS; and it’s handily included with Windows 10 and Windows 11.

You can also build and use curl as a shared library (look for files named libcurl.*.so or CURL*.DLL), so that you can call curl’s code without running a separate process and collecting the output from that, but that still counts as “using curl”.

Latest update

The project just pushed out its latest update, fixing six medium-level CVE-numbered bugs, and bringing curl to version 7.83.1.

You can check what version you’ve got with the command curl --version, like this:

$ curl --version
curl 7.83.1 (x86_64-pc-linux-gnu) libcurl/7.83.1 OpenSSL/1.1.1o zlib/1.2.12 brotli/1.0.9 zstd/1.5.2 c-ares/1.18.1 libidn2/2.3.2 libpsl/0.21.1 (+libidn2/2.3.0) libssh2/1.10.0 nghttp2/1.47.0 OpenLDAP/2.6.2
Release-Date: 2022-05-11
Protocols: dict file ftp ftps gopher gophers http https imap imaps ldap ldaps mqtt pop3 pop3s rtsp scp sftp smb smbs smtp smtps telnet tftp Features: alt-svc AsynchDNS brotli GSS-API HSTS HTTP2 HTTPS-proxy IDN IPv6 Kerberos Largefile libz NTLM NTLM_WB PSL SPNEGO SSL TLS-SRP UnixSockets zstd $ # Details in your build may vary depending on what was compiled in

The bugs were:

  • CVE-2022-30115. HSTS bypass via trailing dot. HSTS is short for HTTP Strict Transport Security. It’s a cookie-like system by means of which a website that you visit using HTTPS can tell you and the software you use, “Always do this in future! Never use plain old HTTP again, even if the user has an old http:// link buried in a web page or a script somewhere and keeps on using it.” The idea is that by redirecting your HTTP server to the equivalent HTTPS pages, visitors who use HTTP by mistake will only do so once. After the first redirect, their browser will remember the HSTS flag set by the page they were redirected to, and start off with HTTPS in future. Unfortunately, given that server names can be written with or without a dot at the end (strictly speaking, the domain example DOT com is actually example DOT com DOT), curl could be tricked into treating the two variants as if they were different websites, potentially giving attackers a way of luring curl into unexpectedly using an insecure connection that could therefore be redirected, spied upon or modified in transit. The updated code now recognises these “name pairs” as referring to the same server.
  • CVE-2022-27782. TLS and SSH connection too eager reuse. Curl tries to keep existing web connections open for re-use, given that it’s very common to make repeated requests to the same site, and even to the same directory, when downloading bunches of new files such as updates, image galleries, and so on. Generally speaking, there aren’t any security problems in doing this, as long as re-used connections involve connecting in the exactly the same way to the same site. But curl didn’t always check that all the connection settings were the same, so that some security details could have been swapped out in the interim. Those details could include information such as username and password, thus theoretically allowing a sneaky user to piggy-back on a previous connection, even though the authentication credentials they supplied in their own request wouldn’t pass muster if the connection were established from scratch. (This is another slip twixt authentication cup and activation lip bug, like the RubyGems security bypass we wrote about earlier this week.) The updated code now forces a fresh connection unless all the connection settings exactly match those of its previous use.
  • CVE-2022-27781. CERTINFO never-ending busy-loop. This bug could be triggered if you asked curl to extract full details of the so-called chain-of-trust of web certificates in a TLS-protected connection. Curl could get stuck in an infinite loop while chasing its way through the list. Given that you can instruct curl to validate the chain-of-trust without fetching all the certificates for yourself (in fact, you can argue that it’s safer to let curl do the verification for you, in the same way that it’s safer to used a trusted cryptographic library than to knit your own), this bug is unlikely to affect much real-life code. Security logging tools are often interested in examining and recording chain-of-certificate details, but we’re hoping that tools of this sort, developed as they are to look for and record potential anomalies, would include their own infinite-loop protection to detect and kill off security spelunking attempts that never finish.
  • CVE-2022-27780. Percent-encoded path separator in URL host. This is a fascinating bug that reminds you just how hard it is to deal with all the variations and vagaries of how data gets presented in web requests. For example, URLs use the SLASH character in a special way, as a separator, so if you want to encode a slash character into a search term, for instance, you need to encode it in a special way too, using a percent sign followed by its hexadecimal code: %2F. Unfortunately, you could sneak a %2F into the server name part of a curl URL, for example by writing dodgy.invalid%2Fmy.nice.example, which looks to a URL filter as though it’s a server hosted under a domain called nice.example). But when curl actually went to make the connection, the string would be converted into dodgy.invalid/my.nice.example, where the decoded SLASH character would suddenly act as a separator between the server name and the rest of the URL, so the connection would be made to the top-level domain invalid instead.
  • CVE-2022-27779. Cookie for trailing dot TLD. This was a similar sort of string mismatch error to the first item. Browsers and downloaders are supposed to ignore cookies set for so-called public prefixes, such as .com or .co.uk, so that unscrupulous operators can’t trick you into setting cookies at a domain level under which each subdomain is likely to be under the control of a different owner. As you can imagine, this would mess up the “same origin” policy, and could leak cookie data between teo sites that were owned and operated by completely different people. A dot at the end of a domain name could confuse curl’s check, and allow cookies to be set for dangerously high-level domains.
  • CVE-2022-27778. Curl removes wrong file on error. This is a reminder of how different product options may end up competing with one another in ways the programmer never expected. Curl has an option --no-clobber, which prevents a download from overwriting an existing file by mistake. The second and subsequent downloads of the same file have a number appended to create a new and unique name that won’t clobber any existing files. But curl also has --remove-on-error, which says to delete the file you just downloaded if anything goes wrong, to avoid leaving partial or damaged files behind. If you used both options, then a failed download of a file that already existed would leave behind incomplete data in the new-and-unique file (the one with a number at the end), and wrongly delete the original file that --no-clobber was supposed to protect.

What to do?

  • Update to curl 7.83.1 if you can on your own systems. If curl comes as part of your operating system distro, as it typically does on Windows, Macs and Linux, you can probably expect an patch in the next scheduled update. (The fact that none of these bugs are critical, and that none of them have been seen “in the wild”, means that emergency or out-of-band updates are unlikely for closed-source products.)
  • If you have an appliance or other network device, check with your vendor to see if they use curl (it’s a good bet they do) and, if so, when you can expect an update.
  • If you look after software projects of your own, take a look at the curl security advisories page. It’s an excellent example of how to document security updates clearly, cleanly and correctly, with plain-English explanations and a helpful list showing the version number when each bug first entered the codebase, and when it was fixed.

The curl project makes it easy to find out how to report bugs; tells what you can expect when you report them; and even includes a Security item in its drop-down Documentation menu, thus making it clear that security reports are first class citizens in its software development ecosystem.

One little thing you can do that the curl team hasn’t done yet. Add a security.txt file, in a standard format, at a standard well-known place on your website. That way, there’s a canonical place, in a canonical format, where security researchers can find your offical bug-reporting channels. You can use ours as an example by looking at sophos.com/security.txt and at sophos.com/.well-known/security.txt.

go top