revoke: certIsRevokedCRL does not validate cached CRL was issued by the cert's issuer
- Dominant language
- Go
- Stars
- 9.5k
- Forks
- 1.2k
- PR merge metrics
- No merged PRs in 30d
Description
In `certIsRevokedCRL`, the CRL's signature is only validated immediately after being fetched and before storing it into the cache keyed by URL. In particular, there's no check to make sure that when a cached CRL is used, that the CRL is valid for the current issuer.
This can be a security issue if a maliciously generated certificate reuses the CRL distribution URL of a legitimate CA, and can MITM a request to that URL.
In practice, this probably isn't a major issue if the certificate chain is first validated against a trusted root store, but package revoke doesn't explicitly caution that. Package revoke might also be used by applications that validate certificate chains against different root stores (e.g., a "test" root store including a test CA that freely signs all well-formed CSRs), and it's inappropriate for one root store to be able to subvert another's security.
Attack scenario:
- Attacker has compromised a public key that has a legitimate *but revoked* VictimCert issued by VictimCA; the CRL is published via HTTP at VictimURL (most CRLs are published over HTTP).
- Attacker has the ability to MITM HTTP requests made by the cfssl/revoke-using application.
- Attacker can have the application invoke `revoke.VerifyCertificate` to validate an attacker supplied certificate chain (e.g., MaliciousCert signed by MaliciousCA).
Attack steps:
- Attacker generates MaliciousCert to specify VictimURL as the CRL distribution point.
- Attacker sends the {MaliciousCert, MaliciousCA} chain to the victim application to be checked for revocation.
- The application will try to download VictimURL (as specified by MaliciousCert).
- Attacker MITMs this request and provides a CRL response valid forever and without any revoked certificates.
- The application validates the CRL against MaliciousCA, and then caches it in `revoke.CRLSet` for VictimURL.
- Now if the attacker sends {VictimCert, VictimCA}, the `revoke.VerifyCertificate` will report that it has *not* been revoked, because it will use the maliciously generated CRL that was issued by MaliciousCA.
Contributor guide
Assessment
This issue has not been assessed yet.