Every AD compromise I work follows a predictable pattern in the first 48 hours. The attacker has domain admin. They have been in the environment for days, sometimes weeks. The client wants them out immediately. And the decisions made in those first two days determine whether the eviction sticks or whether the attacker comes back through a persistence mechanism nobody thought to check.

This is the playbook I follow. Not the sanitized vendor version. The actual sequence of decisions, in order, with the reasoning behind each one.

Before You Touch Anything: Preserve Evidence

The instinct is to start resetting passwords immediately. Resist it. Every action you take in the first hour either preserves or destroys forensic evidence. Before changing a single credential:

Do not power off compromised machines. You will lose volatile memory, running processes, and network connections. Isolate them from the network instead. Disable the NIC or quarantine the VLAN.

Step 1: Identify What Was Compromised

Before you can evict, you need to know the scope. The attacker may have compromised more than what triggered the incident. Start with:

# Find recent privileged logons across all DCs Get-WinEvent -FilterHashtable @{LogName='Security';ID=4672} -MaxEvents 1000 | Select TimeCreated, @{N='User';E={$_.Properties[1].Value}}, @{N='LogonID';E={$_.Properties[3].Value}} | Where-Object { $_.User -notmatch 'SYSTEM|LOCAL SERVICE|NETWORK SERVICE' } | Sort TimeCreated -Descending # Cross-reference with Kerberos TGT requests Get-WinEvent -FilterHashtable @{LogName='Security';ID=4768} -MaxEvents 5000 | Where-Object { $_.Properties[0].Value -match 'admin|svc|service' } | Select TimeCreated, @{N='User';E={$_.Properties[0].Value}}, @{N='IP';E={$_.Properties[9].Value}}

Map every account the attacker touched. Every machine they logged into. Every service account they may have Kerberoasted. This becomes your remediation scope.

Step 2: Check for Persistence Before Resetting Credentials

This is the step most guides skip and the reason most evictions fail. If the attacker planted persistence mechanisms and you reset passwords without removing them first, they just come back.

Check for these in order of severity:

# Check for unauthorized DCSync rights $domain = (Get-ADDomain).DistinguishedName $acl = Get-Acl "AD:\$domain" $acl.Access | Where-Object { $_.ObjectType -match '1131f6aa-9c07-11d1-f79f-00c04fc2dcd2|1131f6ad-9c07-11d1-f79f-00c04fc2dcd2' -and $_.IdentityReference -notmatch 'Domain Controllers|Enterprise Domain Controllers|Administrators' } | Select IdentityReference, ActiveDirectoryRights # Check AdminSDHolder for unexpected ACEs dsacls "CN=AdminSDHolder,CN=System,$domain" | findstr /C:"ALLOW"

Step 3: Reset Credentials in the Right Order

Order and timing matter. Credential resets only stick once the persistence from Step 2 is gone and the attacker's access is cut - otherwise they simply harvest the new passwords. Plan the resets as one coordinated window, starting with KRBTGT.

  1. Reset KRBTGT twice with a 10-12 hour gap between resets. AD accepts both the current and the previous KRBTGT key, so after the first reset the stolen key is still valid as the "previous" one. The second reset pushes it out. Only then are golden tickets made with it dead.
  2. Reset all compromised account passwords. Every account the attacker touched, plus every account they could have harvested via DCSync or Kerberoasting.
  3. Reset all service account passwords. Especially Kerberoastable accounts (those with SPNs).
  4. Reset computer account passwords for compromised machines.
  5. Rotate the Entra Connect credentials if hybrid: the on-prem MSOL_ connector account and the cloud sync account. If you use Seamless SSO, roll the AZUREADSSOACC Kerberos key too. These are frequently forgotten and give the attacker a bridge back to the cloud - or straight back to DCSync.

KRBTGT reset timing: The 10-12 hour gap is critical. If you reset both immediately, every Kerberos ticket in the environment becomes invalid simultaneously. That means every user session, every service authentication, and a lot of services need restarting at once. Leaving at least the maximum ticket lifetime (10 hours by default) plus replication time between resets lets legitimate tickets expire and renew naturally. In an active eviction where the attacker is known to hold the key, some teams accept that disruption and reset twice quickly - make that a deliberate decision, not an accident.

Step 4: Clean and Verify

What Gets Missed

The Entra Connect sync account. I see this missed in about half the evictions I review. Its on-prem MSOL_ account can DCSync if you use password hash sync, and its cloud account can change any synced user in Entra ID - including synced admins. Anyone who controlled the Connect server can walk back in through either side. Rebuild or verify the server, rotate both accounts, check Entra ID audit logs for changes made by the sync account, and make sure no privileged cloud roles are held by synced accounts.

Trust relationships. If the compromised domain has trust relationships with other domains, the attacker may have already pivoted. Check SID History for cross-domain privilege escalation.

Backup systems. If the attacker compromised backup infrastructure, they may have copies of the AD database (ntds.dit) that contain all password hashes. Rotate every credential, not just the ones you know were accessed.

The measure of a successful eviction is not that the attacker is gone today. It is that they cannot return tomorrow. Every persistence mechanism must be found and removed. Every credential must be rotated. Every attack path must be closed. If you skip any of these, you are not evicting. You are hoping.