Skip to content
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
name: Cisco NVM - MacOS Browser Spawned Shell External Connection
id: 6f2de8d1-9a2d-4c7a-9b8c-3b8a2f7d0e41
version: 1
creation_date: '2026-09-02'
modification_date: '2026-09-02'
author: Maria Jose Erquiaga, Splunk
status: production
type: Anomaly
description: |
Detects potentially suspicious behavior on MacOS where a browser process spawns a command interpreter that establishes a network connection to a public IP address. This behavior may indicate malicious browser content, a compromised website, drive-by execution, or browser-initiated command execution.
data_source:
- Cisco Network Visibility Module Flow Data
search: |
`cisco_network_visibility_module_flowdata`
process_path IN ("*/bash","*/csh","*/dash","*/fish","*/sh","*/tcsh","*/zsh")
parent_process_path IN ("*/arc","*/brave","*/brave-browser","*/chrome","*/chromium","*/duckduckgo","*/firefox","*/firefox-bin","*/google chrome","*/google-chrome","*/librewolf","*/microsoft edge","*/msedge","*/opera","*/opera gx","*/safari","*/tor browser","*/vivaldi","*/waterfox")
AND NOT (
cidrmatch("0.0.0.0/8",dest_ip) OR cidrmatch("10.0.0.0/8",dest_ip) OR cidrmatch("100.64.0.0/10",dest_ip) OR
cidrmatch("127.0.0.0/8",dest_ip) OR cidrmatch("169.254.0.0/16",dest_ip) OR cidrmatch("172.16.0.0/12",dest_ip) OR
cidrmatch("192.0.0.0/24",dest_ip) OR cidrmatch("192.0.2.0/24",dest_ip) OR cidrmatch("192.168.0.0/16",dest_ip) OR
cidrmatch("198.18.0.0/15",dest_ip) OR cidrmatch("198.51.100.0/24",dest_ip) OR cidrmatch("203.0.113.0/24",dest_ip) OR
cidrmatch("224.0.0.0/4",dest_ip) OR cidrmatch("240.0.0.0/4",dest_ip) OR cidrmatch("255.255.255.255/32",dest_ip) OR
cidrmatch("fc00::/7",dest_ip) OR cidrmatch("fe80::/10",dest_ip) OR cidrmatch("ff00::/8",dest_ip) OR
cidrmatch("2001:db8::/32",dest_ip) OR dest_ip="::" OR dest_ip="::1"
)
| stats count
min(_time) as firstTime
max(_time) as lastTime
by src_ip dest_ip dest_hostname bytes_in bytes_out
user process_id process_name process_path process
parent_process_id parent_process_name parent_process_path parent_process
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `cisco_nvm___macos_browser_spawned_shell_external_connection_filter`
how_to_implement: |
This search requires Network Visibility Module logs, which includes the flow data sourcetype.
This search uses an input macro named `cisco_network_visibility_module_flowdata`.
We strongly recommend that you specify your environment-specific configurations
(index, source, sourcetype, etc.) for Cisco Network Visibility Module logs.
Replace the macro definition with configurations for your Splunk environment.
The search also uses a post-filter macro designed to filter out known false positives.
The logs are to be ingested using the Splunk Add-on for Cisco Endpoint Security Analytics (CESA) (https://splunkbase.splunk.com/app/4221).
known_false_positives: |
Legitimate workflows may launch Unix command interpreters from browser contexts, including developer tooling, software installers, SSO helpers, browser extensions, and automation wrappers. Tuning may be required for approved applications, users, and destinations.
references:
- https://attack.mitre.org/tactics/TA0002/
- https://attack.mitre.org/techniques/T1059/
- https://redcanary.com/threat-detection-report/threats/socgholish/
drilldown_searches:
- name: View the detection results for - "$src$"
search: '%original_detection_search% | search src="$src$"'
earliest_offset: $info_min_time$
latest_offset: $info_max_time$
- name: View risk events for the last 7 days for - "$src$"
search: '| from datamodel Risk.All_Risk | search normalized_risk_object IN ("$src$") | stats count min(_time) as firstTime max(_time) as lastTime values(search_name) as "Search Name" values(risk_message) as "Risk Message" values(analyticstories) as "Analytic Stories" values(annotations._all) as "Annotations" values(annotations.mitre_attack.mitre_tactic) as "ATT&CK Tactics" by normalized_risk_object | `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)`'
Comment on lines +51 to +55

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Use the emitted src_ip field in drilldowns

When an analyst opens either drilldown, $src$ cannot be populated because the preceding stats command retains only src_ip, not src. This leaves the detection-results filter and risk-object lookup with an empty or unresolved source value; update both drilldowns to reference $src_ip$ and filter on src_ip.

Useful? React with 👍 / 👎.

earliest_offset: 7d
latest_offset: "0"
intermediate_findings:
entities:
- field: src_ip
type: system
score: 40
message: Browser process $parent_process$ spawned command interpreter $process$ on $src_ip$, which connected to public IP $dest_ip$.
threat_objects:
- field: process
type: process
- field: dest_ip
type: ip_address
- field: dest_hostname
type: domain
analytic_story:
- Cisco Network Visibility Module Analytics
asset_type: Endpoint
mitre_attack_id:
- T1059
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
tests:
- name: True Positive Test - Cisco NVM Browser Spawned Interpreter Public Egress
attack_data:
- data: https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/attack_techniques/T1059/macos_browser_spawned_script_external_network_connection/nvm_flowdata.log
source: not_applicable
sourcetype: cisco:nvm:flowdata:v2
test_type: unit
Loading