Skip to content
02 · Kerberos & AuthenticationPart 4 of 4Foundation

Defending against Kerberoasting and AS-REP roasting

Shrink Kerberoasting and AS-REP roasting exposure: inventory SPNs, remove stale ones, move to gMSA and AES, deploy a honey SPN and detect RC4 4769 spikes.

Florian Amette7 min read

Kerberoasting needs nothing but a domain account. The attacker lists accounts with a Service Principal Name, requests a service ticket for each one, and cracks the tickets offline with tools such as Hashcat. The DC logs a routine 4769 event and nothing else happens until a service account password falls. AS-REP roasting is the same idea against accounts that do not require Kerberos pre-authentication, and it does not even need a domain account. Both attacks target human-chosen passwords on accounts that often hold far more privilege than their owners realise.

The Kerberos hardening guide introduced both attacks. This one is the operational plan: measure your roastable surface, remove what you do not need, make the rest uncrackable, and detect the attempts you cannot prevent.

Measure: your roastable surface

Computer accounts also have SPNs, but their passwords are random and rotated every 30 days, so they are not practical targets. The risk is user accounts with SPNs. Exclude krbtgt, which carries the kadmin/changepw SPN but cannot be roasted through a normal service ticket request.

PowerShell
Get-ADUser -Filter 'ServicePrincipalName -like "*"' `
    -Properties ServicePrincipalName, PasswordLastSet, LastLogonDate, AdminCount,
                msDS-SupportedEncryptionTypes, MemberOf, Enabled |
    Where-Object { $_.SamAccountName -ne 'krbtgt' } |
    Select-Object SamAccountName, Enabled, PasswordLastSet, LastLogonDate, AdminCount,
        @{n='EncTypes';e={$_.'msDS-SupportedEncryptionTypes'}},
        @{n='SPNs';e={$_.ServicePrincipalName -join '; '}} |
    Sort-Object PasswordLastSet

Rank the output by three questions:

  1. Is it privileged? AdminCount = 1 or membership in any Tier 0 group means a cracked password is a domain compromise. These come first. Treat them as Tier 0 until proven otherwise.
  2. How old is the password? A PasswordLastSet from years ago almost always means a short, human-chosen password, and possibly no AES keys.
  3. Does it allow RC4? An empty or RC4-inclusive msDS-SupportedEncryptionTypes means the KDC may issue RC4 tickets for it.

For AS-REP roasting, the exposure is the DONT_REQ_PREAUTH flag (userAccountControl bit 0x400000):

PowerShell
Get-ADUser -Filter 'DoesNotRequirePreAuth -eq $true' -Properties DoesNotRequirePreAuth, PasswordLastSet |
    Select-Object SamAccountName, Enabled, PasswordLastSet

Do not forget who can create new exposure. Any principal with write access to servicePrincipalName on a user can add an SPN and roast it (so-called targeted Kerberoasting), and anyone who can change userAccountControl can disable pre-authentication. That is an ACL problem; audit it with ACL and object security.

Why the encryption type matters

An RC4 service ticket is encrypted with a key that is simply the account's NT hash, so each password guess costs one MD4 computation. An AES ticket uses a key derived with PBKDF2 (4,096 iterations of HMAC-SHA1) salted with the realm and account name, which makes each guess thousands of times more expensive on the same hardware. That gap turns an eight-character password from "cracked over lunch" into "not worth the electricity", but it does not rescue a password that appears in a wordlist. Treat AES as a multiplier on password strength, not a substitute for it, and remember that many roasting tools will ask for RC4 whenever the account still allows it.

Audit: decide per account

For each SPN-bearing user account, pick one outcome:

SituationAction
Service decommissioned, account unusedRemove SPNs, disable, delete after a grace period
SPN is stale or duplicatedRemove the SPN only
Windows service that supports gMSAMigrate to a gMSA
Cannot use gMSARandom 25+ character vaulted password, AES-only, FGPP
Account is privilegedRemove the privilege first, whatever else you do

Check LastLogonDate and 4769 events to confirm whether an SPN is actually requested before removing it:

PowerShell
# Remove one stale SPN from an account
Set-ADUser -Identity 'svc-oldreport' -ServicePrincipalNames @{ Remove = 'HTTP/oldreport.corp.example.com' }

# Find duplicate SPNs across the domain (duplicates also break Kerberos)
setspn -X

Enforce: make remaining tickets uncrackable

Move to gMSA

A gMSA has a 120-character random password managed by the domain and rotated automatically. Its tickets are still requestable, but cracking them is not realistic. SQL Server, IIS application pools, scheduled tasks and most Windows services support gMSAs. The per-application details are in migrating service accounts to gMSA.

PowerShell
# After migration: the old account should hold no SPNs
Get-ADUser 'svc-sql01' -Properties ServicePrincipalName | Select-Object -ExpandProperty ServicePrincipalName
Get-ADServiceAccount 'gmsa-sql01' -Properties ServicePrincipalName | Select-Object -ExpandProperty ServicePrincipalName

Long passwords and AES-only for the rest

For accounts that must remain user accounts:

  • Generate a random password of at least 25 characters with your PAM or password manager, and rotate it on a schedule the application can tolerate.
  • Enforce the length with a fine-grained password policy applied to a ServiceAccounts group, so that manual resets cannot drop below it.
  • Set msDS-SupportedEncryptionTypes to 24 (AES128 + AES256) and reset the password afterwards if it predates AES support, so that AES keys exist.
PowerShell
New-ADFineGrainedPasswordPolicy -Name 'PSO-ServiceAccounts' -Precedence 10 `
    -MinPasswordLength 25 -ComplexityEnabled $true -PasswordHistoryCount 24 `
    -MaxPasswordAge '365.00:00:00' -LockoutThreshold 0
Add-ADFineGrainedPasswordPolicySubject -Identity 'PSO-ServiceAccounts' -Subjects 'ServiceAccounts'

Set-ADUser 'svc-app01' -Replace @{ 'msDS-SupportedEncryptionTypes' = 24 }

AES alone does not save a weak password; it only makes each guess more expensive. Length and randomness do the real work. Domain-wide RC4 removal is covered in disabling RC4 in Kerberos.

Deal with privileged service accounts first

The worst finding in almost every assessment is a service account with an SPN that is also a Domain Admin, often because an installer asked for it a decade ago. Cracking that one password ends the engagement. Before any other remediation, remove these accounts from privileged groups and grant only the rights the application actually uses, which is usually local administrator on a handful of servers or a delegated permission on one OU.

This takes negotiation with application owners, so gather evidence first: which servers the account logs on to (4624 events on those servers, or LastLogonDate plus the SPN host names), which scheduled tasks and services use it, and which AD permissions it exercises. Where the application cannot run without domain-level rights, the account and every server it runs on are Tier 0 and must be managed that way. Either outcome is better than a roastable Domain Admin.

Fix AS-REP roastable accounts

Clear the flag, then reset the password of every account that had it, because its AS-REP may already have been collected:

PowerShell
Get-ADUser -Filter 'DoesNotRequirePreAuth -eq $true' |
    ForEach-Object { Set-ADAccountControl -Identity $_ -DoesNotRequirePreAuth $false }

If a legacy application genuinely requires it, document the exception, give the account a random 25-plus character password, and monitor it.

Detect what remains

Audit policy

On DCs: Computer Configuration > Policies > Windows Settings > Security Settings > Advanced Audit Policy Configuration > Audit Policies > Account Logon > Audit Kerberos Service Ticket Operations and Audit Kerberos Authentication Service, Success and Failure. Forward 4768 and 4769 to your SIEM or a central collector.

Detection logic

  • RC4 service tickets for user accounts: 4769 with TicketEncryptionType 0x17 where the service is a user account, in an environment where AES is otherwise the norm. Many roasting tools request RC4 explicitly.
  • Volume: one account requesting service tickets for many distinct SPNs in a short window (for example more than 10 within 5 minutes).
  • AS-REP roasting: 4768 with PreAuthType 0.
PowerShell
# Clients that requested RC4 tickets for more than 10 distinct services in the last hour
$since = (Get-Date).AddHours(-1)
Get-WinEvent -FilterHashtable @{ LogName='Security'; Id=4769; StartTime=$since } |
    ForEach-Object {
        $d = @{}; ([xml]$_.ToXml()).Event.EventData.Data | ForEach-Object { $d[$_.Name] = $_.'#text' }
        if ($d.TicketEncryptionType -eq '0x17' -and $d.ServiceName -notlike '*$') {
            [pscustomobject]@{ Client = $d.TargetUserName; Service = $d.ServiceName }
        }
    } | Group-Object Client | Where-Object { ($_.Group.Service | Sort-Object -Unique).Count -gt 10 }

Tuning

Expect some noise on day one. Vulnerability scanners, identity governance tools and some monitoring products enumerate SPNs and request tickets in bulk, and older clients legitimately negotiate RC4 against accounts that still allow it. Build an allowlist of known scanner source addresses and service identities, and review it quarterly. The RC4 signal becomes much sharper once service accounts are AES-only: after that, any RC4 ticket for a user-based service account is either an unfixed legacy client or a roasting tool asking for the weaker encryption type on purpose.

Honey SPN

Create a honeytoken: a user account with a realistic name and SPN, a random long password, no logon activity and no real service behind it. Any 4769 for it is an alert. Design details are in honeytokens and deception.

PowerShell
New-ADUser -Name 'svc-sqlbackup-legacy' -SamAccountName 'svc-sqlbackup-legacy' `
    -Path 'OU=ServiceAccounts,DC=corp,DC=example,DC=com' -Enabled $true `
    -AccountPassword (Read-Host -AsSecureString 'Random 30+ char password') `
    -ServicePrincipalNames 'MSSQLSvc/sqlbackup01.corp.example.com:1433'

Verify

  • The SPN inventory query returns only gMSAs, computer accounts and a short, documented list of user accounts, each with a password younger than your rotation interval and msDS-SupportedEncryptionTypes set to 24.
  • The DoesNotRequirePreAuth query returns nothing, or only documented exceptions.
  • No user account with an SPN is a member of a privileged group.
  • A test ticket request for the honey SPN (klist get MSSQLSvc/sqlbackup01.corp.example.com:1433 from an admin workstation, announced to the SOC) produces an alert.

What it breaks

  • Removing SPNs that are still used breaks Kerberos to that service; clients fall back to NTLM where allowed, or fail. Check 4769 history before removal.
  • Password resets on legacy service accounts break every place the old password is hard-coded: services, scheduled tasks, application config files, scripts on other servers.
  • AES-only on service accounts breaks clients and keytabs that only support RC4, notably old Java and Linux integrations.
  • gMSA migration does not work for applications that need the password in clear text, or for services on hosts outside the domain.
  • Clearing DONT_REQ_PREAUTH can break the rare legacy Unix or appliance integration that relied on it.

Related reading: the Kerberos and authentication area and service account hardening with gMSA and LAPS for the wider service account programme.

Frequently asked questions

Can Kerberoasting be blocked completely?

No. Any authenticated user can request a service ticket for any SPN; that is how Kerberos works. What you control is whether the ticket is worth cracking. A gMSA or computer account has a random 120-character password that will not be cracked, and AES tickets are far slower to attack than RC4. The goal is that every roastable account is either uncrackable or monitored.

Is a 25-character password enough for a service account that cannot be a gMSA?

A randomly generated 25-plus character password stored in a vault puts offline cracking out of practical reach, even for RC4 tickets. The weakness is usually not length but human handling: the same password reused on several accounts, written into scripts, or never rotated since 2012. Use a password manager or PAM tool to generate, store and rotate it, and pair it with AES-only encryption types.

Why does a honey SPN work as a detection?

A honey SPN is a service account that no legitimate client ever uses. Normal traffic never requests a ticket for it, so any 4769 event naming it is suspicious by definition, with essentially no false positives. Attackers enumerating all SPNs and requesting tickets in bulk will usually include it, which gives you a high-confidence alert early in the attack.

Defending against Kerberoasting and AS-REP roasting

Related guides

Passwords & Service Accounts

Migrating service accounts to gMSA and dMSA

Step-by-step migration from static service accounts to gMSA and Windows Server 2025 dMSA: KDS root key, retrieval rights, per-app notes and rollback.

Intermediate