Detection: Cisco IOS XE Remote Access Probe Burst

Description

This analytic detects bursts of ping, SSH, and Telnet commands issued from Cisco IOS or NX-OS devices. The Salt Typhoon notes describe repeated SSH, Telnet-to-port-22, and ping activity across multiple IP addresses in a short time window.

 1`cisco_ios`
 2facility IN ("AAA", "HA_EM")
 3mnemonic IN ("AAA_ACCOUNTING_MESSAGE", "LOG")
 4message_text IN ("*ssh *", "*telnet *", "*ping *")
 5
 6| rex field=message_text "^\w+:(?<aaa_src>[^:@]+)(?:@[^:]*)?:(?<aaa_user>[^:]*):(?<aaa_command>.*?)(?:\s+\((?<aaa_result>SUCCESS
 7|FAILURE)\))?$"
 8
 9| rex field=message_text "^(?:[^:]+:\s+)?(?:catchall:\s+)?(?<eem_command>.+?)\s*$"
10
11| eval command=lower(trim(coalesce(aaa_command, eem_command, "")))
12
13| where match(command, "^(ssh
14|telnet
15|ping)\s+")
16
17| rex field=command "(?i)^(?:ssh(?:\s+-l\s+\S+)?
18|telnet
19|ping)\s+(?<target_ip>\d{1,3}(?:\.\d{1,3}){3})"
20
21| eval command_type=case(match(command, "^ssh\s+"), "ssh", match(command, "^telnet\s+"), "telnet", match(command, "^ping\s+"), "ping")
22
23| eval user=coalesce(aaa_user, user, "unknown")
24
25| eval src_ip=coalesce(aaa_src, src_ip, "unknown")
26
27| eval dest=coalesce(host, dvc, dest, "unknown")
28
29| bin _time span=10m
30
31| stats count as command_count
32        min(_time) as firstTime
33        max(_time) as lastTime
34        dc(target_ip) as distinct_targets
35        values(target_ip) as target_ips
36        values(command_type) as command_types
37        values(command) as commands
38  by _time dest user src_ip
39
40| where command_count >= 8 OR distinct_targets >= 5
41
42| `security_content_ctime(firstTime)`
43
44| `security_content_ctime(lastTime)`
45
46| `cisco_ios_xe_remote_access_probe_burst_filter`

Data Source

Name Platform Sourcetype Source
Cisco IOS Logs Other 'cisco:ios' 'cisco:ios'

Macros Used

Name Value
security_content_ctime convert timeformat="%Y-%m-%dT%H:%M:%S" ctime($field$)
cisco_ios_xe_remote_access_probe_burst_filter search *
cisco_ios_xe_remote_access_probe_burst_filter is an empty macro by default. It allows the user to filter out any results (false positives) without editing the SPL.

Annotations

Default Configuration

This detection is configured by default in Splunk Enterprise Security to run with the following settings:

Setting Value
Disabled true
Cron Schedule 0 * * * *
Earliest Time -70m@m
Latest Time -10m@m
Schedule Window auto
Creates Finding (Notable) No
Creates Intermediate Finding (Risk Event) Yes
Anomaly detections generate Intermediate Findings (Risk Events). They do not generate a Finding (Notable) directly.

Implementation

Use the Cisco Catalyst Add-on for Splunk (https://splunkbase.splunk.com/app/7538) to Ingest Cisco IOS-XE syslog with sourcetype "cisco:ios". Command visibility requires AAA command accounting, archive/config logging for configuration commands, or EEM catchall logging.

Known False Positives

Network reachability testing, migration validation, and troubleshooting can generate repeated ping, SSH, or Telnet commands.

Associated Analytic Story

Intermediate Findings

Message Entity Field Entity Type Risk Score
User $user$ issued $command_count$ ping, SSH, or Telnet commands from Cisco device $dest$ across $distinct_targets$ targets. dest system 20

Threat Objects

Field Type
commands command
target_ips ip_address

References

Detection Testing

Test Type Status Dataset Source Sourcetype
Validation Passing N/A N/A N/A
Unit Passing Dataset ctb:nexus:syslog cisco:ios
Integration ✅ Passing Dataset ctb:nexus:syslog cisco:ios

Replay any dataset to Splunk Enterprise by using our replay.py tool or the UI. Alternatively you can replay a dataset into a Splunk Attack Range


Source: GitHub | Version: 1