Detection rules › Splunk
Splunk rules: 0n
Active Directory Lateral Movement Identified
#The following analytic identifies potential lateral movement activities within an organization's Active Directory (AD) environment. It detects this activity by correlating multiple analytics from the Active Directory Lateral Movement analytic story within a specified time frame. This is significant for a SOC as lateral movement is a common tactic used by attackers to expand their access within a network, posing a substantial risk. If confirmed malicious, this activity could allow attackers to escalate privileges, access sensitive information, and persist within the environment, leading to severe security breaches.
Known False Positives
- False positives will most likely be present based on risk scoring and how the organization handles system to system communication. Filter, or modify as needed. In addition to count by analytics, adding a risk score may be useful. In our testing, with 22 events over 30 days, the risk scores ranged from 500 to 80,000. Your organization will be different, monitor and modify as needed.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Lateral Movement |
Rule Body
name: Active Directory Lateral Movement Identified
id: 6aa6f9dd-adfe-45a8-8f74-c4c7a0d7d037
version: 10
creation_date: '2023-04-19'
modification_date: '2026-05-13'
author: Michael Haag, Splunk
status: production
type: Correlation
description: The following analytic identifies potential lateral movement activities within an organization's Active Directory (AD) environment. It detects this activity by correlating multiple analytics from the Active Directory Lateral Movement analytic story within a specified time frame. This is significant for a SOC as lateral movement is a common tactic used by attackers to expand their access within a network, posing a substantial risk. If confirmed malicious, this activity could allow attackers to escalate privileges, access sensitive information, and persist within the environment, leading to severe security breaches.
data_source: []
search: |-
| tstats `security_content_summariesonly` min(_time) as firstTime max(_time) as lastTime sum(All_Risk.calculated_risk_score) as risk_score, count(All_Risk.calculated_risk_score) as risk_event_count, values(All_Risk.annotations.mitre_attack.mitre_tactic_id) as annotations.mitre_attack.mitre_tactic_id, dc(All_Risk.annotations.mitre_attack.mitre_tactic_id) as mitre_tactic_id_count, values(All_Risk.annotations.mitre_attack.mitre_technique_id) as annotations.mitre_attack.mitre_technique_id, dc(All_Risk.annotations.mitre_attack.mitre_technique_id) as mitre_technique_id_count, values(All_Risk.tag) as tag, values(source) as source, dc(source) as source_count FROM datamodel=Risk.All_Risk
WHERE All_Risk.analyticstories="Active Directory Lateral Movement" All_Risk.risk_object_type="system"
BY All_Risk.risk_object All_Risk.risk_object_type All_Risk.annotations.mitre_attack.mitre_tactic
| `drop_dm_object_name(All_Risk)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| where source_count >= 4
| `active_directory_lateral_movement_identified_filter`
how_to_implement: Splunk Enterprise Security is required to utilize this correlation. In addition, modify the source_count value to your environment. In our testing, a count of 4 or 5 was decent in a lab, but the number may need to be increased as the analytic story includes over 30 analytics. In addition, based on false positives, modify any analytics to be anomaly and lower or increase risk based on organization importance.
known_false_positives: False positives will most likely be present based on risk scoring and how the organization handles system to system communication. Filter, or modify as needed. In addition to count by analytics, adding a risk score may be useful. In our testing, with 22 events over 30 days, the risk scores ranged from 500 to 80,000. Your organization will be different, monitor and modify as needed.
references:
- https://attack.mitre.org/tactics/TA0008/
- https://research.splunk.com/stories/active_directory_lateral_movement/
finding:
title: Active Directory Lateral Movement Identified - $risk_object$
entity:
field: risk_object
type: system
score: 0
analytic_story:
- Active Directory Lateral Movement
asset_type: Endpoint
mitre_attack_id:
- T1210
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: tstats
| tstats `security_content_summariesonly`
min(_time) as firstTime
max(_time) as lastTime
sum(All_Risk.calculated_risk_score) as risk_score,
count(All_Risk.calculated_risk_score) as risk_event_count,
values(All_Risk.annotations.mitre_attack.mitre_tactic_id) as annotations.mitre_attack.mitre_tactic_id,
dc(All_Risk.annotations.mitre_attack.mitre_tactic_id) as mitre_tactic_id_count,
values(All_Risk.annotations.mitre_attack.mitre_technique_id) as annotations.mitre_attack.mitre_technique_id,
dc(All_Risk.annotations.mitre_attack.mitre_technique_id) as mitre_technique_id_count,
values(All_Risk.tag) as tag,
values(source) as source,
dc(source) as source_count
FROM datamodel=Risk.All_Risk
WHERE All_Risk.analyticstories="Active Directory Lateral Movement"
All_Risk.risk_object_type="system"
BY All_Risk.risk_object All_Risk.risk_object_type All_Risk.annotations.mitre_attack.mitre_tactic
Stage 2: search
| `drop_dm_object_name(All_Risk)`
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: where
| where source_count >= 4
Stage 6: search
| `active_directory_lateral_movement_identified_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
All_Risk.analyticstories | eq |
| field:"All_Risk.analyticstories" kind:eq value:"Active Directory Lateral Movement" |
All_Risk.risk_object_type | eq |
| field:"All_Risk.risk_object_type" kind:eq value:"system" |
source_count | ge |
| field:"source_count" kind:ge value:"4" |
AutoHotkey Execution (Sysmon)
#Adversaries may execute commands and perform malicious tasks using AutoIT and AutoHotKey automation scripts. AutoIT and AutoHotkey (AHK) are scripting languages that enable users to automate Windows tasks. These automation scripts can be used to perform a wide variety of actions, such as clicking on buttons, entering text, and opening and closing programs. This use case detects the usage of the AutoHotkey software to execute ahk files.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution |
References
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
Rule Body
id: '32156.57264'
title: AutoHotkey Execution
description: Adversaries may execute commands and perform malicious tasks using AutoIT
and AutoHotKey automation scripts. AutoIT and AutoHotkey (AHK) are scripting languages
that enable users to automate Windows tasks. These automation scripts can be used
to perform a wide variety of actions, such as clicking on buttons, entering text,
and opening and closing programs. This use case detects the usage of the AutoHotkey
software to execute ahk files.
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_sysmon` (TERM(EventCode=1) OR "<EventID>1<")
("AutoHotkey.exe" OR "AutoHotkey.rc" OR "AutoHotkey32.exe" OR "AutoHotkey32_UIA.exe"
OR "AutoHotkey64.exe" OR "AutoHotkey64_UIA.exe" OR "AutoHotkeyA32.exe" OR "AutoHotkeyA32_UIA.exe"
OR "AutoHotkeyU32.exe" OR "AutoHotkeyU32_UIA.exe" OR "AutoHotkeyU64.exe" OR "AutoHotkeyU64_UIA.exe"
OR "AutoHotkeyUX.exe") "ahk" | table _time, host, user, process, parent_process_name,
process_name, process_path | bin span=1s | stats values(*) as * by _time, host '
techniques:
- execution:command and scripting interpreter
technique_id:
- T1059
data_category:
- Windows Sysmon
references:
- https://attack.mitre.org/techniques/T1059/010/
- https://detection.fyi/sigmahq/sigma/windows/process_creation/proc_creation_win_renamed_autohotkey/
- https://www.autohotkey.com/
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_sysmon` (TERM(EventCode=1) OR "<EventID>1<") ("AutoHotkey.exe" OR "AutoHotkey.rc" OR "AutoHotkey32.exe" OR "AutoHotkey32_UIA.exe" OR "AutoHotkey64.exe" OR "AutoHotkey64_UIA.exe" OR "AutoHotkeyA32.exe" OR "AutoHotkeyA32_UIA.exe" OR "AutoHotkeyU32.exe" OR "AutoHotkeyU32_UIA.exe" OR "AutoHotkeyU64.exe" OR "AutoHotkeyU64_UIA.exe" OR "AutoHotkeyUX.exe") "ahk"
Stage 2: table
| table _time, host, user, process, parent_process_name, process_name, process_path
Stage 3: bucket
| bin span=1s
Stage 4: stats
| stats values(*) as * by _time, host
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"1" |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>1<" |
| 1 | "AutoHotkey.exe" |
| 1 | "AutoHotkey.rc" |
| 1 | "AutoHotkey32.exe" |
| 1 | "AutoHotkey32_UIA.exe" |
| 1 | "AutoHotkey64.exe" |
| 1 | "AutoHotkey64_UIA.exe" |
| 1 | "AutoHotkeyA32.exe" |
| 1 | "AutoHotkeyA32_UIA.exe" |
| 1 | "AutoHotkeyU32.exe" |
| 1 | "AutoHotkeyU32_UIA.exe" |
| 1 | "AutoHotkeyU64.exe" |
| 1 | "AutoHotkeyU64_UIA.exe" |
| 1 | "AutoHotkeyUX.exe" |
| 1 | "ahk" |
AWS Successful Console Authentication From Multiple IPs
#The following analytic detects an AWS account successfully authenticating from multiple unique IP addresses within a 5-minute window. It leverages AWS CloudTrail logs, specifically monitoring ConsoleLogin events and counting distinct source IPs. This behavior is significant as it may indicate compromised credentials, potentially from a phishing attack, being used concurrently by an adversary and a legitimate user. If confirmed malicious, this activity could allow unauthorized access to corporate resources, leading to data breaches or further exploitation within the AWS environment.
Known False Positives
- A user with successful authentication events from different Ips may also represent the legitimate use of more than one device. Filter as needed and/or customize the threshold to fit your environment.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Resource Development | |
| Stealth |
Telemetry Coverage
Rules Detecting the Same Action
These rules filter on the same operation.
- AWS Console Login (Panther)
- AWS Console Login Failed During MFA Challenge (Splunk)
- AWS ConsoleLogin Failed Authentication (Sigma)
- AWS CreateLoginProfile (Splunk)
- AWS Credential Access Failed Login (Splunk)
- AWS High Number Of Failed Authentications For User (Splunk)
- AWS High Number Of Failed Authentications From Ip (Splunk)
- AWS Multiple Failed MFA Requests For User (Splunk)
Rule Body
name: AWS Successful Console Authentication From Multiple IPs
id: 395e50e1-2b87-4fa3-8632-0dfbdcbcd2cb
version: 12
creation_date: '2023-01-19'
modification_date: '2026-05-13'
author: Bhavin Patel, Splunk
status: production
type: Anomaly
description: The following analytic detects an AWS account successfully authenticating from multiple unique IP addresses within a 5-minute window. It leverages AWS CloudTrail logs, specifically monitoring `ConsoleLogin` events and counting distinct source IPs. This behavior is significant as it may indicate compromised credentials, potentially from a phishing attack, being used concurrently by an adversary and a legitimate user. If confirmed malicious, this activity could allow unauthorized access to corporate resources, leading to data breaches or further exploitation within the AWS environment.
data_source:
- AWS CloudTrail ConsoleLogin
search: |-
`cloudtrail` eventName = ConsoleLogin
| bin span=5m _time
| rename user_name as user
| stats dc(src) as distinct_ip_count values(src) as src values(user_agent) as user_agent values(dest) as dest
BY _time, user, signature,
vendor_account, vendor_region, vendor_product
| where distinct_ip_count>1
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `aws_successful_console_authentication_from_multiple_ips_filter`
how_to_implement: You must install Splunk AWS add on and Splunk App for AWS. This search works when AWS CloudTrail events are normalized use the Authentication datamodel.
known_false_positives: A user with successful authentication events from different Ips may also represent the legitimate use of more than one device. Filter as needed and/or customize the threshold to fit your environment.
references:
- https://rhinosecuritylabs.com/aws/mfa-phishing-on-aws/
intermediate_findings:
entities:
- field: user
type: user
score: 20
message: User $user$ has successfully logged into the AWS Console from different IP addresses $src$ within 5 mins
threat_objects:
- field: src
type: ip_address
analytic_story:
- Suspicious AWS Login Activities
- Compromised User Account
asset_type: AWS Account
mitre_attack_id:
- T1586
- T1535
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: cloud
security_domain: threat
Stages and Predicates
Stage 1: search
`cloudtrail` eventName = ConsoleLogin
Stage 2: bucket
| bin span=5m _time
Stage 3: rename
| rename user_name as user
Stage 4: stats
| stats
dc(src) as distinct_ip_count
values(src) as src
values(user_agent) as user_agent
values(dest) as dest
BY _time, user, signature,
vendor_account, vendor_region, vendor_product
Stage 5: where
| where distinct_ip_count>1
Stage 6: search
| `security_content_ctime(firstTime)`
Stage 7: search
| `security_content_ctime(lastTime)`
Stage 8: search
| `aws_successful_console_authentication_from_multiple_ips_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
distinct_ip_count | gt |
| field:"distinct_ip_count" kind:gt value:"1" |
eventName | eq |
| field:"aws::eventName" kind:eq value:"ConsoleLogin" |
sourcetype | eq |
| field:"sourcetype" kind:eq value:"aws:cloudtrail" |
Browser Started with Remote Debugging - Windows (Windows Event Log)
#Threat actors may abuse browser remote debugging features to extract sensitive data, maintain access, or facilitate communication with C2 servers. This is typically done by launching the browser with specific remote debugging flags, allowing remote access to browser sessions and potentially bypassing traditional security controls. This use case detects instances where a browser is started in remote debugging mode.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Collection |
References
- https://yoroi.company/wp-content/uploads/2022/05/EternityGroup_report_compressed.pdf
- https://www.mdsec.co.uk/2022/10/analysing-lastpass-part-1/
- https://github.com/defaultnamehere/cookie_crimes/
- https://github.com/wunderwuzzi23/firefox-cookiemonster
- https://www.trendmicro.com/en_us/research/25/c/ai-assisted-fake-github-repositories.html
- https://cyble.com/blog/fake-coding-challenges-steal-sensitive-data-via-fogdoor/
- https://detection.fyi/sigmahq/sigma/windows/process_creation/proc_creation_win_browsers_remote_debugging/
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Security-Auditing | Event ID 4688: A new process has been created. |
Rule Body
id: '44220.86860'
title: Browser Started with Remote Debugging - Windows
description: Threat actors may abuse browser remote debugging features to extract
sensitive data, maintain access, or facilitate communication with C2 servers. This
is typically done by launching the browser with specific remote debugging flags,
allowing remote access to browser sessions and potentially bypassing traditional
security controls. This use case detects instances where a browser is started in
remote debugging mode.
logic_format: Splunk
logic: ' `get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=4688) OR
"<EventID>4688<" OR Type=Process) (TERM(Firefox) " -start-debugger-service") OR
" --remote-debugging-" | where match(process, "(?i)\s+--remote-debugging-\S+") or
(process="firefox.exe" and match(process, "(?i)\s+-start-debugger-service")) | table
_time, host, user, process, parent_process_name, process_path | bin span=1s | stats
values(*) as * by _time, host '
techniques:
- collection:browser session hijacking
technique_id:
- T1185
data_category:
- Process command-line parameters
- Windows event logs
references:
- https://yoroi.company/wp-content/uploads/2022/05/EternityGroup_report_compressed.pdf
- https://www.mdsec.co.uk/2022/10/analysing-lastpass-part-1/
- https://github.com/defaultnamehere/cookie_crimes/
- https://github.com/wunderwuzzi23/firefox-cookiemonster
- https://www.trendmicro.com/en_us/research/25/c/ai-assisted-fake-github-repositories.html
- https://cyble.com/blog/fake-coding-challenges-steal-sensitive-data-via-fogdoor/
- https://detection.fyi/sigmahq/sigma/windows/process_creation/proc_creation_win_browsers_remote_debugging/
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=4688) OR "<EventID>4688<" OR Type=Process) (TERM(Firefox) " -start-debugger-service") OR " --remote-debugging-"
Stage 2: where
| where match(process, "(?i)\s+--remote-debugging-\S+") or (
process="firefox.exe"
and match(process, "(?i)\s+-start-debugger-service")
)
Stage 3: table
| table _time, host, user, process, parent_process_name, process_path
Stage 4: bucket
| bin span=1s
Stage 5: stats
| stats values(*) as * by _time, host
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"4688" |
process | eq |
| field:"CommandLine" kind:eq value:"firefox.exe" |
process | regex_match |
| field:"CommandLine" kind:regex_match |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>4688<" |
| 1 | Firefox |
| 1 | " -start-debugger-service" |
| 1 | " --remote-debugging-" |
CertUtil With Decode Argument
#The following analytic detects the use of CertUtil.exe with the 'decode' argument, which may indicate an attempt to decode a previously encoded file, potentially containing malicious payloads. This detection leverages data from Endpoint Detection and Response (EDR) agents, focusing on command-line executions involving CertUtil.exe. This activity is significant because attackers often use CertUtil to decode malicious files downloaded from the internet, which are then executed to compromise the system. If confirmed malicious, this activity could lead to unauthorized code execution, further system compromise, and potential data exfiltration.
Known False Positives
- Typically seen used to `encode` files, but it is possible to see legitimate use of `decode`. Filter based on parent-child relationship, file paths, endpoint or user.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
| Security-Auditing | Event ID 4688: A new process has been created. |
Rule Body
name: CertUtil With Decode Argument
id: bfe94226-8c10-11eb-a4b3-acde48001122
version: 15
creation_date: '2021-03-25'
modification_date: '2026-05-13'
author: Michael Haag, Splunk
status: production
type: TTP
description: The following analytic detects the use of CertUtil.exe with the 'decode' argument, which may indicate an attempt to decode a previously encoded file, potentially containing malicious payloads. This detection leverages data from Endpoint Detection and Response (EDR) agents, focusing on command-line executions involving CertUtil.exe. This activity is significant because attackers often use CertUtil to decode malicious files downloaded from the internet, which are then executed to compromise the system. If confirmed malicious, this activity could lead to unauthorized code execution, further system compromise, and potential data exfiltration.
data_source:
- Sysmon EventID 1
- Windows Event Log Security 4688
- CrowdStrike ProcessRollup2
search: |-
| tstats `security_content_summariesonly` count min(_time) as firstTime max(_time) as lastTime FROM datamodel=Endpoint.Processes
WHERE `process_certutil` Processes.process=*decode*
BY Processes.action Processes.dest Processes.original_file_name
Processes.parent_process Processes.parent_process_exec Processes.parent_process_guid
Processes.parent_process_id Processes.parent_process_name Processes.parent_process_path
Processes.process Processes.process_exec Processes.process_guid
Processes.process_hash Processes.process_id Processes.process_integrity_level
Processes.process_name Processes.process_path Processes.user
Processes.user_id Processes.vendor_product
| `drop_dm_object_name(Processes)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `certutil_with_decode_argument_filter`
how_to_implement: The detection is based on data that originates from Endpoint Detection and Response (EDR) agents. These agents are designed to provide security-related telemetry from the endpoints where the agent is installed. To implement this search, you must ingest logs that contain the process GUID, process name, and parent process. Additionally, you must ingest complete command-line executions. These logs must be processed using the appropriate Splunk Technology Add-ons that are specific to the EDR product. The logs must also be mapped to the `Processes` node of the `Endpoint` data model. Use the Splunk Common Information Model (CIM) to normalize the field names and speed up the data modeling process.
known_false_positives: Typically seen used to `encode` files, but it is possible to see legitimate use of `decode`. Filter based on parent-child relationship, file paths, endpoint or user.
references:
- https://attack.mitre.org/techniques/T1140/
- https://github.com/redcanaryco/atomic-red-team/blob/master/atomics/T1140/T1140.md
- https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/certutil
- https://www.bleepingcomputer.com/news/security/certutilexe-could-allow-attackers-to-download-malware-while-bypassing-av/
finding:
title: An instance of $parent_process_name$ spawning $process_name$ was identified on endpoint $dest$ by user $user$ attempting to decode a file.
entity:
field: user
type: user
score: 50
intermediate_findings:
entities:
- field: dest
type: system
score: 50
message: An instance of $parent_process_name$ spawning $process_name$ was identified on endpoint $dest$ by user $user$ attempting to decode a file.
threat_objects:
- field: parent_process_name
type: parent_process_name
- field: process_name
type: process_name
analytic_story:
- Deobfuscate-Decode Files or Information
- Living Off The Land
- Forest Blizzard
- APT29 Diplomatic Deceptions with WINELOADER
- Storm-2460 CLFS Zero Day Exploitation
- GhostRedirector IIS Module and Rungan Backdoor
threat_group:
- APT29
- Cozy Bear
- Midnight Blizzard
asset_type: Endpoint
mitre_attack_id:
- T1140
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: tstats
| tstats `security_content_summariesonly`
count
min(_time) as firstTime
max(_time) as lastTime
FROM datamodel=Endpoint.Processes
WHERE `process_certutil` Processes.process=*decode*
BY
Processes.action
Processes.dest
Processes.original_file_name
Processes.parent_process
Processes.parent_process_exec
Processes.parent_process_guid
Processes.parent_process_id
Processes.parent_process_name
Processes.parent_process_path
Processes.process
Processes.process_exec
Processes.process_guid
Processes.process_hash
Processes.process_id
Processes.process_integrity_level
Processes.process_name
Processes.process_path
Processes.user
Processes.user_id
Processes.vendor_product
Stage 2: search
| `drop_dm_object_name(Processes)`
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: search
| `certutil_with_decode_argument_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
Processes.original_file_name | eq |
| field:"OriginalFileName" kind:eq value:"CertUtil.exe" |
Processes.process | eq |
| field:"CommandLine" kind:eq value:"*decode*" |
Processes.process_name | eq |
| field:"process_basename" kind:eq value:"certutil.exe" |
Cloud Provisioning Activity From Previously Unseen City
#The following analytic detects cloud provisioning activities originating from previously unseen cities. It leverages cloud infrastructure logs and compares the geographic location of the source IP address against a baseline of known locations. This activity is significant as it may indicate unauthorized access or misuse of cloud resources from an unexpected location. If confirmed malicious, this could lead to unauthorized resource creation, potential data exfiltration, or further compromise of cloud infrastructure.
Known False Positives
- This is a strictly behavioral search, so we define "false positive" slightly differently. Every time this fires, it will accurately reflect the first occurrence in the time period you're searching within, plus what is stored in the cache feature. But while there are really no "false positives" in a traditional sense, there is definitely lots of noise. This search will fire any time a new IP address is seen in the **GeoIP** database for any kind of provisioning activity. If you typically do all provisioning from tools inside of your country, there should be few false positives. If you are located in countries where the free version of **MaxMind GeoIP** that ships by default with Splunk has weak resolution (particularly small countries in less economically powerful regions), this may be much less valuable to you.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Persistence | |
| Privilege Escalation | |
| Stealth |
Rule Body
name: Cloud Provisioning Activity From Previously Unseen City
id: e7ecc5e0-88df-48b9-91af-51104c68f02f
version: 9
creation_date: '2020-11-30'
modification_date: '2026-05-13'
author: Rico Valdez, Bhavin Patel, Splunk
status: production
type: Anomaly
description: The following analytic detects cloud provisioning activities originating from previously unseen cities. It leverages cloud infrastructure logs and compares the geographic location of the source IP address against a baseline of known locations. This activity is significant as it may indicate unauthorized access or misuse of cloud resources from an unexpected location. If confirmed malicious, this could lead to unauthorized resource creation, potential data exfiltration, or further compromise of cloud infrastructure.
data_source:
- AWS CloudTrail
search: |-
| tstats earliest(_time) as firstTime, latest(_time) as lastTime FROM datamodel=Change
WHERE (
All_Changes.action=started
OR
All_Changes.action=created
)
All_Changes.status=success
BY All_Changes.src, All_Changes.user, All_Changes.object,
All_Changes.command
| `drop_dm_object_name("All_Changes")`
| iplocation src
| where isnotnull(City)
| lookup previously_seen_cloud_provisioning_activity_sources City as City OUTPUT firstTimeSeen, enough_data
| eventstats max(enough_data) as enough_data
| where enough_data=1
| eval firstTimeSeenCity=min(firstTimeSeen)
| where isnull(firstTimeSeenCity) OR firstTimeSeenCity > relative_time(now(), `previously_unseen_cloud_provisioning_activity_window`)
| `security_content_ctime(firstTime)`
| table firstTime, src, City, user, object, command
| `cloud_provisioning_activity_from_previously_unseen_city_filter`
how_to_implement: You must be ingesting your cloud infrastructure logs from your cloud provider. You should run the baseline search `Previously Seen Cloud Provisioning Activity Sources - Initial` to build the initial table of source IP address, geographic locations, and times. You must also enable the second baseline search `Previously Seen Cloud Provisioning Activity Sources - Update` to keep this table up to date and to age out old data. You can adjust the time window for this search by updating the `previously_unseen_cloud_provisioning_activity_window` macro. You can also provide additional filtering for this search by customizing the `cloud_provisioning_activity_from_previously_unseen_city_filter` macro.
known_false_positives: "This is a strictly behavioral search, so we define \"false positive\" slightly differently. Every time this fires, it will accurately reflect the first occurrence in the time period you're searching within, plus what is stored in the cache feature. But while there are really no \"false positives\" in a traditional sense, there is definitely lots of noise.\nThis search will fire any time a new IP address is seen in the **GeoIP** database for any kind of provisioning activity. If you typically do all provisioning from tools inside of your country, there should be few false positives. If you are located in countries where the free version of **MaxMind GeoIP** that ships by default with Splunk has weak resolution (particularly small countries in less economically powerful regions), this may be much less valuable to you."
references: []
intermediate_findings:
entities:
- field: user
type: user
score: 20
message: User $user$ is starting or creating an instance $object$ for the first time in City $City$ from IP address $src$
- field: object
type: system
score: 20
message: User $user$ is starting or creating an instance $object$ for the first time in City $City$ from IP address $src$
threat_objects:
- field: src
type: ip_address
analytic_story:
- Suspicious Cloud Provisioning Activities
asset_type: AWS Instance
mitre_attack_id:
- T1078
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: cloud
security_domain: threat
baselines:
- Previously Seen Cloud Provisioning Activity Sources - Initial
- Previously Seen Cloud Provisioning Activity Sources - Update
Stages and Predicates
Stage 1: tstats
| tstats earliest(_time) as firstTime, latest(_time) as lastTime FROM datamodel=Change
WHERE (
All_Changes.action=started
OR
All_Changes.action=created
)
All_Changes.status=success
BY All_Changes.src, All_Changes.user, All_Changes.object,
All_Changes.command
Stage 2: search
| `drop_dm_object_name("All_Changes")`
Stage 3: search
| iplocation src
Stage 4: where
| where isnotnull(City)
Stage 5: lookup
| lookup previously_seen_cloud_provisioning_activity_sources City as City OUTPUT firstTimeSeen,
enough_data
Stage 6: eventstats
| eventstats max(enough_data) as enough_data
Stage 7: where
| where enough_data=1
Stage 8: eval
| eval firstTimeSeenCity=min(firstTimeSeen)
Stage 9: where
| where isnull(firstTimeSeenCity)
OR firstTimeSeenCity > relative_time(
now(),
`previously_unseen_cloud_provisioning_activity_window`
)
Stage 10: search
| `security_content_ctime(firstTime)`
Stage 11: table
| table firstTime, src, City, user, object, command
Stage 12: search
| `cloud_provisioning_activity_from_previously_unseen_city_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
All_Changes.action | eq |
| field:"All_Changes.action" kind:eq |
All_Changes.status | eq |
| field:"All_Changes.status" kind:eq value:"success" |
City | is_not_null | field:"City" kind:is_not_null | |
enough_data | eq |
| field:"enough_data" kind:eq value:"1" |
firstTimeSeenCity | is_null | field:"firstTimeSeenCity" kind:is_null |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 3 | iplocation |
| 3 | src |
Kubernetes Abuse of Secret by Unusual User Name
#The following analytic detects unauthorized access or misuse of Kubernetes Secrets by unusual user names. It leverages Kubernetes Audit logs to identify anomalies in access patterns by analyzing the source of requests based on user names. This activity is significant for a SOC as Kubernetes Secrets store sensitive information like passwords, OAuth tokens, and SSH keys, making them critical assets. If confirmed malicious, this activity could lead to unauthorized access to sensitive systems or data, potentially resulting in significant security breaches and exfiltration of sensitive information.
Known False Positives
- No false positives have been identified at this time.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Credential Access |
Telemetry Coverage
| Platform | Record / event type |
|---|---|
| Kubernetes | get-secrets: get secrets |
Rules Detecting the Same Action
These rules filter on the same operation.
- Azure AKS Secret get or list with Suspicious User Agent (Elastic)
- Direct Interactive Kubernetes API Request by Unusual Utilities (Elastic)
- GKE Rapid Secret GET Activity Against Multiple Objects (Elastic)
- GKE Secret Access from Node or Denied Service Account (Elastic)
- GKE Secret Access via Unusual User Agent (Elastic)
- GKE Secret get or list with Suspicious User Agent (Elastic)
- GKE Unusual Service Account Secret Access via New User Agent (Elastic)
- Kubernetes Abuse of Secret by Unusual Location (Splunk)
Rule Body
name: Kubernetes Abuse of Secret by Unusual User Name
id: df6e9cae-5257-4a34-8f3a-df49fa0f5c46
version: 10
creation_date: '2023-12-20'
modification_date: '2026-05-13'
author: Patrick Bareiss, Splunk
status: production
type: Anomaly
description: The following analytic detects unauthorized access or misuse of Kubernetes Secrets by unusual user names. It leverages Kubernetes Audit logs to identify anomalies in access patterns by analyzing the source of requests based on user names. This activity is significant for a SOC as Kubernetes Secrets store sensitive information like passwords, OAuth tokens, and SSH keys, making them critical assets. If confirmed malicious, this activity could lead to unauthorized access to sensitive systems or data, potentially resulting in significant security breaches and exfiltration of sensitive information.
data_source:
- Kubernetes Audit
search: |-
`kube_audit` objectRef.resource=secrets verb=get
| search NOT `kube_allowed_user_names`
| fillnull
| stats count
BY objectRef.name objectRef.namespace objectRef.resource
requestReceivedTimestamp requestURI responseStatus.code
sourceIPs{} stage user.groups{}
user.uid user.username userAgent
verb
| rename sourceIPs{} as src_ip, user.username as user
| `kubernetes_abuse_of_secret_by_unusual_user_name_filter`
how_to_implement: The detection is based on data that originates from Kubernetes Audit logs. Ensure that audit logging is enabled in your Kubernetes cluster. Kubernetes audit logs provide a record of the requests made to the Kubernetes API server, which is crucial for monitoring and detecting suspicious activities. Configure the audit policy in Kubernetes to determine what kind of activities are logged. This is done by creating an Audit Policy and providing it to the API server. Use the Splunk OpenTelemetry Collector for Kubernetes to collect the logs. This doc will describe how to collect the audit log file https://github.com/signalfx/splunk-otel-collector-chart/blob/main/docs/migration-from-sck.md. When you want to use this detection with AWS EKS, you need to enable EKS control plane logging https://docs.aws.amazon.com/eks/latest/userguide/control-plane-logs.html. Then you can collect the logs from Cloudwatch using the AWS TA https://splunk.github.io/splunk-add-on-for-amazon-web-services/CloudWatchLogs/.
known_false_positives: No false positives have been identified at this time.
references:
- https://kubernetes.io/docs/tasks/debug/debug-cluster/audit/
intermediate_findings:
entities:
- field: user
type: user
score: 20
message: Access of Kubernetes secret $objectRef.name$ from unusual user name $user$
threat_objects:
- field: src_ip
type: ip_address
analytic_story:
- Kubernetes Security
asset_type: Kubernetes
mitre_attack_id:
- T1552.007
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: cloud
security_domain: network
Stages and Predicates
Stage 1: search
`kube_audit` objectRef.resource=secrets verb=get
Stage 2: search
| search NOT `kube_allowed_user_names`
Stage 3: fillnull
| fillnull
Stage 4: stats
| stats count
BY objectRef.name objectRef.namespace objectRef.resource
requestReceivedTimestamp requestURI responseStatus.code
sourceIPs{} stage user.groups{}
user.uid user.username userAgent
verb
Stage 5: rename
| rename sourceIPs{} as src_ip, user.username as user
Stage 6: search
| `kubernetes_abuse_of_secret_by_unusual_user_name_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
objectRef.resource | eq |
| field:"objectRef.resource" kind:eq value:"secrets" |
verb | eq |
| field:"verb" kind:eq value:"get" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
user.username | eq | admin | excludes:user.username field:"user.username" value:"admin" |
Linux Auditd Unix Shell Configuration Modification
#The following analytic detects suspicious access or modifications to Unix shell configuration files, which may indicate an attempt to alter system behavior or gain unauthorized access. Unix shell configuration files, such as .bashrc or .profile, control user environment settings and command execution. Unauthorized changes to these files can be used to execute malicious commands, escalate privileges, or hide malicious activities. By monitoring for unusual or unauthorized modifications to shell configuration files, this analytic helps identify potential security threats, allowing security teams to respond quickly and mitigate risks. Correlate this with related EXECVE or PROCTITLE events to identify the process or user responsible for the access or modification.
Known False Positives
- Administrator or network operator can use this application for automation purposes. Please update the filter macros to remove false positives.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation |
Telemetry Coverage
| Platform | Record / event type |
|---|---|
| Linux | auditd PATH record: Filename path information |
| Linux | auditd CWD record: Current working directory |
Rule Body
name: Linux Auditd Unix Shell Configuration Modification
id: 66f737c6-3f7f-46ed-8e9b-cc0e5bf01f04
version: 11
creation_date: '2024-08-22'
modification_date: '2026-05-13'
author: Teoderick Contreras, Splunk
status: production
type: TTP
description: |
The following analytic detects suspicious access or modifications to Unix shell configuration files, which may indicate an attempt to alter system behavior or gain unauthorized access.
Unix shell configuration files, such as `.bashrc` or `.profile`, control user environment settings and command execution.
Unauthorized changes to these files can be used to execute malicious commands, escalate privileges, or hide malicious activities.
By monitoring for unusual or unauthorized modifications to shell configuration files, this analytic helps identify potential security threats, allowing security teams to respond quickly and mitigate risks.
Correlate this with related EXECVE or PROCTITLE events to identify the process or user responsible for the access or modification.
data_source:
- Linux Auditd Path
- Linux Auditd Cwd
search: |
`linux_auditd`
(type=PATH OR type=CWD)
| rex "msg=audit\([^)]*:(?<audit_id>\d+)\)"
| stats
values(type) as types
values(name) as names
values(nametype) as nametype
values(cwd) as cwd_list
values(_time) as event_times
by audit_id, host
| eval current_working_directory = coalesce(mvindex(cwd_list, 0), "N/A")
| eval candidate_paths = mvmap(names, if(match(names, "^/"), names, current_working_directory + "/" + names))
| eval matched_paths = mvfilter(match(candidate_paths, "/etc/profile|/etc/shells|/etc/profile\\.d/.*|/etc/bash\\.bashrc.*|/etc/bashrc|.*/zsh/zprofile|.*/zsh/zshrc|.*/zsh/zlogin|.*/zsh/zlogout|/etc/csh\\.cshrc.*|/etc/csh\\.login.*|/root/\\.bashrc.*|/root/\\.bash_profile.*|/root/\\.profile.*|/root/\\.zshrc.*|/root/\\.zprofile.*|/home/.*/\\.bashrc.*|/home/.*/\\.zshrc.*|/home/.*/\\.bash_profile.*|/home/.*/\\.zprofile.*|/home/.*/\\.profile.*|/home/.*/\\.bash_login.*|/home/.*/\\.bash_logout.*|/home/.*/\\.zlogin.*|/home/.*/\\.zlogout.*"))
| eval match_count = mvcount(matched_paths)
| eval reconstructed_path = mvindex(matched_paths, 0)
| eval e_time = mvindex(event_times, 0)
| where match_count > 0
| rename host as dest
| stats count min(e_time) as firstTime max(e_time) as lastTime
values(nametype) as nametype
by current_working_directory
reconstructed_path
match_count
dest
audit_id
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `linux_auditd_unix_shell_configuration_modification_filter`
how_to_implement: |
To implement this detection, the process begins by ingesting auditd
data, that consist SYSCALL, TYPE, EXECVE and PROCTITLE events, which captures command-line
executions and process details on Unix/Linux systems. These logs should be ingested
and processed using Splunk Add-on for Unix and Linux (https://splunkbase.splunk.com/app/833),
which is essential for correctly parsing and categorizing the data. The next step
involves normalizing the field names to match the field names set by the Splunk
Common Information Model (CIM) to ensure consistency across different data sources
and enhance the efficiency of data modeling and make sure the type=CWD record type is activate in your auditd configuration.
This approach enables effective monitoring and detection of linux endpoints where auditd is deployed.
known_false_positives: |
Administrator or network operator can use this application for automation purposes.
Please update the filter macros to remove false positives.
references:
- https://www.splunk.com/en_us/blog/security/deep-dive-on-persistence-privilege-escalation-technique-and-detection-in-linux-platform.html
- https://github.com/peass-ng/PEASS-ng/tree/master/linPEAS
finding:
title: A [$nametype$] event occurred on host - [$dest$] to modify the unix shell configuration file.
entity:
field: dest
type: system
score: 50
analytic_story:
- Linux Living Off The Land
- Linux Privilege Escalation
- Linux Persistence Techniques
- Compromised Linux Host
- QuietVault
asset_type: Endpoint
mitre_attack_id:
- T1546.004
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`linux_auditd`
(type=PATH OR type=CWD)
Stage 2: rex
| rex "msg=audit\([^)]*:(?<audit_id>\d+)\)"
Stage 3: stats
| stats
values(type) as types
values(name) as names
values(nametype) as nametype
values(cwd) as cwd_list
values(_time) as event_times
by audit_id, host
Stage 4: eval
| eval current_working_directory = coalesce(mvindex(cwd_list, 0), "N/A")
Stage 5: eval
| eval
candidate_paths = mvmap(
names,
if(match(names, "^/"), names, current_working_directory + "/" + names)
)
Stage 6: eval
| eval
matched_paths = mvfilter(
match(
candidate_paths,
"/etc/profile|/etc/shells|/etc/profile\\.d/.*|/etc/bash\\.bashrc.*|/etc/bashrc|.*/zsh/zprofile|.*/zsh/zshrc|.*/zsh/zlogin|.*/zsh/zlogout|/etc/csh\\.cshrc.*|/etc/csh\\.login.*|/root/\\.bashrc.*|/root/\\.bash_profile.*|/root/\\.profile.*|/root/\\.zshrc.*|/root/\\.zprofile.*|/home/.*/\\.bashrc.*|/home/.*/\\.zshrc.*|/home/.*/\\.bash_profile.*|/home/.*/\\.zprofile.*|/home/.*/\\.profile.*|/home/.*/\\.bash_login.*|/home/.*/\\.bash_logout.*|/home/.*/\\.zlogin.*|/home/.*/\\.zlogout.*"
)
)
Stage 7: eval
| eval match_count = mvcount(matched_paths)
Stage 8: eval
| eval reconstructed_path = mvindex(matched_paths, 0)
Stage 9: eval
| eval e_time = mvindex(event_times, 0)
Stage 10: where
| where match_count > 0
Stage 11: rename
| rename host as dest
Stage 12: stats
| stats count min(e_time) as firstTime max(e_time) as lastTime
values(nametype) as nametype
by current_working_directory
reconstructed_path
match_count
dest
audit_id
Stage 13: search
| `security_content_ctime(firstTime)`
Stage 14: search
| `security_content_ctime(lastTime)`
Stage 15: search
| `linux_auditd_unix_shell_configuration_modification_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
match_count | gt |
| field:"match_count" kind:gt value:"0" |
sourcetype | eq |
| field:"sourcetype" kind:eq value:"auditd" |
type | eq |
| field:"type" kind:eq |
Linux Possible Access To Sudoers File
#The following analytic detects potential access or modification of the /etc/sudoers file on a Linux system. It leverages data from Endpoint Detection and Response (EDR) agents, focusing on processes like "cat," "nano," "vim," and "vi" accessing the /etc/sudoers file. This activity is significant because the sudoers file controls user permissions for executing commands with elevated privileges. If confirmed malicious, an attacker could gain persistence or escalate privileges, compromising the security of the targeted host.
Known False Positives
- administrator or network operator can execute this command. Please update the filter macros to remove false positives.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation |
Telemetry Coverage
| Platform | Record / event type |
|---|---|
| Linux | Event ID 1: Process Create |
Rule Body
name: Linux Possible Access To Sudoers File
id: 4479539c-71fc-11ec-b2e2-acde48001122
version: 13
creation_date: '2022-01-10'
modification_date: '2026-05-13'
author: Teoderick Contreras, Splunk
status: production
type: Anomaly
description: The following analytic detects potential access or modification of the /etc/sudoers file on a Linux system. It leverages data from Endpoint Detection and Response (EDR) agents, focusing on processes like "cat," "nano," "vim," and "vi" accessing the /etc/sudoers file. This activity is significant because the sudoers file controls user permissions for executing commands with elevated privileges. If confirmed malicious, an attacker could gain persistence or escalate privileges, compromising the security of the targeted host.
data_source:
- Sysmon for Linux EventID 1
search: |-
| tstats `security_content_summariesonly` count min(_time) as firstTime max(_time) as lastTime FROM datamodel=Endpoint.Processes
WHERE Processes.process_name IN("cat", "nano*","vim*", "vi*")
AND
Processes.process IN("*/etc/sudoers*")
BY Processes.action Processes.dest Processes.original_file_name
Processes.parent_process Processes.parent_process_exec Processes.parent_process_guid
Processes.parent_process_id Processes.parent_process_name Processes.parent_process_path
Processes.process Processes.process_exec Processes.process_guid
Processes.process_hash Processes.process_id Processes.process_integrity_level
Processes.process_name Processes.process_path Processes.user
Processes.user_id Processes.vendor_product
| `drop_dm_object_name(Processes)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `linux_possible_access_to_sudoers_file_filter`
how_to_implement: The detection is based on data that originates from Endpoint Detection and Response (EDR) agents. These agents are designed to provide security-related telemetry from the endpoints where the agent is installed. To implement this search, you must ingest logs that contain the process GUID, process name, and parent process. Additionally, you must ingest complete command-line executions. These logs must be processed using the appropriate Splunk Technology Add-ons that are specific to the EDR product. The logs must also be mapped to the `Processes` node of the `Endpoint` data model. Use the Splunk Common Information Model (CIM) to normalize the field names and speed up the data modeling process.
known_false_positives: administrator or network operator can execute this command. Please update the filter macros to remove false positives.
references:
- https://attack.mitre.org/techniques/T1548/003/
- https://web.archive.org/web/20210708035426/https://www.cobaltstrike.com/downloads/csmanual43.pdf
intermediate_findings:
entities:
- field: dest
type: system
score: 20
message: A commandline $process$ executed on $dest$
analytic_story:
- Linux Persistence Techniques
- China-Nexus Threat Activity
- Salt Typhoon
- Linux Privilege Escalation
asset_type: Endpoint
mitre_attack_id:
- T1548.003
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: tstats
| tstats `security_content_summariesonly`
count
min(_time) as firstTime
max(_time) as lastTime
FROM datamodel=Endpoint.Processes
WHERE Processes.process_name IN("cat", "nano*","vim*", "vi*")
AND
Processes.process IN("*/etc/sudoers*")
BY
Processes.action
Processes.dest
Processes.original_file_name
Processes.parent_process
Processes.parent_process_exec
Processes.parent_process_guid
Processes.parent_process_id
Processes.parent_process_name
Processes.parent_process_path
Processes.process
Processes.process_exec
Processes.process_guid
Processes.process_hash
Processes.process_id
Processes.process_integrity_level
Processes.process_name
Processes.process_path
Processes.user
Processes.user_id
Processes.vendor_product
Stage 2: search
| `drop_dm_object_name(Processes)`
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: search
| `linux_possible_access_to_sudoers_file_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
Processes.process | in |
| field:"CommandLine" kind:in value:"*/etc/sudoers*" |
Processes.process_name | in |
| field:"process_basename" kind:in |
Log4Shell JNDI Payload Injection with Outbound Connection
#The following analytic detects Log4Shell JNDI payload injections via outbound connections. It identifies suspicious LDAP lookup functions in web logs, such as ${jndi:ldap://PAYLOAD_INJECTED}, and correlates them with network traffic to known malicious IP addresses. This detection leverages the Web and Network_Traffic data models in Splunk. Monitoring this activity is crucial as it targets vulnerabilities in Java web applications using log4j, potentially leading to remote code execution. If confirmed malicious, attackers could gain unauthorized access, execute arbitrary code, and compromise sensitive data within the affected environment.
Known False Positives
- If there is a vulnerablility scannner looking for log4shells this will trigger, otherwise likely to have low false positives.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Persistence |
Rule Body
name: Log4Shell JNDI Payload Injection with Outbound Connection
id: 69afee44-5c91-11ec-bf1f-497c9a704a72
version: 9
creation_date: '2021-12-13'
modification_date: '2026-05-13'
author: Jose Hernandez
status: production
type: Anomaly
description: The following analytic detects Log4Shell JNDI payload injections via outbound connections. It identifies suspicious LDAP lookup functions in web logs, such as `${jndi:ldap://PAYLOAD_INJECTED}`, and correlates them with network traffic to known malicious IP addresses. This detection leverages the Web and Network_Traffic data models in Splunk. Monitoring this activity is crucial as it targets vulnerabilities in Java web applications using log4j, potentially leading to remote code execution. If confirmed malicious, attackers could gain unauthorized access, execute arbitrary code, and compromise sensitive data within the affected environment.
data_source: []
search: |-
| from datamodel Web.Web
| rex field=_raw max_match=0 "[jJnNdDiI]{4}(\:|\%3A|\/|\%2F)(?<proto>\w+)(\:\/\/|\%3A\%2F\%2F)(\$\{.*?\}(\.)?)?(?<affected_host>[a-zA-Z0-9\.\-\_\$]+)" | join affected_host type=inner [| tstats `security_content_summariesonly` count min(_time) as firstTime max(_time) as lastTime from datamodel=Network_Traffic.All_Traffic by All_Traffic.dest | `drop_dm_object_name(All_Traffic)` | `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)` | rename dest AS affected_host]
| fillnull
| stats count by action, category, dest, dest_port, http_content_type, http_method, http_referrer, http_user_agent, site, src, url, url_domain, user
| `log4shell_jndi_payload_injection_with_outbound_connection_filter`
how_to_implement: This detection requires the Web datamodel to be populated from a supported Technology Add-On like Splunk for Apache or Splunk for Nginx.
known_false_positives: If there is a vulnerablility scannner looking for log4shells this will trigger, otherwise likely to have low false positives.
references:
- https://www.lunasec.io/docs/blog/log4j-zero-day/
intermediate_findings:
entities:
- field: user
type: user
score: 20
message: CVE-2021-44228 Log4Shell triggered for host $dest$
- field: dest
type: system
score: 20
message: CVE-2021-44228 Log4Shell triggered for host $dest$
analytic_story:
- Log4Shell CVE-2021-44228
- CISA AA22-320A
asset_type: Endpoint
cve:
- CVE-2021-44228
mitre_attack_id:
- T1190
- T1133
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: web
security_domain: threat
Stages and Predicates
Stage 1: search
| from datamodel Web.Web
Stage 2: rex
| rex field=_raw max_match=0
"[jJnNdDiI]{4}(\:|\%3A|\/|\%2F)(?<proto>\w+)(\:\/\/|\%3A\%2F\%2F)(\$\{.*?\}(\.)?)?(?<affected_host>[a-zA-Z0-9\.\-\_\$]+)"
Stage 3: join
| join affected_host type=inner
[
| tstats `security_content_summariesonly`
count
min(_time) as firstTime
max(_time) as lastTime
from datamodel=Network_Traffic.All_Traffic
by All_Traffic.dest
| `drop_dm_object_name(All_Traffic)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| rename dest AS affected_host
]
Stage 4: fillnull
| fillnull
Stage 5: stats
| stats
count
by
action,
category,
dest,
dest_port,
http_content_type,
http_method,
http_referrer,
http_user_agent,
site,
src,
url,
url_domain,
user
Stage 6: search
| `log4shell_jndi_payload_injection_with_outbound_connection_filter`
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | from |
| 1 | datamodel |
| 1 | Web.Web |
LSASS Handle request (Windows Event Log)
#Adversaries may attempt to access credential material stored in the process memory of the Local Security Authority Subsystem Service (LSASS). This use case looks for lsass handle calls, without requiring process execution events as an additional identifier in order to detect those executions which may have been injected into a process
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Credential Access |
References
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Security-Auditing | Event ID 4656: A handle to an object was requested. |
Rule Body
id: '6130.6618'
title: LSASS Handle request
description: 'Adversaries may attempt to access credential material stored in the
process memory of the Local Security Authority Subsystem Service (LSASS). This use
case looks for lsass handle calls, without requiring process execution events as
an additional identifier in order to detect those executions which may have been
injected into a process. -- Software Association: Quantum -- Atomics T1003.002 Test
#4'
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_winevent` ((TERM(EventCode=4656) OR
"<EventID>4656<") "lsass.exe" TERM(Read) TERM(from) TERM(process) TERM(memory))
| eval Source_Process_ID=if(like(Source_Process_ID,"%x%"),tonumber(Source_Process_ID,16),Source_Process_ID)|
eval process_id=mvappend(process_id, Source_Process_ID) | table _time, host, user
signature_id, user, process_* | bin span=6s | stats values(*) as * by _time, host,
user | eventstats c(process_name) as c_process by process_name| where c_process
< 50 and event_count < 10 '
techniques:
- credential-access:os credential dumping:lsass memory
technique_id:
- T1003.001
data_category:
- Windows event logs
references:
- https://www.ired.team/offensive-security/credential-access-and-credential-dumping/dumping-lsass-passwords-without-mimikatz-minidumpwritedump-av-signature-bypass
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_winevent` ((TERM(EventCode=4656) OR "<EventID>4656<") "lsass.exe" TERM(Read) TERM(from) TERM(process) TERM(memory))
Stage 2: eval
| eval
Source_Process_ID=if(
like(Source_Process_ID,"%x%"),
tonumber(Source_Process_ID,16),
Source_Process_ID
)
Stage 3: eval
| eval process_id=mvappend(process_id, Source_Process_ID)
Stage 4: table
| table _time, host, user signature_id, user, process_*
Stage 5: bucket
| bin span=6s
Stage 6: stats
| stats values(*) as * by _time, host, user
Stage 7: eventstats
| eventstats c(process_name) as c_process by process_name
Stage 8: where
| where c_process < 50 and event_count < 10
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"4656" |
c_process | lt |
| field:"c_process" kind:lt value:"50" |
event_count | lt |
| field:"event_count" kind:lt value:"10" |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>4656<" |
| 1 | "lsass.exe" |
| 1 | Read |
| 1 | from |
| 1 | process |
| 1 | memory |
Possible Credential Dumping via Windows Network Providers (Windows Event Log)
#A Network Provider is a Windows component that facilitates the connection, communication, and resource sharing between a system and a network. Threat actors can create a rogue Network Provider to capture or "dump" credentials by intercepting and logging network authentication requests, such as NPPSpy. This use case detects modifications to registry values for Network Providers
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Defense Impairment | |
| Credential Access |
References
- https://www.socinvestigation.com/credential-dumping-using-windows-network-providers-how-to-respond/
- https://www.paloaltonetworks.com/blog/security-operations/through-the-cortex-xdr-lens-uncovering-a-new-activity-group-targeting-governments-in-the-middle-east-and-africa/
- https://github.com/gtworek/PSBits/blob/master/PasswordStealing/NPPSpy/Get-NetworkProviders.ps1
Telemetry Coverage
Rule Body
id: '20390.36161'
title: Possible Credential Dumping via Windows Network Providers
description: 'A Network Provider is a Windows component that facilitates the connection,
communication, and resource sharing between a system and a network. Threat actors
can create a rogue Network Provider to capture or "dump" credentials by intercepting
and logging network authentication requests, such as NPPSpy. This use case detects
modifications to registry values for Network Providers. Atomics T1003 Test #2'
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_winevent` ((TERM(EventCode=4688) OR
"<EventID>4688<" OR Type=Process ((TERM(reg) OR "reg.exe") TERM(add)) OR TERM(EventCode=4657)
OR "<EventID>4657<")) ("SYSTEM\\CurrentControlSet\\Services" "NetworkProvider")
OR "SYSTEM\\CurrentControlSet\\Control\\NetworkProvider\\Order" | table _time, host,
user, process, process_*, parent_process_* | bin span=1s | stats values(*) as *
by _time, host '
techniques:
- defense-evasion:modify registry
- credential-access:os credential dumping
technique_id:
- T1112
- T1003
data_category:
- Process command-line parameters
- Windows event logs
references:
- https://www.socinvestigation.com/credential-dumping-using-windows-network-providers-how-to-respond/
- https://www.paloaltonetworks.com/blog/security-operations/through-the-cortex-xdr-lens-uncovering-a-new-activity-group-targeting-governments-in-the-middle-east-and-africa/
- https://github.com/gtworek/PSBits/blob/master/PasswordStealing/NPPSpy/Get-NetworkProviders.ps1
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_winevent` ((TERM(EventCode=4688) OR "<EventID>4688<" OR Type=Process ((TERM(reg) OR "reg.exe") TERM(add)) OR TERM(EventCode=4657) OR "<EventID>4657<")) ("SYSTEM\\CurrentControlSet\\Services" "NetworkProvider") OR "SYSTEM\\CurrentControlSet\\Control\\NetworkProvider\\Order"
Stage 2: table
| table _time, host, user, process, process_*, parent_process_*
Stage 3: bucket
| bin span=1s
Stage 4: stats
| stats values(*) as * by _time, host
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>4688<" |
| 1 | reg |
| 1 | "reg.exe" |
| 1 | add |
| 1 | "<EventID>4657<" |
| 1 | "SYSTEM\\CurrentControlSet\\Services" |
| 1 | "NetworkProvider" |
| 1 | "SYSTEM\\CurrentControlSet\\Control\\NetworkProvider\\Order" |
RDP Hijacking (Windows Event Log)
#Adversaries may hijack a legitimate user’s remote desktop session to move laterally within an environment. Remote desktop is a common feature in operating systems. It allows a user to log into an interactive session with a system desktop graphical user interface on a remote system. Microsoft refers to its implementation of the Remote Desktop Protocol (RDP) as Remote Desktop Services (RDS)
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Persistence | |
| Lateral Movement |
References
Telemetry Coverage
Rule Body
id: '5464.5627'
title: RDP Hijacking
description: 'Adversaries may hijack a legitimate user’s remote desktop session to
move laterally within an environment. Remote desktop is a common feature in operating
systems. It allows a user to log into an interactive session with a system desktop
graphical user interface on a remote system. Microsoft refers to its implementation
of the Remote Desktop Protocol (RDP) as Remote Desktop Services (RDS) - Threat Actor
Association: APT10, APT27, APT29/Nobelium/Cozy Bear, APT31, APT41, BlackMatter,
Carbanak, DarkSide, DragonFly, FIN6, Lazarus, Whisper Spider, Wizard Spider, UNC2628,
UNC2596 - Software Association: Bazarloader, BlackByte, BlackMatter, Conti, Cuba,
Dharma, Diavol, Lockbit, LV, Midas, PYSA/Mespinoza, Snatch'
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=4778) OR
"<EventID>4778<" OR TERM(EventCode=4779) OR "<EventID>4779<") OR (("rdpclip.exe"
OR "tstheme.exe") (TERM(EventCode=4688) OR "<EventID>4688<")) | table _time, host,
user, signature_id, src_ip, process, process_id, process_name, parent_process_name
`group_events("host",5m)`| eventstats dc(user) as users by user | where (match(signature_id,
"(?i)4778") AND match(signature_id, "(?i)4779") AND match(process_name, "(?i)rdpclip.exe")
AND match(process_name, "(?i)tstheme.exe")) AND users>=2 | lookup dnslookup clientip
as src_ip OUTPUT clienthost as src_dns | iplocation prefix="src_" src_ip| rename
src_Country as src_country '
techniques:
- initial-access:external remote services
- lateral-movement:remote service session hijacking:rdp hijacking
technique_id:
- T1133
- T1563.002
data_category:
- Windows event logs
references:
- https://www.hackingarticles.in/rdp-session-hijacking-with-tscon/
- https://www.ired.team/offensive-security/lateral-movement/t1076-rdp-hijacking-for-lateral-movement
Stages and Predicates
Stage 1: search
search ((EventCode=4778 EventCode=4779) OR EventCode=4688) source="*" source IN (
"WinEventLog:Security",
"XmlWinEventLog:Security"
)
Stage 2: table
table _time, host, parent_process_name, process, process_id, process_name, signature_id, src_ip,
user
Stage 3: bucket
bucket _time
Stage 4: stats
stats BY host, _time
Stage 5: eventstats
eventstats … AS users BY user
Stage 6: where
where match(process_name, "(?i)rdpclip.exe") match(process_name, "(?i)tstheme.exe") match(signature_id, "(?i)4778") match(signature_id, "(?i)4779") users>=2
Stage 7: lookup
lookup <lookup> clienthost, clientip, src_dns, src_ip
Stage 8: search
search prefix="src_"
Stage 9: rename
rename
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq |
prefix | eq |
| field:"prefix" kind:eq value:"src_" |
process_name | regex_match |
| field:"process_name" kind:regex_match |
signature_id | regex_match |
| field:"signature_id" kind:regex_match |
users | ge |
| field:"users" kind:ge value:"2" |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>4778<" |
| 1 | "<EventID>4779<" |
| 1 | "rdpclip.exe" |
| 1 | "tstheme.exe" |
| 1 | "<EventID>4688<" |
| 8 | iplocation |
| 8 | src_ip |
Shai-Hulud 2 Exfiltration Artifact Files
#Detects creation of exfiltration artifact files associated with Shai-Hulud 2.0 npm supply chain malware. The malware creates cloud.json, contents.json, environment.json, truffleSecrets.json, and actionsSecrets.json files containing harvested credentials from AWS, Azure, GCP, GitHub secrets, and environment variables. These files are staged before being pushed to attacker-controlled repositories.
Known False Positives
- Low but possible. Generic filenames like cloud.json or environment.json may appear in legitimate contexts. Correlate with npm install activity or suspicious parent processes.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Credential Access | |
| Collection |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 11: FileCreate |
| Linux | Event ID 11: File created |
Rule Body
name: Shai-Hulud 2 Exfiltration Artifact Files
id: 9e7d3c0f-4a5b-6c8d-1e2f-3a4b5c6d7e8f
version: 4
creation_date: '2025-11-25'
modification_date: '2026-05-13'
author: Michael Haag, Splunk
status: production
type: TTP
description: |
Detects creation of exfiltration artifact files associated with Shai-Hulud 2.0 npm supply
chain malware. The malware creates cloud.json, contents.json, environment.json, truffleSecrets.json,
and actionsSecrets.json files containing harvested credentials from AWS, Azure, GCP, GitHub secrets,
and environment variables. These files are staged before being pushed to attacker-controlled repositories.
data_source:
- Sysmon for Linux EventID 11
- Sysmon EventID 11
search: |
| tstats `security_content_summariesonly` count min(_time) as firstTime max(_time) as lastTime
from datamodel=Endpoint.Filesystem where
Filesystem.file_name IN (
"cloud.json",
"contents.json",
"environment.json",
"truffleSecrets.json",
"actionsSecrets.json"
)
by Filesystem.action Filesystem.dest Filesystem.file_access_time Filesystem.file_create_time
Filesystem.file_hash Filesystem.file_modify_time Filesystem.file_name Filesystem.file_path Filesystem.file_acl Filesystem.file_size Filesystem.process_guid Filesystem.process_id Filesystem.user
Filesystem.vendor_product
| `drop_dm_object_name(Filesystem)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `shai_hulud_2_exfiltration_artifact_files_filter`
how_to_implement: |
The detection is based on data that originates from Endpoint Detection
and Response (EDR) agents. These agents are designed to provide security-related
telemetry from the endpoints where the agent is installed. To implement this search,
you must ingest logs that contain filesystem events, specifically file creation
events. These logs must be processed using the appropriate Splunk Technology Add-ons
that are specific to the EDR product. The logs must also be mapped to the `Filesystem`
node of the `Endpoint` data model. Use the Splunk Common Information Model (CIM)
to normalize the field names and speed up the data modeling process.
known_false_positives: |
Low but possible. Generic filenames like cloud.json or environment.json may appear in legitimate contexts. Correlate with npm install activity or suspicious parent processes.
references:
- https://www.wiz.io/blog/shai-hulud-2-0-ongoing-supply-chain-attack
- https://securelist.com/shai-hulud-worm-infects-500-npm-packages-in-a-supply-chain-attack/117547/
finding:
title: Shai-Hulud 2.0 exfiltration artifact $file_name$ created on $dest$
entity:
field: dest
type: system
score: 50
threat_objects:
- field: file_name
type: file_name
analytic_story:
- NPM Supply Chain Compromise
asset_type: Endpoint
mitre_attack_id:
- T1074.001
- T1552.001
- T1195.002
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: tstats
| tstats `security_content_summariesonly`
count
min(_time) as firstTime
max(_time) as lastTime
from datamodel=Endpoint.Filesystem
where
Filesystem.file_name IN (
"cloud.json",
"contents.json",
"environment.json",
"truffleSecrets.json",
"actionsSecrets.json"
)
by
Filesystem.action
Filesystem.dest
Filesystem.file_access_time
Filesystem.file_create_time
Filesystem.file_hash
Filesystem.file_modify_time
Filesystem.file_name
Filesystem.file_path
Filesystem.file_acl
Filesystem.file_size
Filesystem.process_guid
Filesystem.process_id
Filesystem.user
Filesystem.vendor_product
Stage 2: search
| `drop_dm_object_name(Filesystem)`
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: search
| `shai_hulud_2_exfiltration_artifact_files_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
Filesystem.file_name | in |
| field:"file_name" kind:in |
Suspicious InprocServer32 Registry Modification (Sysmon)
#The Windows Disk Cleanup utility is a legacy tool designed to delete cache and temporary files to improve system performance and free up hard disk space. Threat actors may insert a malicious DLL path into the registry key for the Disk Cleanup Scheduled Task, ensuring that their code is executed whenever Disk Cleanup runs, thus maintaining persistence on the compromised system without immediate detection. This use case detects commands to edit Disk Cleanup registry keys to include DLLs
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation |
References
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
| Sysmon | Event ID 13: RegistryEvent (Value Set) |
Rule Body
id: '28655.52127'
title: Suspicious InprocServer32 Registry Modification
description: The Windows Disk Cleanup utility is a legacy tool designed to delete
cache and temporary files to improve system performance and free up hard disk space.
Threat actors may insert a malicious DLL path into the registry key for the Disk
Cleanup Scheduled Task, ensuring that their code is executed whenever Disk Cleanup
runs, thus maintaining persistence on the compromised system without immediate detection.
This use case detects commands to edit Disk Cleanup registry keys to include DLLs.
Living Off the Land Binary and Scripts (LOLBAS) (LOLBIN)
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_sysmon` ((TERM(EventCode=1) OR "<EventID>1<")
(TERM(reg) OR "reg.exe") (TERM(add) "/t" "/d" "/v")) OR (TERM(EventCode=13) OR "<EventCode>13<")
"HKCU\\SOFTWARE\\Classes\\CLSID\\*\\InprocServer32" ".dll" | table _time, host,
user, parent_process_name, process_* | bin span=1s | stats values(*) as * by _time,
host '
techniques:
- persistence:event triggered execution:component object model hijacking
technique_id:
- T1546.015
data_category:
- Windows Sysmon
- Windows Registry
references:
- https://pentestlab.blog/2024/01/29/persistence-disk-clean-up/
- https://cocomelonc.github.io/persistence/2022/11/16/malware-pers-19.html
- https://www.hexacorn.com/blog/2018/09/02/beyond-good-ol-run-key-part-86/
Stages and Predicates
Stage 1: search
`get_endpoint_data` `get_endpoint_data_sysmon` ((TERM(EventCode=1) OR "<EventID>1<") (TERM(reg) OR "reg.exe") (TERM(add) "/t" "/d" "/v")) OR (TERM(EventCode=13) OR "<EventCode>13<") "HKCU\\SOFTWARE\\Classes\\CLSID\\*\\InprocServer32" ".dll"
Stage 2: table
| table _time, host, user, parent_process_name, process_*
Stage 3: bucket
| bin span=1s
Stage 4: stats
| stats values(*) as * by _time, host
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>1<" |
| 1 | reg |
| 1 | "reg.exe" |
| 1 | add |
| 1 | "/t" |
| 1 | "/d" |
| 1 | "/v" |
| 1 | "<EventCode>13<" |
| 1 | "HKCU\\SOFTWARE\\Classes\\CLSID\\*\\InprocServer32" |
| 1 | ".dll" |
Windows AD GPO Deleted
#This detection identifies when an Active Directory Group Policy is deleted using the Group Policy Management Console.
Known False Positives
- No false positives have been identified at this time.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation | |
| Defense Impairment |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Security-Auditing | Event ID 5136: A directory service object was modified. |
Rule Body
name: Windows AD GPO Deleted
id: 0d41772b-35ab-4e1c-a2ba-d0b455481aee
version: 12
creation_date: '2024-07-01'
modification_date: '2026-05-13'
author: Dean Luxton
status: production
type: TTP
description: This detection identifies when an Active Directory Group Policy is deleted using the Group Policy Management Console.
data_source:
- Windows Event Log Security 5136
search: |-
`wineventlog_security` EventCode=5136 AttributeLDAPDisplayName=gpLink
| eval ObjectDN=upper(ObjectDN)
| stats min(_time) as eventTime values(eval(if(OperationType=="%%14675",AttributeValue,null))) as old_value values(eval(if(OperationType=="%%14674",AttributeValue,null))) as new_value values(OperationType) as OperationType values(src_user) as src_user values(dest) as dest
BY OpCorrelationID ObjectDN SubjectLogonId
| rex field=old_value max_match=10000 "(?i)LDAP://(?P<old_dn>cn.*?);(?P<old_flag>\d)\]"
| rex field=new_value max_match=10000 "(?i)LDAP://(?P<new_dn>cn.*?);(?P<new_flag>\d)\]"
| mvexpand old_dn
| where NOT old_dn IN (new_dn)
| eval ObjectDN=upper(old_dn)
| join ObjectDN type=outer [
| search `admon` objectCategory="CN=Group-Policy-Container*" admonEventType=Update
| eval ObjectDN=upper(distinguishedName)
| stats latest(displayName) as displayName
BY ObjectDN ]
| stats min(eventTime) as _time values(OpCorrelationID) as OpCorrelationID values(displayName) as policyName values(src_user) as src_user
BY ObjectDN SubjectLogonId
| `windows_ad_gpo_deleted_filter`
how_to_implement: Ensure you are ingesting Active Directory audit logs - specifically event 5136, admon data is also used to display the display name of the GPO. See lantern article in references for further on how to onboard AD audit data. Ensure the wineventlog_security and admon macros are configured with the correct indexes.
known_false_positives: No false positives have been identified at this time.
references:
- https://lantern.splunk.com/Security/Product_Tips/Enterprise_Security/Enabling_an_audit_trail_from_Active_Directory
finding:
title: GPO $policyName$ was deleted by $src_user$
entity:
field: src_user
type: user
score: 50
analytic_story:
- Sneaky Active Directory Persistence Tricks
asset_type: Endpoint
mitre_attack_id:
- T1685
- T1484.001
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`wineventlog_security` EventCode=5136 AttributeLDAPDisplayName=gpLink
Stage 2: eval
| eval ObjectDN=upper(ObjectDN)
Stage 3: stats
| stats
min(_time) as eventTime
values(eval(if(OperationType=="%%14675",AttributeValue,null))) as old_value
values(eval(if(OperationType=="%%14674",AttributeValue,null))) as new_value
values(OperationType) as OperationType
values(src_user) as src_user
values(dest) as dest
BY OpCorrelationID ObjectDN SubjectLogonId
Stage 4: rex
| rex field=old_value max_match=10000 "(?i)LDAP://(?P<old_dn>cn.*?);(?P<old_flag>\d)\]"
Stage 5: rex
| rex field=new_value max_match=10000 "(?i)LDAP://(?P<new_dn>cn.*?);(?P<new_flag>\d)\]"
Stage 6: mvexpand
| mvexpand old_dn
Stage 7: where
| where NOT old_dn IN (new_dn)
Stage 8: eval
| eval ObjectDN=upper(old_dn)
Stage 9: join
| join ObjectDN type=outer [
| search `admon` objectCategory="CN=Group-Policy-Container*" admonEventType=Update
| eval ObjectDN=upper(distinguishedName)
| stats latest(displayName) as displayName
BY ObjectDN ]
Stage 10: stats
| stats
min(eventTime) as _time
values(OpCorrelationID) as OpCorrelationID
values(displayName) as policyName
values(src_user) as src_user
BY ObjectDN SubjectLogonId
Stage 11: search
| `windows_ad_gpo_deleted_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
AttributeLDAPDisplayName | eq |
| field:"AttributeLDAPDisplayName" kind:eq value:"gpLink" |
EventCode | eq |
| field:"EventID" kind:eq value:"5136" |
admonEventType | eq |
| field:"admonEventType" kind:eq value:"Update" |
objectCategory | eq |
| field:"objectCategory" kind:eq value:"CN=Group-Policy-Container*" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
old_dn | eq | new_dn | excludes:old_dn field:"old_dn" value:"new_dn" |
Windows Filtering Platform Filter Added To Block EDR Process
#The following analytic detects Windows Filtering Platform filters that are added and configured to block outbound traffic for known EDR and security agent processes. Tools such as EDRSilencer abuse WFP to disrupt outbound telemetry from EDR processes, which can bypass detections that only look for the tool process name. This detection looks for WFP add events with a block action and EDR process names embedded in the hexdump-like Conditions field.
Known False Positives
- Legitimate firewall, VPN, EDR, and Group Policy changes can add WFP block filters. Tune by approved ProviderName, LayerName, FilterName, or known administrative windows after validating the WFP filter context.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Defense Impairment |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Security-Auditing | Event ID 5447: A Windows Filtering Platform filter has been changed. |
Rule Body
name: Windows Filtering Platform Filter Added To Block EDR Process
id: 8bb64b2a-299e-4ddc-a7e1-037bdc5b904a
version: 1
creation_date: '2026-08-23'
modification_date: '2026-08-23'
author: Nasreddine Bencherchali, Splunk
status: production
type: TTP
description: |-
The following analytic detects Windows Filtering Platform filters that are added and configured to block outbound traffic for known EDR and security agent processes.
Tools such as EDRSilencer abuse WFP to disrupt outbound telemetry from EDR processes, which can bypass detections that only look for the tool process name.
This detection looks for WFP add events with a block action and EDR process names embedded in the hexdump-like Conditions field.
data_source:
- Windows Event Log Security 5447
search: |-
`wineventlog_security`
EventCode=5447
ChangeType IN ("%%16384", "Add")
Action IN ("%%16389", "Block")
Conditions=*
| eval conditions_text=coalesce(Conditions,"")
| rex mode=sed field=conditions_text "s/-/ /g"
| rex mode=sed field=conditions_text "s/[0-9A-Fa-f]{8}\s+([0-9A-Fa-f]{2}\s+){1,16}//g"
| eval conditions_normalized=lower(replace(conditions_text, "[^A-Za-z0-9]", ""))
| eval edr_process=case(
like(conditions_normalized, "%msmpengexe%"), "MsMpEng.exe",
like(conditions_normalized, "%mssenseexe%"), "MsSense.exe",
like(conditions_normalized, "%senseirexe%"), "SenseIR.exe",
like(conditions_normalized, "%sensendrexe%"), "SenseNdr.exe",
like(conditions_normalized, "%sensecncproxyexe%"), "SenseCncProxy.exe",
like(conditions_normalized, "%sensesampleuploaderexe%"), "SenseSampleUploader.exe",
like(conditions_normalized, "%winlogbeatexe%"), "winlogbeat.exe",
like(conditions_normalized, "%elasticagentexe%"), "elastic-agent.exe",
like(conditions_normalized, "%elasticendpointexe%"), "elastic-endpoint.exe",
like(conditions_normalized, "%filebeatexe%"), "filebeat.exe",
like(conditions_normalized, "%xagtexe%"), "xagt.exe",
like(conditions_normalized, "%qualysagentexe%"), "QualysAgent.exe",
like(conditions_normalized, "%sentinelagentexe%"), "SentinelAgent.exe",
like(conditions_normalized, "%sentinelagentworkerexe%"), "SentinelAgentWorker.exe",
like(conditions_normalized, "%sentinelservicehostexe%"), "SentinelServiceHost.exe",
like(conditions_normalized, "%sentinelstaticengineexe%"), "SentinelStaticEngine.exe",
like(conditions_normalized, "%logprocessorserviceexe%"), "LogProcessorService.exe",
like(conditions_normalized, "%sentinelstaticenginescannerexe%"), "SentinelStaticEngineScanner.exe",
like(conditions_normalized, "%sentinelhelperserviceexe%"), "SentinelHelperService.exe",
like(conditions_normalized, "%sentinelbrowsernativehostexe%"), "SentinelBrowserNativeHost.exe",
like(conditions_normalized, "%cylancesvcexe%"), "CylanceSvc.exe",
like(conditions_normalized, "%amsvcexe%"), "AmSvc.exe",
like(conditions_normalized, "%cramtrayexe%"), "CrAmTray.exe",
like(conditions_normalized, "%crssvcexe%"), "CrsSvc.exe",
like(conditions_normalized, "%executionpreventionsvcexe%"), "ExecutionPreventionSvc.exe",
like(conditions_normalized, "%cybereasonavexe%"), "CybereasonAV.exe",
like(conditions_normalized, "%cbexe%"), "cb.exe",
like(conditions_normalized, "%repmgrexe%"), "RepMgr.exe",
like(conditions_normalized, "%reputilsexe%"), "RepUtils.exe",
like(conditions_normalized, "%repuxexe%"), "RepUx.exe",
like(conditions_normalized, "%repwavexe%"), "RepWAV.exe",
like(conditions_normalized, "%repwscexe%"), "RepWSC.exe",
like(conditions_normalized, "%taniumclientexe%"), "TaniumClient.exe",
like(conditions_normalized, "%taniumcxexe%"), "TaniumCX.exe",
like(conditions_normalized, "%taniumdetectengineexe%"), "TaniumDetectEngine.exe",
like(conditions_normalized, "%trapsexe%"), "Traps.exe",
like(conditions_normalized, "%cyserverexe%"), "cyserver.exe",
like(conditions_normalized, "%cyveraserviceexe%"), "CyveraService.exe",
like(conditions_normalized, "%cyvrfsfltexe%"), "CyvrFsFlt.exe",
like(conditions_normalized, "%fortiedrexe%"), "fortiedr.exe",
like(conditions_normalized, "%sfcexe%"), "sfc.exe",
like(conditions_normalized, "%eiconnectorexe%"), "EIConnector.exe",
like(conditions_normalized, "%ekrnexe%"), "ekrn.exe",
like(conditions_normalized, "%hurukaiexe%"), "hurukai.exe",
like(conditions_normalized, "%cetasvcexe%"), "CETASvc.exe",
like(conditions_normalized, "%wscommunicatorexe%"), "WSCommunicator.exe",
like(conditions_normalized, "%endpointbasecampexe%"), "EndpointBasecamp.exe",
like(conditions_normalized, "%tmlistenexe%"), "TmListen.exe",
like(conditions_normalized, "%ntrtscanexe%"), "Ntrtscan.exe",
like(conditions_normalized, "%tmwscsvcexe%"), "TmWSCSvc.exe",
like(conditions_normalized, "%pccntmonexe%"), "PccNTMon.exe",
like(conditions_normalized, "%tmbmsrvexe%"), "TMBMSRV.exe",
like(conditions_normalized, "%cntaosmgrexe%"), "CNTAoSMgr.exe",
like(conditions_normalized, "%tmccsfexe%"), "TmCCSF.exe"
)
| where isnotnull(edr_process)
| eval user=coalesce(UserName,user,"unknown")
| eval filter_action=case(Action="%%16389","Block", true(), Action),
change_type=case(ChangeType="%%16384","Add", true(), ChangeType)
| stats count min(_time) as firstTime
max(_time) as lastTime
values(filter_action) as filter_action
values(change_type) as change_type
values(edr_process) as edr_process
values(ProviderName) as provider_name
values(FilterType) as filter_type
values(FilterId) as filter_id
values(LayerName) as layer_name
values(LayerId) as layer_id
values(Conditions) as conditions
values(CalloutName) as callout_name
BY dest user process_id FilterName
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `windows_filtering_platform_filter_added_to_block_edr_process_filter`
how_to_implement: |-
To implement this analytic, enable auditing for Windows Filtering Platform policy changes and ingest Windows Security Event Log data with EventCode 5447. The Splunk Add-on for Microsoft Windows should extract fields such as EventCode, ChangeType, FilterName, Conditions, and Action from XmlWinEventLog:Security events.
known_false_positives: |-
Legitimate firewall, VPN, EDR, and Group Policy changes can add WFP block filters.
Tune by approved ProviderName, LayerName, FilterName, or known administrative windows after validating the WFP filter context.
references:
- https://github.com/netero1010/EDRSilencer
- https://learn.microsoft.com/en-us/previous-versions/windows/it-pro/windows-10/security/threat-protection/auditing/event-5447
- https://learn.microsoft.com/en-us/windows/win32/fwp/auditing-and-logging
finding:
title: Windows Filtering Platform block filter targeting [$edr_process$] was detected on [$dest$].
entity:
field: dest
type: system
score: 50
threat_objects:
- field: edr_process
type: process_name
- field: FilterName
type: signature
analytic_story:
- Disabling Security Tools
- Security Solution Tampering
asset_type: Endpoint
mitre_attack_id:
- T1685
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`wineventlog_security`
EventCode=5447
ChangeType IN ("%%16384", "Add")
Action IN ("%%16389", "Block")
Conditions=*
Stage 2: eval
| eval conditions_text=coalesce(Conditions,"")
Stage 3: rex
| rex mode=sed field=conditions_text "s/-/ /g"
Stage 4: rex
| rex mode=sed field=conditions_text "s/[0-9A-Fa-f]{8}\s+([0-9A-Fa-f]{2}\s+){1,16}//g"
Stage 5: eval
| eval conditions_normalized=lower(replace(conditions_text, "[^A-Za-z0-9]", ""))
Stage 6: eval
| eval edr_process=case(
like(conditions_normalized, "%msmpengexe%"), "MsMpEng.exe",
like(conditions_normalized, "%mssenseexe%"), "MsSense.exe",
like(conditions_normalized, "%senseirexe%"), "SenseIR.exe",
like(conditions_normalized, "%sensendrexe%"), "SenseNdr.exe",
like(conditions_normalized, "%sensecncproxyexe%"), "SenseCncProxy.exe",
like(conditions_normalized, "%sensesampleuploaderexe%"), "SenseSampleUploader.exe",
like(conditions_normalized, "%winlogbeatexe%"), "winlogbeat.exe",
like(conditions_normalized, "%elasticagentexe%"), "elastic-agent.exe",
like(conditions_normalized, "%elasticendpointexe%"), "elastic-endpoint.exe",
like(conditions_normalized, "%filebeatexe%"), "filebeat.exe",
like(conditions_normalized, "%xagtexe%"), "xagt.exe",
like(conditions_normalized, "%qualysagentexe%"), "QualysAgent.exe",
like(conditions_normalized, "%sentinelagentexe%"), "SentinelAgent.exe",
like(conditions_normalized, "%sentinelagentworkerexe%"), "SentinelAgentWorker.exe",
like(conditions_normalized, "%sentinelservicehostexe%"), "SentinelServiceHost.exe",
like(conditions_normalized, "%sentinelstaticengineexe%"), "SentinelStaticEngine.exe",
like(conditions_normalized, "%logprocessorserviceexe%"), "LogProcessorService.exe",
like(conditions_normalized, "%sentinelstaticenginescannerexe%"),
"SentinelStaticEngineScanner.exe",
like(conditions_normalized, "%sentinelhelperserviceexe%"), "SentinelHelperService.exe",
like(conditions_normalized, "%sentinelbrowsernativehostexe%"), "SentinelBrowserNativeHost.exe",
like(conditions_normalized, "%cylancesvcexe%"), "CylanceSvc.exe",
like(conditions_normalized, "%amsvcexe%"), "AmSvc.exe",
like(conditions_normalized, "%cramtrayexe%"), "CrAmTray.exe",
like(conditions_normalized, "%crssvcexe%"), "CrsSvc.exe",
like(conditions_normalized, "%executionpreventionsvcexe%"), "ExecutionPreventionSvc.exe",
like(conditions_normalized, "%cybereasonavexe%"), "CybereasonAV.exe",
like(conditions_normalized, "%cbexe%"), "cb.exe",
like(conditions_normalized, "%repmgrexe%"), "RepMgr.exe",
like(conditions_normalized, "%reputilsexe%"), "RepUtils.exe",
like(conditions_normalized, "%repuxexe%"), "RepUx.exe",
like(conditions_normalized, "%repwavexe%"), "RepWAV.exe",
like(conditions_normalized, "%repwscexe%"), "RepWSC.exe",
like(conditions_normalized, "%taniumclientexe%"), "TaniumClient.exe",
like(conditions_normalized, "%taniumcxexe%"), "TaniumCX.exe",
like(conditions_normalized, "%taniumdetectengineexe%"), "TaniumDetectEngine.exe",
like(conditions_normalized, "%trapsexe%"), "Traps.exe",
like(conditions_normalized, "%cyserverexe%"), "cyserver.exe",
like(conditions_normalized, "%cyveraserviceexe%"), "CyveraService.exe",
like(conditions_normalized, "%cyvrfsfltexe%"), "CyvrFsFlt.exe",
like(conditions_normalized, "%fortiedrexe%"), "fortiedr.exe",
like(conditions_normalized, "%sfcexe%"), "sfc.exe",
like(conditions_normalized, "%eiconnectorexe%"), "EIConnector.exe",
like(conditions_normalized, "%ekrnexe%"), "ekrn.exe",
like(conditions_normalized, "%hurukaiexe%"), "hurukai.exe",
like(conditions_normalized, "%cetasvcexe%"), "CETASvc.exe",
like(conditions_normalized, "%wscommunicatorexe%"), "WSCommunicator.exe",
like(conditions_normalized, "%endpointbasecampexe%"), "EndpointBasecamp.exe",
like(conditions_normalized, "%tmlistenexe%"), "TmListen.exe",
like(conditions_normalized, "%ntrtscanexe%"), "Ntrtscan.exe",
like(conditions_normalized, "%tmwscsvcexe%"), "TmWSCSvc.exe",
like(conditions_normalized, "%pccntmonexe%"), "PccNTMon.exe",
like(conditions_normalized, "%tmbmsrvexe%"), "TMBMSRV.exe",
like(conditions_normalized, "%cntaosmgrexe%"), "CNTAoSMgr.exe",
like(conditions_normalized, "%tmccsfexe%"), "TmCCSF.exe"
)
edr_process =like(conditions_normalized, "%msmpengexe%")"MsMpEng.exe"like(conditions_normalized, "%mssenseexe%")"MsSense.exe"like(conditions_normalized, "%senseirexe%")"SenseIR.exe"like(conditions_normalized, "%sensendrexe%")"SenseNdr.exe"like(conditions_normalized, "%sensecncproxyexe%")"SenseCncProxy.exe"like(conditions_normalized, "%sensesampleuploaderexe%")"SenseSampleUploader.exe"like(conditions_normalized, "%winlogbeatexe%")"winlogbeat.exe"like(conditions_normalized, "%elasticagentexe%")"elastic-agent.exe"like(conditions_normalized, "%elasticendpointexe%")"elastic-endpoint.exe"like(conditions_normalized, "%filebeatexe%")"filebeat.exe"like(conditions_normalized, "%xagtexe%")"xagt.exe"like(conditions_normalized, "%qualysagentexe%")"QualysAgent.exe"like(conditions_normalized, "%sentinelagentexe%")"SentinelAgent.exe"like(conditions_normalized, "%sentinelagentworkerexe%")"SentinelAgentWorker.exe"like(conditions_normalized, "%sentinelservicehostexe%")"SentinelServiceHost.exe"like(conditions_normalized, "%sentinelstaticengineexe%")"SentinelStaticEngine.exe"like(conditions_normalized, "%logprocessorserviceexe%")"LogProcessorService.exe"like(conditions_normalized, "%sentinelstaticenginescannerexe%")"SentinelStaticEngineScanner.exe"like(conditions_normalized, "%sentinelhelperserviceexe%")"SentinelHelperService.exe"like(conditions_normalized, "%sentinelbrowsernativehostexe%")"SentinelBrowserNativeHost.exe"like(conditions_normalized, "%cylancesvcexe%")"CylanceSvc.exe"like(conditions_normalized, "%amsvcexe%")"AmSvc.exe"like(conditions_normalized, "%cramtrayexe%")"CrAmTray.exe"like(conditions_normalized, "%crssvcexe%")"CrsSvc.exe"like(conditions_normalized, "%executionpreventionsvcexe%")"ExecutionPreventionSvc.exe"like(conditions_normalized, "%cybereasonavexe%")"CybereasonAV.exe"like(conditions_normalized, "%cbexe%")"cb.exe"like(conditions_normalized, "%repmgrexe%")"RepMgr.exe"like(conditions_normalized, "%reputilsexe%")"RepUtils.exe"like(conditions_normalized, "%repuxexe%")"RepUx.exe"like(conditions_normalized, "%repwavexe%")"RepWAV.exe"like(conditions_normalized, "%repwscexe%")"RepWSC.exe"like(conditions_normalized, "%taniumclientexe%")"TaniumClient.exe"like(conditions_normalized, "%taniumcxexe%")"TaniumCX.exe"like(conditions_normalized, "%taniumdetectengineexe%")"TaniumDetectEngine.exe"like(conditions_normalized, "%trapsexe%")"Traps.exe"like(conditions_normalized, "%cyserverexe%")"cyserver.exe"like(conditions_normalized, "%cyveraserviceexe%")"CyveraService.exe"like(conditions_normalized, "%cyvrfsfltexe%")"CyvrFsFlt.exe"like(conditions_normalized, "%fortiedrexe%")"fortiedr.exe"like(conditions_normalized, "%sfcexe%")"sfc.exe"like(conditions_normalized, "%eiconnectorexe%")"EIConnector.exe"like(conditions_normalized, "%ekrnexe%")"ekrn.exe"like(conditions_normalized, "%hurukaiexe%")"hurukai.exe"like(conditions_normalized, "%cetasvcexe%")"CETASvc.exe"like(conditions_normalized, "%wscommunicatorexe%")"WSCommunicator.exe"like(conditions_normalized, "%endpointbasecampexe%")"EndpointBasecamp.exe"like(conditions_normalized, "%tmlistenexe%")"TmListen.exe"like(conditions_normalized, "%ntrtscanexe%")"Ntrtscan.exe"like(conditions_normalized, "%tmwscsvcexe%")"TmWSCSvc.exe"like(conditions_normalized, "%pccntmonexe%")"PccNTMon.exe"like(conditions_normalized, "%tmbmsrvexe%")"TMBMSRV.exe"like(conditions_normalized, "%cntaosmgrexe%")"CNTAoSMgr.exe""TmCCSF.exe"Stage 7: where
| where isnotnull(edr_process)
Stage 8: eval
| eval user=coalesce(UserName,user,"unknown")
Stage 9: eval
| eval filter_action=case(Action="%%16389","Block", true(), Action),
change_type=case(ChangeType="%%16384","Add", true(), ChangeType)
change_type =ChangeType = "%%16384""Add"ChangeTypefilter_action =Action = "%%16389""Block"ActionStage 10: stats
| stats count min(_time) as firstTime
max(_time) as lastTime
values(filter_action) as filter_action
values(change_type) as change_type
values(edr_process) as edr_process
values(ProviderName) as provider_name
values(FilterType) as filter_type
values(FilterId) as filter_id
values(LayerName) as layer_name
values(LayerId) as layer_id
values(Conditions) as conditions
values(CalloutName) as callout_name
BY dest user process_id FilterName
Stage 11: search
| `security_content_ctime(firstTime)`
Stage 12: search
| `security_content_ctime(lastTime)`
Stage 13: search
| `windows_filtering_platform_filter_added_to_block_edr_process_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
Action | in |
| field:"Action" kind:in |
ChangeType | in |
| field:"ChangeType" kind:in |
Conditions | eq |
| field:"Conditions" kind:eq value:"*" |
EventCode | eq |
| field:"EventID" kind:eq value:"5447" |
edr_process | is_not_null | field:"edr_process" kind:is_not_null |
Windows Handle Duplication in Known UAC-Bypass Binaries
#The following analytic detects suspicious handle duplication activity targeting known Windows utilities such as ComputerDefaults.exe, Eventvwr.exe, and others. This technique is commonly used to escalate privileges or bypass UAC by inheriting or injecting elevated tokens or handles. The detection focuses on non-standard use of DuplicateHandle or token duplication where process, thread, or token handles are copied into the context of trusted, signed utilities. Such behavior may indicate attempts to execute with elevated rights without user consent. Alerts enable rapid triage using process trees, handle data, token attributes, command-lines, and binary hashes.
Known False Positives
- It is possible legitimate applications will request access to list of know abused Windows UAC binaries process, filter as needed.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation | |
| Stealth |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 10: ProcessAccess |
Rule Body
name: Windows Handle Duplication in Known UAC-Bypass Binaries
id: d7369bf5-1315-4138-b927-2dd8bb8c1da7
version: 4
creation_date: '2025-11-07'
modification_date: '2026-05-13'
author: Teoderick Contreras, Splunk
status: production
type: Anomaly
description: The following analytic detects suspicious handle duplication activity targeting known Windows utilities such as ComputerDefaults.exe, Eventvwr.exe, and others. This technique is commonly used to escalate privileges or bypass UAC by inheriting or injecting elevated tokens or handles. The detection focuses on non-standard use of DuplicateHandle or token duplication where process, thread, or token handles are copied into the context of trusted, signed utilities. Such behavior may indicate attempts to execute with elevated rights without user consent. Alerts enable rapid triage using process trees, handle data, token attributes, command-lines, and binary hashes.
data_source:
- Sysmon EventID 10
search: '`sysmon` EventCode=10 TargetImage IN("*\\ComputerDefaults.exe", "*\\eventvwr.exe*", "*\\fodhelper.exe","*\\slui.exe","*\\sdclt.exe","*\\mmc.exe", "*\\colorcpl.exe","*\\wsreset.exe","*\\esentutl.exe", "*\PkgMgr.exe") AND NOT (SourceImage IN ("*C:\\Windows\\system32\\*","*C:\\Windows\\syswow64\\*","*C:\\Program Files\\*", "*C:\\Program Files (x86)\\*","%systemroot%\\*")) | eval g_access_decimal = tonumber(replace(GrantedAccess,"0x",""),16) | eval PROCESS_DUP_HANDLE = 64 | eval dup_handle_set = bit_and (g_access_decimal, PROCESS_DUP_HANDLE) | where dup_handle_set == PROCESS_DUP_HANDLE | stats count min(_time) as firstTime max(_time) as lastTime by SourceImage TargetImage GrantedAccess PROCESS_DUP_HANDLE g_access_decimal dup_handle_set Guid Opcode ProcessID SecurityID SourceProcessGUID SourceProcessId TargetProcessGUID TargetProcessId UserID dest granted_access parent_process_exec parent_process_guid parent_process_id parent_process_name parent_process_path process_exec process_guid process_id process_name process_path signature signature_id user_id vendor_product CallTrace EventID | `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)` | `windows_handle_duplication_in_known_uac_bypass_binaries_filter`'
how_to_implement: To successfully implement this search, you must be ingesting data that records process activity from your hosts to populate the endpoint data model in the processes node. If you are using Sysmon, you must have at least version 6.0.4 of the Sysmon TA.
known_false_positives: It is possible legitimate applications will request access to list of know abused Windows UAC binaries process, filter as needed.
references:
- https://www.recordedfuture.com/research/from-castleloader-to-castlerat-tag-150-advances-operations
intermediate_findings:
entities:
- field: dest
type: system
score: 20
message: A process $SourceImage$ is duplicating the handle token of $TargetImage$ on $dest$
threat_objects:
- field: parent_process_name
type: parent_process_name
analytic_story:
- Castle RAT
asset_type: Endpoint
mitre_attack_id:
- T1134.001
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`sysmon` EventCode=10 TargetImage IN(
"*\\ComputerDefaults.exe",
"*\\eventvwr.exe*",
"*\\fodhelper.exe",
"*\\slui.exe",
"*\\sdclt.exe",
"*\\mmc.exe",
"*\\colorcpl.exe",
"*\\wsreset.exe",
"*\\esentutl.exe",
"*\PkgMgr.exe"
) AND NOT (
SourceImage IN (
"*C:\\Windows\\system32\\*",
"*C:\\Windows\\syswow64\\*",
"*C:\\Program Files\\*",
"*C:\\Program Files (x86)\\*",
"%systemroot%\\*"
)
)
Stage 2: eval
| eval g_access_decimal = tonumber(replace(GrantedAccess,"0x",""),16)
Stage 3: eval
| eval PROCESS_DUP_HANDLE = 64
Stage 4: eval
| eval dup_handle_set = bit_and (g_access_decimal, PROCESS_DUP_HANDLE)
Stage 5: where
| where dup_handle_set == PROCESS_DUP_HANDLE
Stage 6: stats
| stats
count
min(_time) as firstTime
max(_time) as lastTime
by
SourceImage
TargetImage
GrantedAccess
PROCESS_DUP_HANDLE
g_access_decimal
dup_handle_set
Guid
Opcode
ProcessID
SecurityID
SourceProcessGUID
SourceProcessId
TargetProcessGUID
TargetProcessId
UserID
dest
granted_access
parent_process_exec
parent_process_guid
parent_process_id
parent_process_name
parent_process_path
process_exec
process_guid
process_id
process_name
process_path
signature
signature_id
user_id
vendor_product
CallTrace
EventID
Stage 7: search
| `security_content_ctime(firstTime)`
Stage 8: search
| `security_content_ctime(lastTime)`
Stage 9: search
| `windows_handle_duplication_in_known_uac_bypass_binaries_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"10" |
TargetImage | in |
| field:"TargetImage" kind:in |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
SourceImage | in | %systemroot%\*, *C:\Program Files (x86)\*, *C:\Program Files\*, *C:\Windows\system32\*, *C:\Windows\syswow64\* | excludes:SourceImage |
Windows Impair Defense Disable Web Evaluation
#The following analytic detects modifications to the Windows registry entry "EnableWebContentEvaluation" to disable Windows Defender web content evaluation. It leverages data from the Endpoint.Registry datamodel, specifically monitoring changes where the registry value is set to "0x00000000". This activity is significant as it indicates an attempt to impair browser security features, potentially allowing malicious web content to bypass security checks. If confirmed malicious, this could lead to users interacting with harmful scripts or unsafe web elements, increasing the risk of system exploitation and security breaches.
Known False Positives
- It is unusual to turn this feature off a Windows system since it is a default security control, although it is not rare for some policies to disable it. Although no false positives have been identified, use the provided filter macro to tune the search.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Defense Impairment |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 13: RegistryEvent (Value Set) |
Rule Body
name: Windows Impair Defense Disable Web Evaluation
id: e234970c-dcf5-4f80-b6a9-3a562544ca5b
version: 13
creation_date: '2024-01-29'
modification_date: '2026-06-08'
author: Teoderick Contreras, Splunk
status: production
type: TTP
description: The following analytic detects modifications to the Windows registry entry "EnableWebContentEvaluation" to disable Windows Defender web content evaluation. It leverages data from the Endpoint.Registry datamodel, specifically monitoring changes where the registry value is set to "0x00000000". This activity is significant as it indicates an attempt to impair browser security features, potentially allowing malicious web content to bypass security checks. If confirmed malicious, this could lead to users interacting with harmful scripts or unsafe web elements, increasing the risk of system exploitation and security breaches.
data_source:
- Sysmon EventID 13
search: |
| tstats `security_content_summariesonly` count min(_time) as firstTime max(_time) as lastTime FROM datamodel=Endpoint.Registry
WHERE (
Registry.registry_path= "*\\Windows\\CurrentVersion\\AppHost\\EnableWebContentEvaluation" AND
Registry.registry_value_data IN (0, "0x00000000")
)
by Registry.action Registry.dest Registry.process_guid Registry.process_id Registry.registry_hive Registry.registry_path Registry.registry_key_name Registry.registry_value_data Registry.registry_value_name Registry.registry_value_type Registry.status Registry.user Registry.vendor_product
| `drop_dm_object_name(Registry)`
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| `windows_impair_defense_disable_web_evaluation_filter`
how_to_implement: To successfully implement this search you need to be ingesting information on process that include the name of the process responsible for the changes from your endpoints into the `Endpoint` datamodel in the `Registry` node.
known_false_positives: It is unusual to turn this feature off a Windows system since it is a default security control, although it is not rare for some policies to disable it. Although no false positives have been identified, use the provided filter macro to tune the search.
references:
- https://x.com/malmoeb/status/1742604217989415386?s=20
- https://github.com/undergroundwires/privacy.sexy
finding:
title: Windows Defender web content evaluation feature set to disable on $dest$.
entity:
field: dest
type: system
score: 50
analytic_story:
- Windows Defense Evasion Tactics
- Windows Registry Abuse
- Salat Stealer
asset_type: Endpoint
mitre_attack_id:
- T1685
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: tstats
| tstats `security_content_summariesonly`
count
min(_time) as firstTime
max(_time) as lastTime
FROM datamodel=Endpoint.Registry
WHERE (
Registry.registry_path= "*\\Windows\\CurrentVersion\\AppHost\\EnableWebContentEvaluation"
AND Registry.registry_value_data IN (0, "0x00000000")
)
by
Registry.action
Registry.dest
Registry.process_guid
Registry.process_id
Registry.registry_hive
Registry.registry_path
Registry.registry_key_name
Registry.registry_value_data
Registry.registry_value_name
Registry.registry_value_type
Registry.status
Registry.user
Registry.vendor_product
Stage 2: search
| `drop_dm_object_name(Registry)`
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: search
| `windows_impair_defense_disable_web_evaluation_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
Registry.registry_path | eq |
| field:"registry_path" kind:eq value:"*\Windows\CurrentVersion\AppHost\EnableWebContentEvaluation" |
Registry.registry_value_data | in |
| field:"Details" kind:in |
Windows RDP Connection Successful
#The following analytic detects successful Remote Desktop Protocol (RDP) connections by monitoring EventCode 1149 from the Windows TerminalServices RemoteConnectionManager Operational log. This detection is significant as successful RDP connections can indicate remote access to a system, which may be leveraged by attackers to control or exfiltrate data. If confirmed malicious, this activity could lead to unauthorized access, data theft, or further lateral movement within the network. Monitoring successful RDP connections is crucial for identifying potential security breaches and mitigating risks promptly.
Known False Positives
- False positives will be present, filter as needed or restrict to critical assets on the perimeter.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Lateral Movement |
Telemetry Coverage
Rule Body
name: Windows RDP Connection Successful
id: ceaed840-56b3-4a70-b8e1-d762b1c5c08c
version: 11
creation_date: '2023-04-17'
modification_date: '2026-05-13'
author: Michael Haag, Splunk
status: production
type: Hunting
description: The following analytic detects successful Remote Desktop Protocol (RDP) connections by monitoring EventCode 1149 from the Windows TerminalServices RemoteConnectionManager Operational log. This detection is significant as successful RDP connections can indicate remote access to a system, which may be leveraged by attackers to control or exfiltrate data. If confirmed malicious, this activity could lead to unauthorized access, data theft, or further lateral movement within the network. Monitoring successful RDP connections is crucial for identifying potential security breaches and mitigating risks promptly.
data_source:
- Windows Event Log RemoteConnectionManager 1149
search: |-
`remoteconnectionmanager` EventCode=1149
| stats count min(_time) as firstTime max(_time) as lastTime
BY Computer, user_id
| `security_content_ctime(firstTime)`
| `security_content_ctime(lastTime)`
| rename Computer as dest
| `windows_rdp_connection_successful_filter`
how_to_implement: The following analyic requires the WIndows TerminalServices RemoteConnectionManager Operational log to be enabled and ingested into Splunk. For the inputs, review https://gist.github.com/MHaggis/138c6bf563bacbda4a2524f089773706.
known_false_positives: False positives will be present, filter as needed or restrict to critical assets on the perimeter.
references:
- https://gist.github.com/MHaggis/138c6bf563bacbda4a2524f089773706
- https://doublepulsar.com/rdp-hijacking-how-to-hijack-rds-and-remoteapp-sessions-transparently-to-move-through-an-da2a1e73a5f6
analytic_story:
- Active Directory Lateral Movement
- BlackByte Ransomware
- Windows RDP Artifacts and Defense Evasion
- Interlock Ransomware
- NetSupport RMM Tool Abuse
asset_type: Endpoint
mitre_attack_id:
- T1563.002
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`remoteconnectionmanager` EventCode=1149
Stage 2: stats
| stats count min(_time) as firstTime max(_time) as lastTime
BY Computer, user_id
Stage 3: search
| `security_content_ctime(firstTime)`
Stage 4: search
| `security_content_ctime(lastTime)`
Stage 5: rename
| rename Computer as dest
Stage 6: search
| `windows_rdp_connection_successful_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"1149" |
Windows Unsigned DLL Side-Loading In Same Process Path
#This detection identifies unsigned DLLs loaded through DLL side-loading with same file path with the process loaded the DLL, a technique observed in DarkGate malware. This detection monitors DLL loading, verifies signatures, and flags unsigned DLLs. Suspicious file paths and known executable associations are checked. Detecting such suspicious DLLs is crucial in preventing privilege escalation attacks and other potential security breaches. Regular security assessments, thorough monitoring, and implementing security best practices are essential in safeguarding systems from such threats.
Known False Positives
- No false positives have been identified at this time.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 7: Image loaded |
Rule Body
name: Windows Unsigned DLL Side-Loading In Same Process Path
id: 3cf85c02-f9d6-4186-bf3c-e70ee99fbc7f
version: 20
creation_date: '2024-06-26'
modification_date: '2026-05-13'
author: Teoderick Contreras, Splunk
status: production
type: TTP
description: This detection identifies unsigned DLLs loaded through DLL side-loading with same file path with the process loaded the DLL, a technique observed in DarkGate malware. This detection monitors DLL loading, verifies signatures, and flags unsigned DLLs. Suspicious file paths and known executable associations are checked. Detecting such suspicious DLLs is crucial in preventing privilege escalation attacks and other potential security breaches. Regular security assessments, thorough monitoring, and implementing security best practices are essential in safeguarding systems from such threats.
data_source:
- Sysmon EventID 7
search: '`sysmon` EventCode=7 Signed=false SignatureStatus != Valid NOT (Image IN ("*:\\windows\\system32\\*", "*:\\windows\\syswow64\\*", "c:\\Program Files*")) NOT (ImageLoaded IN ("*:\\windows\\system32\\*", "*:\\windows\\syswow64\\*", "c:\\Program Files*")) | rex field=Image "(?<ImageFolderPath>.+\\\)" | rex field=ImageLoaded "(?<ImageLoadedFolderPath>.+\\\)" | where ImageFolderPath = ImageLoadedFolderPath | stats count min(_time) as firstTime max(_time) as lastTime by Image ImageLoaded dest loaded_file loaded_file_path process_exec process_guid process_hash process_id process_name process_path service_dll_signature_exists service_dll_signature_verified signature signature_id user_id vendor_product | `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)` | `windows_unsigned_dll_side_loading_in_same_process_path_filter`'
how_to_implement: To successfully implement this search, you need to be ingesting logs with the process name and imageloaded executions from your endpoints. If you are using Sysmon, you must have at least version 6.0.4 of the Sysmon TA.
known_false_positives: No false positives have been identified at this time.
references:
- https://www.splunk.com/en_us/blog/security/enter-the-gates-an-analysis-of-the-darkgate-autoit-loader.html
- https://www.trendmicro.com/en_us/research/23/b/investigating-the-plugx-trojan-disguised-as-a-legitimate-windows.html
finding:
title: An unsigned dll module was loaded on $dest$
entity:
field: dest
type: system
score: 50
analytic_story:
- PlugX
- DarkGate Malware
- Derusbi
- China-Nexus Threat Activity
- Malicious Inno Setup Loader
- Salt Typhoon
- XWorm
- SnappyBee
- NailaoLocker Ransomware
- Lokibot
- SolarWinds WHD RCE Post Exploitation
asset_type: Endpoint
mitre_attack_id:
- T1574.001
product:
- Splunk Enterprise
- Splunk Enterprise Security
- Splunk Cloud
category: endpoint
security_domain: endpoint
Stages and Predicates
Stage 1: search
`sysmon` EventCode=7 Signed=false SignatureStatus != Valid NOT (Image IN ("*:\\windows\\system32\\*", "*:\\windows\\syswow64\\*", "c:\\Program Files*")) NOT (ImageLoaded IN ("*:\\windows\\system32\\*", "*:\\windows\\syswow64\\*", "c:\\Program Files*"))
Stage 2: rex
| rex field=Image "(?<ImageFolderPath>.+\\\)"
Stage 3: rex
| rex field=ImageLoaded "(?<ImageLoadedFolderPath>.+\\\)"
Stage 4: where
| where ImageFolderPath = ImageLoadedFolderPath
Stage 5: stats
| stats
count
min(_time) as firstTime
max(_time) as lastTime
by
Image
ImageLoaded
dest
loaded_file
loaded_file_path
process_exec
process_guid
process_hash
process_id
process_name
process_path
service_dll_signature_exists
service_dll_signature_verified
signature
signature_id
user_id
vendor_product
Stage 6: search
| `security_content_ctime(firstTime)`
Stage 7: search
| `security_content_ctime(lastTime)`
Stage 8: search
| `windows_unsigned_dll_side_loading_in_same_process_path_filter`
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"7" |
SignatureStatus | ne |
| field:"SignatureStatus" kind:ne value:"Valid" |
Signed | eq |
| field:"Signed" kind:eq value:"false" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
Image | in | *:\windows\system32\*, *:\windows\syswow64\*, c:\Program Files* | excludes:Image field:"Image" value:"*:\windows\system32\*" field:"Image" value:"*:\windows\syswow64\*" field:"Image" value:"c:\Program Files*" |
ImageLoaded | in | *:\windows\system32\*, *:\windows\syswow64\*, c:\Program Files* | excludes:ImageLoaded field:"ImageLoaded" value:"*:\windows\system32\*" field:"ImageLoaded" value:"*:\windows\syswow64\*" field:"ImageLoaded" value:"c:\Program Files*" |
wuauclt.exe Network Connection (Windows Event Log)
#wuauclt.exe is the Windows Update client. It can be abused to proxy execution of malicious code as documented in the LOLBAS project. This use case detects network connection events with wuauclt.exe. Connections to Microsoft-owned IPs are expected behavior and have been filtered out
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
References
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Security-Auditing | Event ID 5156: The Windows Filtering Platform has permitted a connection. |
Rule Body
id: '25039.46462'
title: wuauclt.exe Network Connection
description: wuauclt.exe is the Windows Update client. It can be abused to proxy execution
of malicious code as documented in the LOLBAS project. This use case detects network
connection events with wuauclt.exe. Connections to Microsoft-owned IPs are expected
behavior and have been filtered out. Living Off the Land Binary and Scripts (LOLBAS)
(LOLBIN)
logic_format: Splunk
logic: '`get_endpoint_data` `get_endpoint_data_winevent` (TERM(EventCode=5156) OR
"<EventID>5156<") "wuauclt" | where not match(dest_ip, "^(20\.18[4-9]\.|20\.19[0-1]\.|23\.79\.|51\.10[3-5]\.|52\.239\.)")
and match(process_name, "(?i)wuauclt\.exe") | table _time, host, user, signature_id,
process, process_name, parent_process_path, parent_process_name, src_ip, dest_ip
`group_events("host,1)` '
techniques:
- defense-evasion:system binary proxy execution
technique_id:
- T1218
data_category:
- Windows event logs
references:
- https://lolbas-project.github.io/lolbas/Binaries/Wuauclt/
Stages and Predicates
Stage 1: search
search EventCode=5156 source="*" source IN ("WinEventLog:Security", "XmlWinEventLog:Security")
Stage 2: where
where NOT match(dest_ip, "^(20\\.18[4-9]\\.|20\\.19[0-1]\\.|23\\.79\\.|51\\.10[3-5]\\.|52\\.239\\.)") match(process_name, "(?i)wuauclt\\.exe")
Stage 3: table
table _time, dest_ip, host, parent_process_name, parent_process_path, process, process_name,
signature_id, src_ip, user
Stage 4: bucket
bucket _time
Stage 5: stats
stats BY host, _time
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
EventCode | eq |
| field:"EventID" kind:eq value:"5156" |
process_name | regex_match |
| field:"process_name" kind:regex_match value:"(?i)wuauclt.exe" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
dest_ip | regex_match | ^(20.18[4-9].|20.19[0-1].|23.79.|51.10[3-5].|52.239.) | excludes:dest_ip field:"dest_ip" value:"^(20.18[4-9].|20.19[0-1].|23.79.|51.10[3-5].|52.239.)" |
Search Terms
These SPL tokens match against raw event text.
| Stage | Term |
|---|---|
| 1 | "<EventID>5156<" |
| 1 | "wuauclt" |