Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

🏠 Back to Blog

ACL Enumeration

Practical methods for enumerating ACL attack paths using PowerView, built-in PowerShell cmdlets, and BloodHound. The key is targeted enumeration — starting from a user you control and following the chain of rights outward.

Enumerating ACLs with PowerView

The Problem with Broad Enumeration

Running Find-InterestingDomainAcl without filters returns a massive amount of data that is impractical to sift through during a time-boxed assessment.

Find-InterestingDomainAcl

This will work, but the output is overwhelming. Instead, start with a user you control and enumerate outward.

Step 1: Get the SID of your controlled user

Import-Module .\PowerView.ps1
$sid = Convert-NameToSid wley

Step 2: Find all objects this user has rights over

Without -ResolveGUIDs, the ObjectAceType field shows raw GUIDs instead of human-readable names:

Get-DomainObjectACL -Identity * | ? {$_.SecurityIdentifier -eq $sid}

This returns results with ObjectAceType values like 00299570-246d-11d0-a768-00aa006e0529 — not useful without translation.

Step 3: Resolve GUIDs to readable names

Get-DomainObjectACL -ResolveGUIDs -Identity * | ? {$_.SecurityIdentifier -eq $sid}

Now the ObjectAceType shows User-Force-Change-Password instead of the raw GUID. This command can take 1-2 minutes in large environments.

Manually resolving a GUID (without PowerView)

$guid = "00299570-246d-11d0-a768-00aa006e0529"
Get-ADObject -SearchBase "CN=Extended-Rights,$((Get-ADRootDSE).ConfigurationNamingContext)" -Filter {ObjectClass -like 'ControlAccessRight'} -Properties * | Select Name,DisplayName,DistinguishedName,rightsGuid | ?{$_.rightsGuid -eq $guid} | fl

Following the Chain

Once you find the first link (e.g., user wley has ForceChangePassword over damundsen), continue the process with the next user:

$sid2 = Convert-NameToSid damundsen
Get-DomainObjectACL -ResolveGUIDs -Identity * | ? {$_.SecurityIdentifier -eq $sid2} -Verbose

Check for nested group memberships that expand the attack surface:

Get-DomainGroup -Identity "Help Desk Level 1" | select memberof

Continue until you reach a high-value target or dead end.

Enumeration Without PowerView (Built-in Cmdlets)

Useful when you can’t import tools onto the system.

Build a user list

Get-ADUser -Filter * | Select-Object -ExpandProperty SamAccountName > ad_users.txt

Iterate over all users checking ACLs

foreach($line in [System.IO.File]::ReadLines("C:\Users\htb-student\Desktop\ad_users.txt")) {
    get-acl "AD:\$(Get-ADUser $line)" | Select-Object Path -ExpandProperty Access | Where-Object {$_.IdentityReference -match 'INLANEFREIGHT\\wley'}
}

This is slow but works without any external tools. The output contains raw GUIDs that must be resolved manually.

Enumerating ACLs with BloodHound

BloodHound makes ACL attack path discovery dramatically faster than manual methods.

Key BloodHound Features for ACL Enumeration

  1. Node Info > Outbound Control Rights — select a user node and check:

    • First Degree Object Control — objects you have direct rights over
    • Transitive Object Control — full chain of objects reachable via ACL abuse (the multi-hop path)
  2. Right-click any edge → select Help for:

    • Explanation of the specific right
    • Tools and commands to exploit it
    • OPSEC considerations
    • External references
  3. Pre-built queries — use “Find Principals with DCSync Rights”, “Shortest Paths to Domain Admins”, etc. to confirm critical attack paths

Example Attack Chain (Discovered via BloodHound)

wley
  → ForceChangePassword → damundsen
    → GenericWrite → Help Desk Level 1 (group)
      → MemberOf → Information Technology (group)
        → GenericAll → adunn
          → DS-Replication-Get-Changes + DS-Replication-Get-Changes-In-Filtered-Set → DCSync

Each hop represents a different ACL abuse primitive. BloodHound shows this entire path in a single graph view — what would take extensive manual enumeration is visible at a glance.

DCSync Rights Indicator

When a user has both of these extended rights on the domain object, they can perform a DCSync attack:

  • DS-Replication-Get-Changes
  • DS-Replication-Get-Changes-In-Filtered-Set

Use the BloodHound pre-built query “Find Principals with DCSync Rights” to identify these quickly.

Enumeration Methodology Summary

StepActionTool
1Get SID of controlled userConvert-NameToSid (PowerView)
2Find all objects user has rights overGet-DomainObjectACL -ResolveGUIDs (PowerView)
3Identify the right (ForceChangePassword, GenericWrite, etc.)-ResolveGUIDs flag or manual GUID lookup
4Follow the chain — enumerate next user’s rightsRepeat step 2 with new user’s SID
5Check group nesting for inherited rightsGet-DomainGroup -Identity <GROUP> | select memberof
6Validate full attack pathBloodHound Transitive Object Control / pre-built queries