In order to inspect encrypted data streams using SSL/TLS, Kasperky installs a WFP driver to intercept all outgoing HTTPS connections. They effectively proxy SSL connections, inserting their own certificate as a trusted authority in the system store and then replace all leaf certificates on-the-fly. This is why if you examine a certificate when using Kaspersky Antivirus, the issuer appears to be "Kaspersky Anti-Virus Personal Root".
Kaspersky's certificate interception has previously resulted in serious vulnerabilities, but quick review finds many simple problems still exist. for example, the way leaf certificates are cached uses an extremely naive fingerprinting technique.
Kaspersky cache recently generated certificates in memory in case the user agent initiates another connection. In order to do this, Kaspersky fetches the certificate chain and then checks if it's already generated a matching leaf certificate in the cache. If it has, it just grabs the existing certificate and private key and then reuses it for the new connection.
The cache is a binary tree, and as new leaf certificates and keys are generated, they're inserted using the first 32 bits of MD5(serialNumber||issuer) as the key. If a match is found for a key, they just pull the previously generated certificate and key out of the binary tree and start using it to relay data to the user-agent.
You don't have to be a cryptographer to understand a 32bit key is not enough to prevent brute-forcing a collision in seconds. In fact, producing a collision with any other certificate is trivial.
The attack goes like this:
- Mallory wants to intercept mail.google.com traffic, for which the 32bit key is 0xdeadbeef.
- Mallory sends you the real leaf certificate for mail.google.com, which Kasperksy validates and then generates it's own certificate and key for.
- On the next connection, Mallory sends you a colliding valid certificate with key 0xdeadbeef, for any commonName (lets say attacker.com)
- Now mallory redirects DNS for mail.google.com to attacker.com, Kaspersky starts using their cached certificate and the attacker has complete control of mail.google.com.
It seems incredible that Kaspersky haven't noticed that they sometimes get certificate errors for mismatching commonNames just by random chance. When they get those errors, it's only because an active attacker didn't fixup DNS responses that they're not giving remote websites access to other domain owners.
Just for fun, I searched the certificate transparency logs for some collisions.
# Fetch the Hacker News certificate
$ openssl s_client -connect news.ycombinator.com:443 < /dev/null
# Find the issuer/serial hash
$ ./printhash < hackernews.pem
hash: 0xf3cf4bb3
I wrote a MapReduce to search for any matching certificates, and found that CN=autodiscover.manchesterct.gov had the same serialNumber/issuer hash.
$ ./printhash < autodiscover.manchesterct.gov.pem
hash: 0xf3cf4bb3
You can reproduce this bug, by visiting https://autodiscover.manchesterct.gov, then https://news.ycombinator.com and observing that the content is signed by the wrong certificate. A hilarious screenshot is attached.
So if you use Kaspersky Antivirus in Manchester, Connecticut and were wondering why Hacker News didn't work sometimes, it's because of a critical vulnerability that has effectively disabled SSL certificate validation for all 400 million Kaspersky users.
I've also attached some quick c source code you can use to generate a colliding certificate for testing.
I don't want to know what happens if a leaf certificate collides with a CA certificate.
(Note: Kaspersky have not implement QUIC, so just use QUIC if you don't want them to inspect an encrypted channel for some reason. This is the reason certificates are not replaced when viewing google.com in Chrome, but they are in Firefox)
This bug is subject to a 90 day disclosure deadline. If 90 days elapsewithout a broadly available patch, then the bug report will automaticallybecome visible to the public.

This issue was fixed on the 28th, there was some delay unrestricting this bug due to the holidays.
There was some discussion about with Kaspersky on how to exploit this vulnerability as I wasn't aware they were checking the commonName sent with SNI. However, we were able to come up with alternative attacks that still worked and Kaspersky resolved it quickly.