This is the third post in my “PowerView PowerUsage” series, and follows the same Scenario/Solution/Explanation pattern as the previous entries. The original post contains a constantly updated list of the entire series.
Active Directory access control is something my workmates and I have been very interested in over the past year. So far, this has resulted in the release of BloodHound’s ACL Attack Path Update, as well as work on Active Directory DACL backdooring by @_wald0 and myself (whitepaper here). This post will cover DACL enumeration for GPOs in a foreign domain.
Why care about this? Well, if you are able to edit a GPO, then you can gain control of any user or computer the GPO applies to. If your goal is to figure out specifically what objects a given GPO applies to, check out this line in the “PowerView-3.0-tricks” gist.
The Scenario
You’re on an engagement and want to know what security principals can edit GPOs in a foreign domain (in this case dev.testlab.local).
The Solution
https://gist.github.com/HarmJ0y/d2eb8e3aa2db4de0bd365cedcef5a406
The Explanation
First, we use PowerView’s Get-DomainObjectACL to enumerate the ACEs for all group policy objects in a foreign domain. The -Domain ‘dev.testlab.local’ flag signals the query to run in the foreign domain, and the LDAP filter -LDAPFilter ‘(objectCategory=groupPolicyContainer)’ indicates to only return group policy objects. The -ResolveGUIDs flag indicates that any target GUIDs in the ACEs should be resolved to their human readable names.
We then implement a custom filter with ? {…} (Where-Object), only returning results where the SecurityIdentifier of the trustee/principal (the object that has the rights) matches the regex ‘^S-1-5-.*-[1-9]\d{3,}$’. This returns only results where the security identifier of the trustee has a relative identifier (RID) of -1000 and above, i.e. objects that are not built in like ‘Domain Admins’. The purpose of this filter is to reduce noise in an attempt to enumerate more ‘interesting’ misconfigurations of non-standard domain users. The second part of the filter matches for rights in the ACE that indicate some type of control relationship (generic all rights, rights to change the owner, etc), i.e. some type of “object takeover” primitive that allows for compromise of the target object. For more information on this type of relationship/attack, check out @wald0’s and my “An ACE Up the Sleeve” whitepaper.
From here, in order to add a bit more contextual information for the operator, we process each ACE result on the pipeline by way of % {…} (ForEach-Object), and resolve the SecurityIdentifier of the ACE to a distinguished name by using PowerView’s Convert-ADName with the -OutputType set to DN (distinguished name). We finish by using New-Object PSObject to create a new custom object in the middle of the pipeline that contains the information we care about, and pipe everything to fl (Format-List) for easy display.
Now that you know what accounts are able to edit these interesting GPOs, you could perform targeted account compromise of these accounts and use them to push malicious GPOs.