Overview
- Assume-breach creds for j.arbuckle give us domain access.
- j.arbuckle has WRITE on the scriptPath attribute of l.wilson and l.wilson_adm, and we can write to the logon-script folder in SYSVOL. Combining the two gives code execution as any user who logs in.
- We overwrite the SYSVOL logon script with a reverse shell and point l.wilson's scriptPath at it, giving a foothold as l.wilson.
- l.wilson can reset l.wilson_adm's password over LDAP. l.wilson_adm is an RODC administrator, which gives user access and WinRM.
- From there we pivot to the internal RODC, abuse RBCD to get SYSTEM on RODC01, then manipulate the RODC's msDS-NeverRevealGroup / msDS-RevealOnDemandGroup to force the RODC to cache the Administrator hash, dump it with mimikatz, and get Domain Admin.
Nmap Scan
Bash
Bash
Recon
Assume Breach Credentials
Bash
Inspecting SMB Shares
Bash
Finding the Logon Script
Bash
Inspecting the Batch File
Bash
BloodyAD, LDAP Enumeration
Bash
Bash
Foothold
The scriptPath Primitive
TL;DR: scriptPath names a batch/script file in \\<dc>\SYSVOL\<domain>\scripts that runs automatically at that user's logon. We have WRITE on scriptPath and write access to the scripts folder, so we replace printerDetect.bat with a reverse shell and set a target's scriptPath to it. Next time they log in, the DC runs our payload as that user.The scriptPath attribute stores the filename of a logon script that Active Directory runs for that user every time they log in. Two conditions have to hold for this to give us execution:
- We must be able to set scriptPath on a target user, which we can (BloodyAD confirmed WRITE).
- The script we point to must exist in the domain's logon-script folder, C:\Windows\SYSVOL\sysvol\<domain>\scripts (exposed as \\dc01\SYSVOL\garfield.htb\scripts and \\dc01\NETLOGON), which is where printerDetect.bat already lives.
Confirming Write Access to the scripts Folder
Bash
Building and Uploading the Payload
Bash
Bash
Choosing the Target with BloodHound
Setting scriptPath and Catching the Shell
Bash
Bash
User: l.wilson_adm
Resetting l.wilson_adm's Password
Powershell
Powershell
Confirming the New Credentials
Bash
Grabbing the User Flag
Powershell
Root
Mapping the Second DC
Powershell
Pivoting with Chisel
Powershell
Note: the target machine was reset at this point in the engagement, so the DC01 IP changes from 10.129.244.207 to 10.129.106.96 in the commands below. Both refer to the same writable Domain Controller.
Getting SYSTEM on RODC01 via RBCD
Don't change the RODC01$ password. Changing the RODC01 computer account appeared to invalidate the RBCD attack path. Since the RODC is not writable, my guess is once we change its password, it can't communicate to the writable domain controller anymore with the hash stored in its memory.First we need a computer account we control. By default any domain user can add up to ten (MachineAccountQuota), so we create m0rgxn$:
Bash
Bash
Bash
Staging Mimikatz on the RODC
Bash
Forcing Administrator Hash Replication to the RODC
TL;DR: An RODC only caches secrets for principals in its msDS-RevealOnDemandGroup (allow-list) and not in its msDS-NeverRevealGroup (deny-list, which wins). Administrator is denied by default via the Denied RODC Password Replication Group. Since l.wilson_adm can write both attributes on RODC01$ (by adding ourselves to the RODC Administrators group), we point the deny-list at a group Administrator isn't in (IT Support), add Administrator to the allow-list, force replication with repadmin /rodcpwdrepl, then dump the now-cached hash with mimikatz from our SYSTEM shell on the RODC.
How RODC credential caching works
- msDS-RevealOnDemandGroup: principals whose secrets the RODC may cache (allow-list).
- msDS-NeverRevealGroup: principals whose secrets the RODC must never cache (deny-list, takes precedence).
Step 1: Inspect the deny-list
Bash
Step 2: Swap the deny-list to IT Support Group
Bash
Step 3: Add Administrator to the allow-list
Bash
Step 4: Trigger replication and dump the hash
Bash
Domain Admin on DC01
Bash
Attack Path Recap
- Recon: assume-breach j.arbuckle → SYSVOL logon script (printerDetect.bat) + WRITE on scriptPath of l.wilson / l.wilson_adm.
- Foothold: overwrite the SYSVOL script with a reverse shell, set l.wilson's scriptPath → shell as l.wilson.
- User: l.wilson resets l.wilson_adm's password (Set-ADAccountPassword -Reset) → RODC administrator + user flag.
- Root: pivot to internal RODC01 (chisel) → RBCD + S4U → SYSTEM on RODC → edit msDS-NeverRevealGroup/msDS-RevealOnDemandGroup → force Administrator hash caching → dump with mimikatz → PtH as Administrator on DC01.


