Skip to content

deps: certifi 2026.10.19, dropping the compromised eMudhra roots - #3

Merged
sethforprivacy merged 1 commit into
mainfrom
cake/certifi-2026.10.19
Oct 20, 2026
Merged

sethforprivacy merged 1 commit into
mainfrom
cake/certifi-2026.10.19

Conversation

@sethforprivacy

Copy link
Copy Markdown

Bumps certifi from 2026.1.4 to 2026.10.19 in poetry.lock. Lock-only, made with the Poetry that wrote the lock (poetry update --lock certifi, Poetry 2.2.1). Nothing else moves, and the hashes match PyPI.

Why

On 2026-10-20 the private keys of eight eMudhra intermediate CAs were disclosed as compromised (https://emudhra.we-have-a-problem.com/). They chain to "emSign ECC Root CA - G3", which certifi 2026.1.4 still trusts. They also chain through the Sectigo cross-sign to "AAA Certificate Services", which 2026.1.4 trusts too.

The forwarder takes every sweep's destination address from Kraken's /0/private/DepositAddresses response (get_new_kraken_address → util.kraken_request → requests.post). requests verifies against certifi's bundle, not the host's, so updating the host's ca-certificates does not protect this container. Someone holding one of those keys who can MITM or DNS-spoof the connection could present a certificate for api.kraken.com that verifies, then return their own deposit address. certifi 2026.10.19 removes both roots.

Verification

I built the app image (docker build --platform linux/amd64 .) twice: once from 21954da (the commit deployed now) and once from this branch. In each image I ran the same script, which prints certifi's version, checks whether the bundle still has the root, then calls requests.get on eMudhra's demo site (its certificate comes from the compromised "EM DV TLS CA - G3B") and on Kraken.

== old
certifi 2026.01.04 /app/.venv/lib/python3.12/site-packages/certifi/cacert.pem
emSign ECC Root CA - G3 in bundle: True
OK   https://dv-g3b-emudhra.we-have-a-problem.com/ 200 Your client successfully connected to the site. That's bad! 
OK   https://api.kraken.com/0/public/Time 200 {"error":[],"result":{"unixtime":1792523684,"rfc1123":"Tue, 20 Oct 26 19:14:44 +
== new
certifi 2026.10.19 /app/.venv/lib/python3.12/site-packages/certifi/cacert.pem
emSign ECC Root CA - G3 in bundle: False
SSLError https://dv-g3b-emudhra.we-have-a-problem.com/ HTTPSConnectionPool(host='dv-g3b-emudhra.we-have-a-problem.com', port=443): Max retries exceeded with url: / (Caused by SSLError(SSLCertVerificationError(1, '[S
OK   https://api.kraken.com/0/public/Time 200 {"error":[],"result":{"unixtime":1792523688,"rfc1123":"Tue, 20 Oct 26 19:14:48 +

The demo site now fails with CERTIFICATE_VERIFY_FAILED: unable to get local issuer certificate. In the new bundle, "AAA Certificate Services" is gone too, and the emSign roots left are C1, C3 and G1, none of them in the disclosed chain. Kraken still verifies.

Deploying

This moves the app image's commit, so on the next autoforward.yaml run autoforward and autoconvert are recreated (the wallet images are tagged by their own build contexts and stay as they are). A recreated autoforward starts a pass right away. The ansible PR that moves autoforward_version carries this warning too.

The forwarder takes every sweep's destination from Kraken's
DepositAddresses response, fetched with requests, which verifies against
certifi's bundle rather than the host's. certifi 2026.1.4 still trusts
"emSign ECC Root CA - G3" (and "AAA Certificate Services", which
cross-signs it), under which the private keys of eight eMudhra
intermediates were disclosed as compromised on 2026-10-20. A holder of
one of those keys who can intercept the connection could present a
certificate for api.kraken.com that verifies, and hand back their own
deposit address. certifi 2026.10.19 removes both roots.

Lock-only change, made with the Poetry that wrote the lock
(poetry update --lock certifi); nothing else moves.

See https://emudhra.we-have-a-problem.com/
@sethforprivacy
sethforprivacy merged commit 926a226 into main Oct 20, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant