Related incident · CA key compromise · 17–21 October 2026
eMudhra compromised intermediate CA keys: what PHP servers need to check
Browsers were protected within hours. PHP is a different story: its curl and OpenSSL extensions trust whatever CA bundle the server gives them and generally do not consume browser revocation lists, so stale bundles matter.
Last updated
What happened
- On 17 October 2026 a researcher reported that eight eMudhra intermediate CA certificates (six TLS, two code signing) had P-384 private keys that were integers below 256: 4, 56, 66, 115, 155, 156, 230 and 237. Mozilla confirmed that each key was zero in every byte except the last (Bugzilla 2083449).
- eMudhra says the keys came from an April 30, 2025 key ceremony on FIPS 140-2 Level 3 HSMs, where a wrap/unwrap step produced a second, weak set of keys that were then published by mistake.
- The TLS intermediates chain to emSign ECC Root CA - G3. Sectigo’s AAA Certificate Services root had cross-signed the same keys; Sectigo revoked those cross-signs on 19 October.
| Date | Event |
|---|---|
| 17 Oct 2026, 18:05 | Report reaches the Chrome Root Program |
| 17 Oct, 19:45 | Chrome blocks the six TLS intermediates by SPKI via CRLSet |
| 17 Oct, 22:59 | Firefox blocks all eight via OneCRL |
| 18 Oct | eMudhra revokes the eight certificates |
| 19 Oct | Apple blocks them; Sectigo revokes its cross-signs |
| 20 Oct | Microsoft blocks them; NSS 3.131.1 removes emSign ECC Root CA - G3; curl’s cacert.pem 2026-10-20; composer/ca-bundle 1.4.16 and 1.6.0 |
| 27 Oct (planned) | Chrome Root Store removes emSign ECC Root CA - G3 for all devices |
Is my PHP server affected?
PHP does not ship a CA list of its own. The openssl and curl extensions read openssl.cafile / curl.cainfo when set, and otherwise the default paths compiled into OpenSSL, normally the distribution’s ca-certificates bundle. Neither consumes Chrome’s CRLSet or Firefox’s OneCRL. Your server still trusts the compromised chain if that bundle still contains emSign ECC Root CA - G3 (or, for the cross-signs, AAA Certificate Services) and nothing else blocks the intermediates.
# Which CA file does PHP use? Run as the same user/SAPI as the site if you can.
php -r 'print_r(openssl_get_cert_locations());'
php -i | grep -E 'openssl.cafile|openssl.capath|curl.cainfo'# Does PHP still trust the compromised eMudhra intermediates?
# Good result: bool(false) plus a "certificate verify failed" warning.
# Bad result: the page body is printed (the chain was trusted).
php -r 'var_dump(file_get_contents("https://dv-g3b-emudhra.we-have-a-problem.com/"));'
php -r 'var_dump(file_get_contents("https://dv-g3b-aaa-emudhra.we-have-a-problem.com/"));'
# Same check through the curl extension
php -r '$c = curl_init("https://dv-g3b-emudhra.we-have-a-problem.com/");
curl_setopt($c, CURLOPT_RETURNTRANSFER, true);
var_dump(curl_exec($c), curl_error($c));'# Is the eMudhra root still in the bundle?
ls /etc/ssl/certs | grep -i emsign # Debian/Ubuntu symlinks
grep -n "emSign ECC Root CA - G3" /path/to/cacert.pem # curl/Mozilla-format bundle
# composer/ca-bundle version inside a project
composer show composer/ca-bundle | grep versionsRun the checks for each SAPI that matters. PHP-FPM and Apache mod_php can load a different php.ini from the CLI, so compare php --ini with a phpinfo() page served by the site.
How to fix it
# Debian / Ubuntu (and Debian-based php:* Docker images)
sudo apt-get update && sudo apt-get install --only-upgrade ca-certificates
dpkg -l ca-certificates
# RHEL / Fedora / AlmaLinux / Rocky
sudo dnf upgrade ca-certificates
# Alpine (php:*-alpine images)
apk upgrade --no-cache ca-certificates
# Composer projects that ship composer/ca-bundle
composer update composer/ca-bundle # 1.4.16+ or 1.6.0+
# Restart long-running PHP processes afterwards
sudo systemctl restart php8.3-fpm # or apache2 / httpd / your queue workers; php.ini — for stacks with their own stale bundle (XAMPP, WAMP, old panels)
; Download a current Mozilla-derived bundle from https://curl.se/ca/cacert.pem
; (the 2026-10-20 release or later), then point both settings at it:
curl.cainfo = "/path/to/cacert.pem"
openssl.cafile = "/path/to/cacert.pem"
; Restart Apache / PHP-FPM so the new values load.Older all-in-one stacks and long-unpatched panels often pin curl.cainfo to a file that ships with the product and is never refreshed. Check the vendor’s release notes for an updated bundle, or point php.ini at a current cacert.pem as shown.
Who has shipped a fix
| Software | Fixed version |
|---|---|
| Mozilla NSS | 3.131.1 (Bug 2084101) |
| curl CA bundle (cacert.pem) | 2026-10-20 |
| composer/ca-bundle | 1.4.16, 1.6.0 (2026-10-20) |
| Debian ca-certificates | 20250419~deb12u2, 20250419+deb13u1, 20260816+nmu1 |
| Ubuntu ca-certificates | 20260816ubuntu0.22.04.1, 0.24.04.1, 0.26.04.1, 0.26.10.1 |
| Fedora ca-certificates | 2026.2.92_v9.0.319 |
| Alpine ca-certificates | 20261020-r0 |
| Arch ca-certificates-mozilla | 3.131.1-1 |
| FreeBSD ca_root_nss | 1.131.1 |
NSS 3.131.1 removes emSign ECC Root CA - G3. We fetched curl’s live cacert.pem (Last-Modified 20 October 2026) and it contains neither emSign ECC Root CA - G3 nor AAA Certificate Services. composer/ca-bundle 1.4.16 and 1.6.0 also add CaBundle::findDistrustedCertificate to flag the compromised intermediates in a chain.
Releases not in this list, including older distributions such as Ubuntu 20.04 or Debian 11, were not shown as patched on the sources we reviewed. Check your vendor’s tracker rather than assuming.
FAQ
Bundled stacks and hosting panels
XAMPP and hosting panels ship their own PHP builds, so their CA bundle may not follow the operating system’s ca-certificates updates. Check the product pages for XAMPP, cPanel, Plesk, DirectAdmin, CloudLinux, aaPanel and 宝塔面板, or the full product list.
Was my website’s certificate affected?
Very unlikely. eMudhra says none of the eight intermediates issued an end-entity certificate, and Chrome says no TLS certificate chaining to them was logged to Certificate Transparency before the block. Sites with certificates under eMudhra’s emSign ECC Root CA - G3 do need new certificates, because that root is being removed from trust stores.
Did tens of millions of certificates become insecure?
No. The large figures circulating refer to eMudhra’s total historical issuance, not to certificates signed by the compromised keys. eMudhra puts the root-distrust impact at one customer ecosystem in the United States.
Why does a PHP server care if browsers are already safe?
Browsers enforce Certificate Transparency and receive CRLSet or OneCRL pushes. PHP’s curl and OpenSSL calls usually do neither, so they are protected only once the CA bundle they read no longer trusts the eMudhra chain. That covers outbound calls such as payment APIs, webhooks, SMTP over TLS and Composer downloads.
Which bundle does PHP actually use?
It uses curl.cainfo and openssl.cafile when they are set in php.ini; otherwise it uses the default locations OpenSSL was built with, usually the distribution’s ca-certificates file. Composer and many libraries use composer/ca-bundle, which prefers the system bundle and falls back to its own cacert.pem.
Should I delete the roots by hand?
Only as a last resort. The reporter’s test site documents manual removal for expert users, and it breaks every legitimate certificate that chains to those roots. Updating the vendor package is the normal fix.
Is there anything to exploit on this site?
No. This page contains no key-recovery or exploit code. The test hosts above are run by the reporter so clients can check whether they still trust the chain.
Sources
Outbound links leave this site. We do not host exploit code.
- Protecting Firefox users following the compromise of eMudhra intermediate certificates (20 October 2026) — Mozilla Security Blog
- Protecting Chrome and Android users from compromised eMudhra intermediate CA certificates — Google (Chrome and Android Security)
- eMudhra statement on recent certificate security incident (updated 21 October 2026) — eMudhra
- eMudhra Intermediate CA Compromise: client check and patched-software list — we-have-a-problem.com (reporter’s test site)
- Bug 2083449 — eMudhra: Private key compromise of Intermediate Certificates — Mozilla Bugzilla
- Bug 2084101 — Remove eMudhra emSign Root CA - G3 from NSS — Mozilla Bugzilla
- Compromised eMudhra Intermediate Certificates (guidance for trust store operators) — Mozilla dev-security-policy
- Indian certification authority eMudhra’s private keys compromised – one of them was the number 4 (20 October 2026) — The Register
- eMudhra’s weak P-384 CA keys: testing curl, Node.js and uv (21 October 2026) — lilting channel
- CA certificates extracted from Mozilla (cacert.pem) — curl project
- composer/ca-bundle 1.6.0 and 1.4.16: distrust compromised eMudhra intermediates — Composer (GitHub)
- OpenSSL runtime configuration (openssl.cafile, openssl.capath) — PHP manual
- cURL runtime configuration (curl.cainfo) — PHP manual