Certificate Trust and Revocation
A certificate principal authenticates to the key server (kS) with an X.509 certificate and the private key that goes with it. This page describes the checks the kS applies at every certificate login, in the order it applies them, and how it learns that a certificate has been revoked. The same checks apply wherever the kS resolves a certificate to a principal: the certificate login (AM08), the TLS client-certificate lookup on a mutually authenticated connection, and the target of a delegated login.
Every check is made at use, against the kS's clock and its database at that moment — not once at enrolment and remembered.
The login is bound to its TLS connection
The certificate login module, X509Authentication (AM08), sends a random challenge.
The client proves possession of its key by signing a message that binds that challenge to
the TLS connection it arrived on (ADR-0104, ADR-0107):
M = "TE-AM08-CHANNEL-BOUND-v1" || 0x00 || SHA-256("tls-exporter:" || exporter) || challenge
exporter is the connection's RFC 9266 channel binding — 32 bytes of TLS exporter output
under the label EXPORTER-Channel-Binding — and M is 89 bytes. The client signs M
under its key's own scheme:
| Key | Signature |
|---|---|
| RSA | RSASSA-PSS, SHA-256, MGF1-SHA-256, salt length exactly 32 |
| EC | ECDSA over SHA-256, DER-encoded |
Nothing else is accepted and nothing is negotiated. The kS verifies against its own copy of the exporter, which no client and no relay can learn, so a signature made for one connection cannot be replayed on another, and a relay that terminates TLS and re-originates it cannot forward the login. The exporter exists only on TLS 1.3, which every kS listener requires; a connection with no exporter is refused by name.
The SDK clients build M for you: see
TEX509AuthenticationContext (C++) and
X509Context (Java).
The checks, in order
1. Validity
The certificate is refused if the kS's clock is before its notBefore or after its
notAfter (ADR-0108). Both bounds are inclusive and there is no clock-skew allowance. The
refusal names the bound: certificate not yet valid: notBefore … or
certificate expired: notAfter …. An already-expired certificate is also refused at
enrolment; a certificate whose notBefore is in the future is admitted at enrolment as
planned activation and refused at use until that time.
2. Fitness for authentication
Read from the certificate's own extensions (ADR-0109):
- a
keyUsageextension that does not includedigitalSignature— refused; - an
extendedKeyUsageextension that does not includeclientAuth— refused; - extensions that do not parse — refused;
- an absent extension — admitted.
The refusal begins certificate not permitted for authentication:. The same rule is
applied at enrolment, so an unfit certificate cannot be enrolled in the first place.
3. Trust
The policy parameter Policy.X509.TrustMode selects what the kS trusts (ADR-0111):
| Value | Meaning |
|---|---|
pinned-leaf-and-ca (shipped) | The presented certificate must be the exact enrolled leaf, and it must chain to an anchor the kS trusts at that moment — a certificate authority in its trusted list, or the kS's own issuing CA. |
pinned-leaf | The exact enrolled leaf; no chain is required. |
Any other value refuses the kS's start. Anchors are read from the database at every check, so removing a CA from the trusted list takes effect at the next login, and an expired anchor anchors nothing. Fitness is required in both modes.
4. Revocation
The kS asks whether the certificate is still good, and refuses when it cannot tell (ADR-0115). Three outcomes refuse a login:
| Refusal begins | When |
|---|---|
certificate is revoked: | The issuer's CRL lists the certificate. Always refused, whatever the policy. |
certificate revocation status is unavailable: | The kS holds no revocation evidence for the issuer, and the policy says refuse. |
certificate revocation evidence is stale: | The evidence is older than the policy allows, or past its nextUpdate, and the policy says refuse. |
The policy is read from Policy.X509.Revocation.Issuer.<digest> for the issuer, else
Policy.X509.Revocation.Default. The shipped default is
evidence=crl;max-age=24h;refresh=1h;fallback=refuse
— it fails closed. Certificates issued by the kS's own CA are exempt; a certificate issued by an external CA is refused until that CA's CRL has been imported or a per-issuer policy says otherwise. Plan for that step when you enrol users under an external CA.
A session that is already open is re-evaluated at its next operation when its certificate is revoked; revocation does not wait for the session to end.
How a CRL reaches the kS
Imported
A Security Officer imports a CRL with the administrative operation IMPORT_CRL; the
C++ SDK surface is TEAdminCertificate::importCRL. The kS validates a CRL once, when it
arrives (ADR-0114) — issuer authority, signature, scope and freshness, in that order —
and refuses it with a message beginning CRL refused: if any check fails. Delta CRLs,
indirect CRLs and CRLs carrying an issuingDistributionPoint are refused, as is a CRL
that is already stale. A CRL is accepted only if it is newer than the one held for
that issuer, and it then replaces that issuer's evidence in one transaction.
Accepted revocation entries are stored as indexed rows in the key database, so a login's
revocation check is a lookup, not a parse. Two further operations read them back:
GET_REVOCATION_EVIDENCE (the CRL held for an issuer —
TERevocationEvidence) and
LOOKUP_REVOCATION (one certificate's answer: revoked, not listed, or no evidence —
TERevocationLookup).
Fetched
The kS can also fetch a CRL itself (ADR-0116). The URL comes only from the url=
clause of the issuer's revocation policy — the kS never follows a certificate's
cRLDistributionPoints extension — and must be http://. The fetch runs on the policy's
refresh= cadence, and a fetched CRL is judged exactly as an imported one. A failed fetch
changes nothing: the evidence already held stays in force until max-age makes it stale.
A login never triggers a fetch.
Remote engines
A Remote Engine (rE) holds no revocation evidence of its own and offers no certificate login (ADR-0119). Online, it takes every key from the kS at the moment of use, so a revocation the kS has recorded is honored immediately. Offline, it serves the keys it checked out, with the authority it had when it checked them out. The kS checks the engine's own certificate at every handshake it makes upstream.
Related pages
- Key Server Architecture — the protocols and principal types.
- Delegated Authentication — the certificate-holding delegator, and a certificate principal as a delegation target.
- Key DB Structure — where principals and certificates are stored.