Remote Desktop Attacks on the Rise - Mitigation
Remove Public Exposure of Port 3389
Never expose RDP directly to the internet.
Use VPNs, Remote Desktop Gateway, or Azure Bastion to
tunnel access securely.
Implement IP allowlists and geo-fencing to restrict access to
known locations.
2. Enforce Strong Authentication
Enable Multi-Factor Authentication (MFA) with
push-spam resistant methods (e.g., number matching, hardware tokens).
Require Network Level Authentication (NLA) to validate users before
session initiation.
Pair NLA with TLS encryption to secure the handshake.
3. Apply Account Lockout Policies
Set thresholds for failed login attempts and lockout
durations to block brute-force bots.
Use smart lockout features in Active Directory or Azure AD to reduce
false positives.
4. Monitor and Alert on RDP Activity
Watch for:
Sudden spikes in failed logons
Repeated login attempts across multiple usernames
Logins from unusual geographies
Use EDR tools that stitch session-level telemetry to detect
“spray and pray” attacks.
5. Use Just-in-Time Access
Implement Just-in-Time (JIT) access via Azure
Security Center or similar tools to limit RDP availability windows. Automatically
revoke access after task completion.
6. Harden RDP Configuration
Disable clipboard redirection, printer mapping, and drive
sharing unless necessary.
Limit concurrent sessions and enforce idle timeouts.
Regularly patch RDP-related services and monitor for CVEs.
7. Audit and Log Everything
Enable detailed logging of RDP sessions, including:
Logon/logoff events
Session duration
Source IP and device
Forward logs to SIEM for correlation and alerting.
Check for RDP Exposure Script
# Check RDP exposure on local or remote machine
$ComputerName = $env:COMPUTERNAME # Replace with remote name if needed
Write-Host "Checking RDP exposure on $ComputerName..." -ForegroundColor Cyan
# 1. Check if RDP is enabled
$rdpStatus = Get-ItemProperty -Path "HKLM:\System\CurrentControlSet\Control\Terminal Server" -Name "fDenyTSConnections"
if ($rdpStatus.fDenyTSConnections -eq 0) {
Write-Host "✅ RDP is ENABLED" -ForegroundColor Yellow
} else {
Write-Host "❌ RDP is DISABLED" -ForegroundColor Green
}
# 2. Check if Network Level Authentication is required
$nlaStatus = Get-ItemProperty -Path "HKLM:\System\CurrentControlSet\Control\Terminal Server\WinStations\RDP-Tcp" -Name "UserAuthentication"
if ($nlaStatus.UserAuthentication -eq 1) {
Write-Host "✅ NLA is ENABLED" -ForegroundColor Green
} else {
Write-Host "⚠️ NLA is DISABLED" -ForegroundColor Red
}
# 3. Check if firewall allows inbound RDP
$firewallRule = Get-NetFirewallRule -DisplayName "Remote Desktop - User Mode (TCP-In)" -ErrorAction SilentlyContinue
if ($firewallRule -and $firewallRule.Enabled -eq "True") {
Write-Host "⚠️ Firewall allows inbound RDP (TCP 3389)" -ForegroundColor Yellow
} else {
Write-Host "✅ Firewall blocks inbound RDP" -ForegroundColor Green
}
# 4. Check if port 3389 is listening
$tcpCheck = Get-NetTCPConnection -LocalPort 3389 -State Listen -ErrorAction SilentlyContinue
if ($tcpCheck) {
Write-Host "⚠️ Port 3389 is LISTENING" -ForegroundColor Yellow
} else {
Write-Host "✅ Port 3389 is NOT listening" -ForegroundColor Green
}