Detection rules › Splunk
Internal Port Scan - Critical Ports (Windows Event Log)
After gaining an initial foothold, threat actors may attempt to identify services operating on hosts within the network, often using legitimate port scanning software. This use case detects when more than 5 of the following ports have been scanned from a single internal source IP within one minute: 21 (FTP), 22 (SSH), 23 (Telnet), 25 (SMTP), 80 (HTTP), 8080 (Alternative HTTP), 139 (NetBIOS/SMB), 389 (LDAP), 443 (HTTPS), 8443 (Alternative HTTPS), 445 (Microsoft-DS/SMB), 3306 (MySQL), 3389 (RDP).
MITRE ATT&CK coverage
| Tactic | Techniques |
|---|---|
| Discovery |
References
Telemetry coverage
Rule body
id: '26208.48343'
title: Internal Port Scan - Critical Ports
description: 'After gaining an initial foothold, threat actors may attempt to identify
services operating on hosts within the network, often using legitimate port scanning
software. This use case detects when more than 5 of the following ports have been
scanned from a single internal source IP within one minute: 21 (FTP), 22 (SSH),
23 (Telnet), 25 (SMTP), 80 (HTTP), 8080 (Alternative HTTP), 139 (NetBIOS/SMB), 389
(LDAP), 443 (HTTPS), 8443 (Alternative HTTPS), 445 (Microsoft-DS/SMB), 3306 (MySQL),
3389 (RDP). '
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=5152) OR
"<EventID>5152<" OR TERM(EventCode=5156) OR "<EventID>5156<") | where match(src_ip,
"(10\.\d{1,3}\.\d{1,3}\.\d{1,3}|172\.(1[6-9]|2[0-9]|3[0-1])\.\d{1,3}\.\d{1,3}|192\.168\.\d{1,3}\.\d{1,3})")
and match(dest_port, "^(21|22|23|25|80|8080|139|389|443|8443|445|3306|3389)$") and
not match(process_path, "(?i)\x5csplunkuniversalforwarder\x5cbin\x5csplunkd\.exe")
| table _time, host, user, signature_id, process, process_*, dest_port, dest_ip,
src_ip | bin span=60s | stats values(*) as * by _time, host | streamstats dc(dest_port)
as dc_dest_port by _time, src_ip| where dc_dest_port>5 '
techniques:
- discovery:network service discovery
technique_id:
- T1046
data_category:
- Windows event logs
references:
- https://www.fortinet.com/content/dam/fortinet/assets/threat-reports/rhysida-ransomware-intrusion.pdf?utm_source=blog&utm_medium=blog&utm_campaign=rhysida-ransomware
- https://www.advanced-port-scanner.com/
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=5152) OR "<EventID>5152<" OR TERM(EventCode=5156) OR "<EventID>5156<")
Stage 2: where
| where match(src_ip, "(10\.\d{1,3}\.\d{1,3}\.\d{1,3}|172\.(1[6-9]|2[0-9]|3[0-1])\.\d{1,3}\.\d{1,3}|192\.168\.\d{1,3}\.\d{1,3})") and match(dest_port, "^(21|22|23|25|80|8080|139|389|443|8443|445|3306|3389)$") and not match(process_path, "(?i)\x5csplunkuniversalforwarder\x5cbin\x5csplunkd\.exe")
Stage 3: table
| table _time, host, user, signature_id, process, process_*, dest_port, dest_ip, src_ip
Stage 4: bucket
| bin span=60s
Stage 5: stats
| stats values(*) as * by _time, host
Stage 6: streamstats
| streamstats dc(dest_port) as dc_dest_port by _time, src_ip
Stage 7: where
| where dc_dest_port>5
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process_path | regex_match | "(?i)\x5csplunkuniversalforwarder\x5cbin\x5csplunkd.exe" | excludes:process_path |
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq |
dc_dest_port | gt |
| field:"dc_dest_port" kind:gt value:"5" |
dest_port | regex_match |
| field:"DestinationPort" kind:regex_match |
src_ip | regex_match |
| field:"src_ip" kind:regex_match |
Search terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>5152<" |
| 1 | "<EventID>5156<" |