Skip to content

AD CS (Active Directory Certificate Services)

AD CS is Microsoft’s PKI: it issues certificates usable to authenticate in the domain (a valid certificate can be exchanged for a TGT via PKINIT). The problem is that the authorization for who can request which certificate and as which identity is configured in templates and permissions that, by default or by oversight, are often lax. The “Certified Pre-Owned” research (SpecterOps) cataloged a family of escalations —ESC1 through ESC16+— that turn a normal user into Domain Admin. Today it’s one of the most reliable and often silent roads to DA.

flowchart LR
    A["Domain user"] -->|"CSR with SAN = Administrator (ESC1)"| CA["AD CS"]
    CA -->|"issues the certificate"| A
    A -->|"authenticates with the cert (PKINIT)"| DC[Domain Controller]
    DC -->|"TGT as Administrator"| A

A certificate is a long-lived, hard-to-revoke authentication credential. If an attacker gets the CA to issue a certificate naming them as another user (e.g. Administrator), they can authenticate as that user with PKINIT and obtain their TGT. Worse: certificates survive password changes, so they’re also persistence. The root is almost always a misconfigured template or overly open enrollment/management permissions.

# Certipy (Linux) — the standard
certipy find -u user@domain -p pass -dc-ip <DC> -vulnerable -stdout
# Certify (Windows)
Certify.exe find /vulnerable

Look for CAs, templates, who can enroll (Enrollment Rights), and the conditions that trigger each ESC.

  • ESC1 — template allowing ENROLLEE_SUPPLIES_SUBJECT (requester chooses the SAN), with client-authentication EKU and enrollment rights for low users → request a cert “as Administrator”.
certipy req -u user@domain -p pass -ca CA -template VulnTemplate -upn administrator@domain
certipy auth -pfx administrator.pfx -dc-ip <DC> # PKINIT -> Administrator's TGT
  • ESC2 — template with Any Purpose EKU or no EKU → the cert authenticates as anyone.
  • ESC3 — abuse of the Certificate Request Agent (enrollment agent) to request on behalf of others.
  • ESC4 — you have write over the template → reconfigure it to be vulnerable (ESC1), then exploit it.
  • ESC6 — EDITF_ATTRIBUTESUBJECTALTNAME2 flag on the CA → add an arbitrary SAN to any request.
  • ESC7 — CA management permissions (ManageCA/ManageCertificates) → approve requests or enable ESC6.
  • ESC8 — Web Enrollment (HTTP) without EPA → NTLM relay of an account (including a coerced DC) to certsrv → that account’s certificate → its TGT (see NTLM Relay). Classic chain: PetitPotam(DC) → relay ESC8 → DC cert → DCSync.
  • ESC9/ESC10 — weak certificate-to-account mappings (szOID/altSecurityIdentities, StrongCertificateBindingEnforcement) → impersonation.
  • ESC11 — relay to the CA’s RPC interface (ICPR).
  • ESC13 — template tied to a group with rights (OID group link).
  • Steal the CA private key (certipy ca -backup / THEFT) → forge certificates for anyone (Golden Certificate) → persistence surviving password resets.
  • Keep a privileged account’s PFX: valid until the certificate expires/is revoked.
  • Certipy (Linux) — enumeration, exploitation of all ESCs, PKINIT, forging.
  • Certify + Rubeus (Windows) — find, request, and PKINIT→TGT.
  • ntlmrelayx —adcs — ESC8/relay to Web Enrollment.
  • PKINITtools — request a TGT with a certificate.

From unprivileged user to Domain Admin via a privileged-account certificate, and domain persistence by stealing the CA key. ESC8 + DC coercion is full compromise; ESC1 is often direct escalation in a single step.

  • Certificate requests with another account’s SAN/UPN (especially privileged): AD CS events 4886/4887 (request/issue) with an unusual SAN.
  • PKINIT authentications (4768 with certificate) for accounts that don’t usually use certificates.
  • Relay to certsrv (ESC8): HTTP enrollment requests from a machine account/DC; prior coercion.
  • Template changes (writes) and CA-configuration changes.

Enable AD CS auditing (events 4886/4887/4899/4900), correlate SAN↔requester, and monitor template/CA-flag changes. Use Certipy/PingCastle to audit yourself.

  • Review and fix templates: remove ENROLLEE_SUPPLIES_SUBJECT except where essential; restrict EKUs and enrollment permissions; require CA manager approval.
  • Remove the EDITF_ATTRIBUTESUBJECTALTNAME2 flag (ESC6).
  • EPA + HTTPS on Web Enrollment or disable it (ESC8); enforce signing/channel binding.
  • Enable StrongCertificateBindingEnforcement (mitigates ESC9/ESC10).
  • Restrict who manages the CA (ESC7); protect the CA private key (HSM).

Revoke the malicious certificates (and remember: an issued cert stays valid until revoked/expired → may require rotating more). If the CA key was stolen, rebuild the PKI. Fix the specific template/flag and, if DCSync happened, rotate krbtgt ×2.

  • “Certified Pre-Owned” (Will Schroeder & Lee Christensen, SpecterOps, 2021) — the research that defined the ESCs.
  • ESC8 + PetitPotam (CVE-2021-36942) — public full-domain chain, patched/mitigated by Microsoft.
  • CVE-2022-26923 (Certifried) — escalation to DA by creating a machine account and requesting a cert with a manipulated dNSHostName.
  • Certipy appears in red-team reports and real intrusions as a shortcut to DA when AD CS is misconfigured.
  • certipy find -vulnerable — which ESCs are present?
  • ESC1: template with supplied SAN + client auth + enroll for low-priv
  • ESC2/ESC3: Any Purpose / enrollment agent
  • ESC4: write over template (reconfigure to vulnerable)
  • ESC6: EDITF_ATTRIBUTESUBJECTALTNAME2 enabled
  • ESC7: ManageCA/ManageCertificates permissions
  • ESC8: HTTP Web Enrollment without EPA → relay (coerce DC)
  • CA key theft → Golden Certificate (persistence)