When it comes to command-line data transfers, curl is one of the most trusted tools. Many scripts and systems use it for automation, making its reliability essential. But even solid software can have lapses. One such flaw—CVE-2023-23914—describes a critical vulnerability around curl's HSTS (HTTP Strict Transport Security) support that could leave sensitive information exposed in plain text.

In this post, we’ll break down the vulnerability in plain English, show you a hands-on example, provide code snippets, and guide you to best practices you can adopt right away.

What is CVE-2023-23914?

Summary:  
In curl versions prior to 7.88., there’s a flaw in how the tool handles HSTS settings when dealing with multiple URLs supplied in a single command. When a user tells curl to use HSTS—either via preload, the --hsts option, or a stored file—curl should upgrade HTTP requests to HTTPS if protected by HSTS rules.

The bug? If you provide several URLs on one command line, only the first one would respect HSTS. Any subsequent URLs could fall back to cleartext HTTP, even if they should be upgraded, potentially leaking sensitive or credentials-laden data over the wire.

Vulnerability Classification:

Affected Versions: < 7.88.

- Official Advisory

Let’s imagine you have a script like this

curl --hsts hsts.txt http://site1.example.com/secret http://site2.example.com/report

Suppose both site1.example.com and site2.example.com are set up with HSTS, and your hsts.txt file has noted them as "always use HTTPS." You expect both requests to be upgraded automatically, so your secrets stay safe.

But due to CVE-2023-23914, only the first URL input is forced to HTTPS by HSTS. The second and any further URLs revert to insecure HTTP, even if your HSTS policy says otherwise! If you’re sending cookies, passwords, or any sensitive headers, you’re risking them being sniffed or intercepted by attackers.

How Does Curl’s HSTS Work?

HSTS tells browsers (and tools like curl) to always use HTTPS with certain domains, even if you type "http://". Curl added HSTS support in curl 7.74., and since then, you can preload domains or save/load HSTS states across sessions.

When using the --hsts option, the HSTS state machine should ensure every request to a protected domain uses HTTPS—period.

What Went Wrong?

Curl’s internal code failed to preserve the HSTS state across multiple URLs on one command line. Here's a _pseudo-code_ of the buggy logic:

for (each url in commandline) {
    set_transfer_options();
    if (first_url) {
        load_hsts_state();
    }
    perform_transfer(url);
    // HSTS state not saved or remembered for next URL!
}


The correct logic: the HSTS state should be loaded once per session, and applied for all transfers.

In the flawed versions, only the very first transfer respected the loaded HSTS state. Any following requests could ignore it completely. This could cause subsequent URLs to fetch over HTTP instead of HTTPS, regardless of the site’s policy or your expectations.

Suppose you want to download two sensitive files

curl --hsts hsts.txt http://private.example.com/file1.txt http://private.example.com/file2.txt

If you recorded private.example.com as always-HTTPS in hsts.txt, you would expect both to go over https.

But with the bug present, check your verbose output

curl --hsts hsts.txt http://private.example.com/file1.txt http://private.example.com/file2.txt -v

You might see

*   Trying 172.16.1.1:443...
* Connected using HTTPS (first URL)
...
*   Trying 172.16.1.1:80...
* Connected using HTTP (second URL)


The second URL falls back to HTTP—even though there’s an HSTS rule saying it shouldn’t!

1. Download old curl version (e.g., via Docker)

docker run -it --rm ubuntu:22.04 bash
apt update && apt install curl=7.81.-1ubuntu1 -y

2. Prepare HSTS file

echo "YOUR_HSTS_DOMAIN 1  18446744073709551615" > hsts.txt

3. Run curl with two URLs

curl --hsts hsts.txt http://YOUR_HSTS_DOMAIN/one http://YOUR_HSTS_DOMAIN/two -v

The log will show HTTPS on the first request, and HTTP on the second.

The simplest prevention: update curl to 7.88. or newer. The issue is fully patched.

*Download latest curl binaries here*

Workaround:

If you’re stuck with an old version, don’t combine URLs in one curl command. Instead, use multiple curl invocations—one for each URL.

`bash

curl --hsts hsts.txt http://site1
 curl --hsts hsts.txt http://site2
 `

- Check your scripts:  
 If you use any scripts or tools that automate curl, check if they pass multiple URLs on a single command line. Update or patch accordingly.

---

## References and Further Reading

- curl Official Security Advisory: CVE-2023-23914
- curl HSTS Documentation
- What is HSTS?
- curl: HSTS support details
- Upgrading curl on your OS

---

## Final Thoughts

It’s tempting to assume the tools we rely on “just work” every time. But even the best software lets mistakes slip in sometimes. Check your curl version, especially if you use its HSTS feature for automation, and always keep your tools patched and your scripts reviewed.

This specific vulnerability is an important lesson: when you trust a tool to protect your sensitive data, make sure that protection isn’t just “on the first try.”

Stay safe. Always prefer HTTPS, and always keep curl up to date!

---

*Feel free to share or adapt this content for your organization's security review or post-mortem. If you have further questions about CVE-2023-23914, reach out to the curl security team directly.*

Timeline

Published on: 02/23/2023 20:15:00 UTC
Last modified on: 03/09/2023 19:15:00 UTC