Detection rules › Elastic
Elastic rules: 16
API Call from Inaccessible Memory Page
#Identifies API calls from memory regions unexpectedly marked as inaccessible. This may indicate an attempt to hide injected code from memory scanners.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies API calls from memory regions unexpectedly marked as inaccessible. This may indicate an attempt to hide
injected code from memory scanners.
"""
id = "2f4afc62-e9df-4654-b0c1-67ce380a1131"
license = "Elastic License v2"
name = "API Call from Inaccessible Memory Page"
os_list = ["windows"]
version = "1.0.3"
query = '''
api where
process.Ext.api.name in ("VirtualProtect", "VirtualAlloc", "SetThreadContext", "MapViewOfFile", "MapViewOfFile2") and
(process.thread.Ext.call_stack_final_user_module.name == "Unbacked" or
process.thread.Ext.call_stack_final_user_module.allocation_private_bytes >= 100000) and
_arraysearch(process.thread.Ext.call_stack, $entry,
$entry.symbol_info == "Unbacked" and $entry.callsite_trailing_bytes like ("NOACCESS*", "GUARD*"))
'''
min_endpoint_version = "8.18.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
tree = true
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1564"
name = "Hide Artifacts"
reference = "https://attack.mitre.org/techniques/T1564/"
[[threat.technique]]
id = "T1620"
name = "Reflective Code Loading"
reference = "https://attack.mitre.org/techniques/T1620/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.18.0"
Stages and Predicates
Stage 1: api
api where
process.Ext.api.name in ("VirtualProtect", "VirtualAlloc", "SetThreadContext", "MapViewOfFile", "MapViewOfFile2") and
(process.thread.Ext.call_stack_final_user_module.name == "Unbacked" or
process.thread.Ext.call_stack_final_user_module.allocation_private_bytes >= 100000) and
_arraysearch(process.thread.Ext.call_stack, $entry,
$entry.symbol_info == "Unbacked" and $entry.callsite_trailing_bytes like ("NOACCESS*", "GUARD*"))
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
process.Ext.api.name | in |
| field:"process.Ext.api.name" kind:in |
process.thread.Ext.call_stack_final_user_module.allocation_private_bytes | ge |
| field:"process.thread.Ext.call_stack_final_user_module.allocation_private_bytes" kind:ge value:"100000" |
process.thread.Ext.call_stack_final_user_module.name | eq |
| field:"process.thread.Ext.call_stack_final_user_module.name" kind:eq value:"Unbacked" |
AWS IAM AdministratorAccess Policy Attached to Group
#An adversary with access to a set of compromised credentials may attempt to persist or escalate privileges by attaching additional permissions to user groups the compromised user account belongs to. This rule looks for use of the IAM AttachGroupPolicy API operation to attach the highly permissive AdministratorAccess AWS managed policy to an existing IAM user group.
Known False Positives
- While this can be normal behavior, it should be investigated to ensure validity. Verify whether the user identity should be using the IAM `AttachGroupPolicy` API operation to attach the `AdministratorAccess` policy to the user group.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation |
Telemetry Coverage
Rules Detecting the Same Action
These rules filter on the same operation.
Rule Body
[metadata]
creation_date = "2024/05/31"
integration = ["aws"]
maturity = "production"
updated_date = "2026/04/10"
[rule]
author = ["Elastic"]
description = """
An adversary with access to a set of compromised credentials may attempt to persist or escalate privileges by attaching
additional permissions to user groups the compromised user account belongs to. This rule looks for use of the IAM
AttachGroupPolicy API operation to attach the highly permissive AdministratorAccess AWS managed policy to an existing
IAM user group.
"""
false_positives = [
"""
While this can be normal behavior, it should be investigated to ensure validity. Verify whether the user identity
should be using the IAM `AttachGroupPolicy` API operation to attach the `AdministratorAccess` policy to the user
group.
""",
]
from = "now-6m"
index = ["filebeat-*", "logs-aws.cloudtrail-*"]
language = "eql"
license = "Elastic License v2"
name = "AWS IAM AdministratorAccess Policy Attached to Group"
note = """## Triage and analysis
### Investigating AWS IAM AdministratorAccess Policy Attached to Group
The AWS-managed `AdministratorAccess` policy grants full administrative privileges across all AWS services.
When attached to a group, all group members inherit this access, often unintentionally broadening the blast radius of a compromise.
Adversaries can exploit `iam:AttachGroupPolicy` permissions to escalate privileges or establish persistence by attaching this policy to an existing user group.
#### Possible investigation steps
- **Identify the affected group and calling principal.**
Review `aws.cloudtrail.user_identity.arn` (caller) and `aws.cloudtrail.request_parameters.groupName` (target group).
Validate whether this aligns with legitimate change management or automation workflows.
- **Review group membership.**
Enumerate current members using `aws iam get-group`.
Determine whether unauthorized users could have gained administrative access as a result.
- **Inspect CloudTrail details.**
Check `source.ip`, `user_agent.original`, and `source.geo` fields for anomalies.
Compare with historical operations by the same principal.
- **Correlate related IAM activity.**
Search for adjacent events such as `AddUserToGroup`, `CreateUser`, or `AttachUserPolicy`.
These may indicate chained privilege escalation.
- **Assess propagation of privileges.**
If the group has many members or is linked to cross-account roles, the impact may extend beyond a single user.
Document all affected identities for containment.
### False positive analysis
- **Intentional access updates.**
Policy attachment may occur during legitimate administrative provisioning. Confirm via ticketing systems.
- **Automation or compliance tasks.**
Some environments use centralized scripts to attach AdministratorAccess temporarily. Validate through automation logs.
### Response and remediation
**Immediate containment**
- Detach the policy from the affected group (`aws iam detach-group-policy`).
- Review and limit group membership. Temporarily remove non-essential users or disable access for impacted accounts.
- Rotate credentials for users who inherited admin privileges from the attachment.
- Enable MFA on all impacted accounts.
**Evidence preservation**
- Export the triggering `AttachGroupPolicy` event and related CloudTrail entries ±30 minutes from the alert.
- Preserve AWS Config and GuardDuty records to support forensic analysis.
**Scoping and investigation**
- Review additional IAM operations from the same caller (`CreateAccessKey`, `AttachRolePolicy`, `UpdateAssumeRolePolicy`).
- Identify whether new groups or roles were created shortly before or after the event.
- Check for subsequent API activity by newly privileged users (for example, S3, EC2, or IAM modifications).
**Recovery and hardening**
- Reinforce least privilege, avoid assigning `AdministratorAccess` to groups.
- Use role-based access control with scoped permissions.
- Enable CloudTrail, GuardDuty, and Security Hub across all regions.
- Implement SCPs at the organization level to restrict direct `AdministratorAccess` attachments.
### Additional information
- **[AWS IR Playbooks](https://github.com/aws-samples/aws-incident-response-playbooks/blob/c151b0dc091755fffd4d662a8f29e2f6794da52c/playbooks/): response steps related to IAM policy modification and unauthorized privilege escalation..
- **[AWS Customer Playbook Framework](https://github.com/aws-samples/aws-customer-playbook-framework/): for containment, analysis, and recovery guidance.
- **AWS Documentation:** [AdministratorAccess Policy](https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies_job-functions.html#jf_administrator).
"""
references = [
"https://docs.aws.amazon.com/IAM/latest/APIReference/API_AttachGroupPolicy.html",
"https://docs.aws.amazon.com/aws-managed-policy/latest/reference/AdministratorAccess.html",
"https://hackingthe.cloud/aws/exploitation/iam_privilege_escalation/",
]
risk_score = 47
rule_id = "df919b5e-a0f6-4fd8-8598-e3ce79299e3b"
severity = "medium"
tags = [
"Domain: Cloud",
"Data Source: AWS",
"Data Source: Amazon Web Services",
"Data Source: AWS IAM",
"Use Case: Identity and Access Audit",
"Tactic: Privilege Escalation",
"Tactic: Persistence",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
iam where data_stream.dataset == "aws.cloudtrail"
and event.provider == "iam.amazonaws.com"
and event.action == "AttachGroupPolicy"
and event.outcome == "success"
and stringContains(aws.cloudtrail.request_parameters, "policyArn=arn:aws:iam::aws:policy/AdministratorAccess")
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.003"
name = "Additional Cloud Roles"
reference = "https://attack.mitre.org/techniques/T1098/003/"
[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 = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.003"
name = "Additional Cloud Roles"
reference = "https://attack.mitre.org/techniques/T1098/003/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[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",
"event.action",
"group.name",
"event.outcome",
"cloud.account.id",
"cloud.region",
"aws.cloudtrail.request_parameters",
]
Stages and Predicates
Stage 1: iam
iam where data_stream.dataset == "aws.cloudtrail"
and event.provider == "iam.amazonaws.com"
and event.action == "AttachGroupPolicy"
and event.outcome == "success"
and stringContains(aws.cloudtrail.request_parameters, "policyArn=arn:aws:iam::aws:policy/AdministratorAccess")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
aws.cloudtrail.request_parameters | contains |
| field:"aws::requestParameters" kind:contains value:"policyArn=arn:aws:iam::aws:policy/AdministratorAccess" |
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"aws.cloudtrail" |
event.action | eq |
| field:"EventType" kind:eq value:"AttachGroupPolicy" |
event.outcome | eq |
| field:"event.outcome" kind:eq value:"success" |
event.provider | eq |
| field:"Provider_Name" kind:eq value:"iam.amazonaws.com" |
AWS Rare Source AS Organization Activity
#Surfaces an AWS identity whose successful API traffic is dominated by a small set of large cloud-provider source AS organization labels, yet also shows a very small share of traffic from other AS organization names—including at least one sensitive control-plane, credential, storage, or model-invocation action on that uncommon network path with recent activity from the uncommon path. The intent is to highlight disproportionate “baseline” cloud egress versus sparse use from rarer networks on the same principal, a shape that can appear when automation or CI credentials are reused or pivoted outside their usual hosted-cloud footprint.
Known False Positives
- Global employees on VPNs, split DNS or proxy paths that change AS labels, regional carrier rebrands, or mobile hotspots can produce a small non-cloud AS share on the same IAM user as hyperscaler- or SaaS-classified traffic. Corporate travel, emergency break-glass from a home ISP, and multi-region runners may also widen AS diversity without malice. Tune thresholds, add account or principal allowlists, or narrow the sensitive-action list after baseline review.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access |
Rule Body
[metadata]
creation_date = "2026/04/21"
integration = ["aws"]
maturity = "production"
updated_date = "2026/04/21"
[rule]
author = ["Elastic"]
description = """
Surfaces an AWS identity whose successful API traffic is dominated by a small set of large cloud-provider source AS
organization labels, yet also shows a very small share of traffic from other AS organization names—including at least one
sensitive control-plane, credential, storage, or model-invocation action on that uncommon network path with recent
activity from the uncommon path. The intent is to highlight disproportionate “baseline” cloud egress versus sparse use
from rarer networks on the same principal, a shape that can appear when automation or CI credentials are reused or
pivoted outside their usual hosted-cloud footprint.
"""
false_positives = [
"""
Global employees on VPNs, split DNS or proxy paths that change AS labels, regional carrier rebrands, or mobile
hotspots can produce a small non-cloud AS share on the same IAM user as hyperscaler- or SaaS-classified traffic.
Corporate travel, emergency break-glass from a home ISP, and multi-region runners may also widen AS diversity without
malice. Tune thresholds, add account or principal allowlists, or narrow the sensitive-action list after baseline review.
""",
]
from = "now-7d"
interval = "1h"
language = "esql"
license = "Elastic License v2"
name = "AWS Rare Source AS Organization Activity"
note = """## Triage and analysis
### Investigating AWS Rare Source AS Organization Activity After High Cloud-Provider Volume
The rule aggregates roughly seven days of successful CloudTrail per `user.name` and `aws.cloudtrail.user_identity.type`.
It expects a **high count** of events whose GeoIP AS organization matches a short allowlist of large cloud/SaaS providers,
**at least one** event from a different AS organization, a **low ratio** of uncommon-network events to all events, few
**distinct** uncommon AS labels, and **recent** uncommon-network timestamps. It further requires at least one
**sensitive** API from an uncommon network (see query `event.action` list).
#### Possible investigation steps
- Compare `Esql.src_asn_values` to `Esql.user_agent_values` and map each `source.ip` (from raw CloudTrail) to expected
admin paths, pipelines, or offices.
- Pivot on `user.name` and `aws.cloudtrail.user_identity.access_key_id` (from underlying events) for IAM, STS, S3, and
Secrets Manager activity around `Esql.most_recent_low_asn_day`.
- Confirm whether the identity is meant for automation only; if so, rare human ISP ASNs warrant higher scrutiny.
- Review `Esql.untrusted_suspicious_actions` for the mix of discovery versus privilege-changing APIs.
### False positive analysis
- **Threshold sensitivity**: Raise `Esql.trusted_cloud_event_count` or Lower `Esql.rare_asn_ratio` and `Esql.untrusted_event_count` if legitimate rare-ASN
noise persists.
- **MongoDB / other allowlist labels**: Extend `is_trusted_cloud` if your approved automation consistently appears under
another legal-entity string.
### Response and remediation
- If abuse is plausible: rotate credentials for the principal, enforce OIDC or short-lived keys for automation, and
tighten IAM and data-plane permissions.
### Additional information
- [CloudTrail user identity](https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference-user-identity.html)
"""
references = [
"https://docs.aws.amazon.com/awscloudtrail/latest/userguide/cloudtrail-event-reference.html",
]
risk_score = 73
rule_id = "d1b37c0b-4f8b-4cfb-9a1d-639bf8c028b7"
severity = "high"
tags = [
"Domain: Cloud",
"Data Source: AWS",
"Data Source: Amazon Web Services",
"Data Source: AWS CloudTrail",
"Use Case: Threat Detection",
"Tactic: Initial Access",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "esql"
query = '''
FROM logs-aws.cloudtrail-*
| WHERE event.dataset == "aws.cloudtrail"
AND event.outcome == "success"
AND source.as.organization.name IS NOT NULL
AND user.name IS NOT NULL
| EVAL is_trusted_cloud = CASE(
source.as.organization.name LIKE "Amazon*" OR
source.as.organization.name == "Google LLC" OR
source.as.organization.name == "Microsoft Corporation" OR
source.as.organization.name == "MongoDB, Inc.",
true, false
)
| EVAL is_suspicious_action = CASE(
event.action IN (
"GetCallerIdentity", "GetAccountSummary", "ListAccountAliases",
"GetSecretValue", "ListSecrets", "DescribeSecret",
"GetParameter", "GetParameters", "GetParametersByPath",
"AssumeRole", "AssumeRoleWithWebIdentity", "AssumeRoleWithSAML",
"AttachUserPolicy", "AttachRolePolicy",
"PutUserPolicy", "PutRolePolicy",
"CreateAccessKey", "UpdateAccessKey",
"CreateUser", "CreateLoginProfile",
"UpdateLoginProfile", "AddUserToGroup",
"GetObject", "ListBuckets", "ListObjects", "ListObjectsV2",
"InvokeModel", "InvokeModelWithResponseStream", "Converse"
), true, false
)
// Single aggregation — full event count preserved for ratio logic
// suspicious action tracking is additive on top
| STATS
Esql.total_events_all_asns = COUNT(*),
Esql.count_distinct_asns = COUNT_DISTINCT(source.as.organization.name),
Esql.src_asn_values = VALUES(source.as.organization.name),
Esql.user_agent_values = VALUES(user_agent.original),
Esql.related_users = VALUES(user.changes.name),
Esql.source_ip_values = VALUES(source.address),
Esql.has_trusted_cloud_asn = MAX(is_trusted_cloud),
Esql.trusted_cloud_event_count = SUM(CASE(is_trusted_cloud == true, 1, 0)),
Esql.untrusted_event_count = SUM(CASE(is_trusted_cloud == false, 1, 0)),
// Suspicious action visibility from untrusted ASNs — informational only, not a filter
Esql.untrusted_suspicious_count = SUM(CASE(
is_trusted_cloud == false AND is_suspicious_action == true, 1, 0
)),
Esql.untrusted_suspicious_actions = VALUES(CASE(
is_trusted_cloud == false AND is_suspicious_action == true,
event.action, null
)),
Esql.most_recent_low_asn_day = MAX(CASE(
is_trusted_cloud == false, @timestamp, null
))
BY user.name, aws.cloudtrail.user_identity.type
| EVAL Esql.rare_asn_ratio = TO_DOUBLE(Esql.untrusted_event_count) / TO_DOUBLE(Esql.total_events_all_asns),
Esql.unique_action_from_untrusted_asn = MV_COUNT(Esql.untrusted_suspicious_actions)
// Detection thresholds — unchanged, full event counts drive the logic
| WHERE Esql.has_trusted_cloud_asn == true
AND Esql.untrusted_event_count >= 1
AND Esql.trusted_cloud_event_count >= 100
AND Esql.rare_asn_ratio <= 0.01
AND Esql.unique_action_from_untrusted_asn >= 2
AND Esql.count_distinct_asns <= 5
AND Esql.most_recent_low_asn_day >= NOW() - 1 hour
| KEEP user.name,
aws.cloudtrail.user_identity.type,
Esql.*
'''
[rule.investigation_fields]
field_names = [
"user.name",
"aws.cloudtrail.user_identity.type",
"Esql.*"
]
[[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.tactic]
id = "TA0001"
name = "Initial Access"
reference = "https://attack.mitre.org/tactics/TA0001/"
Stages and Predicates
Stage 1: from
FROM logs-aws.cloudtrail-*
Stage 2: where
| WHERE event.dataset == "aws.cloudtrail"
AND event.outcome == "success"
AND source.as.organization.name IS NOT NULL
AND user.name IS NOT NULL
Stage 3: eval
| EVAL is_trusted_cloud = CASE(
source.as.organization.name LIKE "Amazon*" OR
source.as.organization.name == "Google LLC" OR
source.as.organization.name == "Microsoft Corporation" OR
source.as.organization.name == "MongoDB, Inc.",
true, false
)
is_trusted_cloud =source.as.organization.name LIKE "Amazon*" OR
source.as.organization.name == "Google LLC" OR
source.as.organization.name == "Microsoft Corporation" OR
source.as.organization.name == "MongoDB, Inc."truefalseStage 4: eval
| EVAL is_suspicious_action = CASE(
event.action IN (
"GetCallerIdentity", "GetAccountSummary", "ListAccountAliases",
"GetSecretValue", "ListSecrets", "DescribeSecret",
"GetParameter", "GetParameters", "GetParametersByPath",
"AssumeRole", "AssumeRoleWithWebIdentity", "AssumeRoleWithSAML",
"AttachUserPolicy", "AttachRolePolicy",
"PutUserPolicy", "PutRolePolicy",
"CreateAccessKey", "UpdateAccessKey",
"CreateUser", "CreateLoginProfile",
"UpdateLoginProfile", "AddUserToGroup",
"GetObject", "ListBuckets", "ListObjects", "ListObjectsV2",
"InvokeModel", "InvokeModelWithResponseStream", "Converse"
), true, false
)
is_suspicious_action =event.action IN (
"GetCallerIdentity", "GetAccountSummary", "ListAccountAliases",
"GetSecretValue", "ListSecrets", "DescribeSecret",
"GetParameter", "GetParameters", "GetParametersByPath",
"AssumeRole", "AssumeRoleWithWebIdentity", "AssumeRoleWithSAML",
"AttachUserPolicy", "AttachRolePolicy",
"PutUserPolicy", "PutRolePolicy",
"CreateAccessKey", "UpdateAccessKey",
"CreateUser", "CreateLoginProfile",
"UpdateLoginProfile", "AddUserToGroup",
"GetObject", "ListBuckets", "ListObjects", "ListObjectsV2",
"InvokeModel", "InvokeModelWithResponseStream", "Converse"
)truefalseStage 5: stats
| STATS
Esql.total_events_all_asns = COUNT(*),
Esql.count_distinct_asns = COUNT_DISTINCT(source.as.organization.name),
Esql.src_asn_values = VALUES(source.as.organization.name),
Esql.user_agent_values = VALUES(user_agent.original),
Esql.related_users = VALUES(user.changes.name),
Esql.source_ip_values = VALUES(source.address),
Esql.has_trusted_cloud_asn = MAX(is_trusted_cloud),
Esql.trusted_cloud_event_count = SUM(CASE(is_trusted_cloud == true, 1, 0)),
Esql.untrusted_event_count = SUM(CASE(is_trusted_cloud == false, 1, 0)),
Esql.untrusted_suspicious_count = SUM(CASE(
is_trusted_cloud == false AND is_suspicious_action == true, 1, 0
)),
Esql.untrusted_suspicious_actions = VALUES(CASE(
is_trusted_cloud == false AND is_suspicious_action == true,
event.action, null
)),
Esql.most_recent_low_asn_day = MAX(CASE(
is_trusted_cloud == false, @timestamp, null
))
BY user.name, aws.cloudtrail.user_identity.type
Stage 6: eval
| EVAL Esql.rare_asn_ratio = TO_DOUBLE(Esql.untrusted_event_count) / TO_DOUBLE(Esql.total_events_all_asns),
Esql.unique_action_from_untrusted_asn = MV_COUNT(Esql.untrusted_suspicious_actions)
Stage 7: where
| WHERE Esql.has_trusted_cloud_asn == true
AND Esql.untrusted_event_count >= 1
AND Esql.trusted_cloud_event_count >= 100
AND Esql.rare_asn_ratio <= 0.01
AND Esql.unique_action_from_untrusted_asn >= 2
AND Esql.count_distinct_asns <= 5
AND Esql.most_recent_low_asn_day >= NOW() - 1 hour
Stage 8: keep
| KEEP user.name,
aws.cloudtrail.user_identity.type,
Esql.*
Indicators
These rows show field, operator, and value matches.
Output Fields
These fields are emitted when the rule matches.
| Field | Source |
|---|---|
user.name | KEEP user.name |
aws.cloudtrail.user_identity.type | KEEP aws.cloudtrail.user_identity.type |
Esql.* | KEEP Esql.* |
AWS STS AssumeRoot by Rare User and Member Account
#Identifies when the STS AssumeRoot action is performed by a rare user in AWS. The AssumeRoot action allows users to assume the root member account role, granting elevated but specific permissions based on the task policy specified. Adversaries who have compromised user credentials can use this technique to escalate privileges and gain unauthorized access to AWS resources. This is a New Terms rule that identifies when the STS AssumeRoot action is performed by a user that rarely assumes this role against a specific member account.
Known False Positives
- AWS administrators or automated processes might regularly assume root for legitimate administrative purposes.
- AWS services might assume root to access AWS resources as part of their standard operations.
- Automated workflows might assume root to perform periodic administrative tasks.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation | |
| Stealth |
Telemetry Coverage
Rule Body
[metadata]
creation_date = "2024/11/24"
integration = ["aws"]
maturity = "production"
updated_date = "2026/07/08"
[rule]
author = ["Elastic"]
description = """
Identifies when the STS AssumeRoot action is performed by a rare user in AWS. The AssumeRoot action allows users to
assume the root member account role, granting elevated but specific permissions based on the task policy specified.
Adversaries who have compromised user credentials can use this technique to
escalate privileges and gain unauthorized access to AWS resources. This is a New Terms rule that identifies
when the STS AssumeRoot action is performed by a user that rarely assumes this role against a specific member account.
"""
false_positives = [
"AWS administrators or automated processes might regularly assume root for legitimate administrative purposes.",
"AWS services might assume root to access AWS resources as part of their standard operations.",
"Automated workflows might assume root to perform periodic administrative tasks.",
]
from = "now-6m"
index = ["filebeat-*", "logs-aws.cloudtrail-*"]
language = "kuery"
license = "Elastic License v2"
name = "AWS STS AssumeRoot by Rare User and Member Account"
note = """
## Triage and analysis
### Investigating AWS STS AssumeRoot by Rare User and Member Account
AWS STS `AssumeRoot` issues temporary credentials that grant elevated access into a member account, constrained by the
task policy and target policy attached to the request. In normal operations, only a small set of platform, security, or
automation roles should ever need to perform `AssumeRoot`, and typically only against a predictable set of member
accounts.
This rule is a New Terms rule that detects when a previously unseen combination of calling principal (`aws.cloudtrail.user_identity.arn`) and target member account (`aws.cloudtrail.resources.account_id`) successfully invokes `AssumeRoot`. Activity that matches this pattern may indicate privilege escalation, lateral movement into a new account, abuse of cross-account access paths, or misuse of administrative workflows.
#### Possible investigation steps
- **Identify the actor and target context**
- Review `aws.cloudtrail.user_identity.arn` and `aws.cloudtrail.user_identity.access_key_id` to determine:
- Whether the caller is an IAM user, federated user, or role.
- Whether this identity is normally used for organization-level administration or automation.
- Inspect `aws.cloudtrail.resources.account_id` and `aws.cloudtrail.recipient_account_id` to identify the affected member account.
- Check `source.address`, `source.geo.*`, and `user_agent.original` to understand where and how the call was made (console, CLI, SDK, automation runner, VPN, corporate IP, etc.).
- **Understand session, policy, and target details**
- Examine `aws.cloudtrail.request_parameters` for:
- `taskPolicyArn` – which predefined task policy was requested and what category of operations it enables (e.g., investigation, remediation, read-only, or broad admin).
- `targetPrincipal` and/or related target fields – which member account principal is being accessed.
- Any duration or configuration parameters (such as `durationSeconds`) that indicate unusually long-lived sessions.
- In `aws.cloudtrail.response_elements`, review:
- `credentials.accessKeyId` and `credentials.expiration` to confirm that credentials were successfully issued and how long they are valid.
- Any additional response fields that indicate session constraints or failures (if present).
- **Correlate follow-on activity from the assumed root session**
- Use the temporary access key from `aws.cloudtrail.response_elements.credentials.accessKeyId` to pivot in CloudTrail:
- Search for subsequent events where `aws.cloudtrail.user_identity.access_key_id` matches that key.
- Look for high-impact actions such as:
- IAM changes (`iam:CreateUser`, `iam:AttachRolePolicy`, `iam:PutRolePolicy`, `iam:UpdateAssumeRolePolicy`).
- Guardrail changes (CloudTrail, Security Hub, Config, GuardDuty configuration or detector changes).
- Data-impacting actions (S3 bucket policy changes, RDS/RDS snapshot operations, EFS/RDS delete, secrets reads).
- Correlate with any prior events for the calling identity:
- STS calls that created the session used to invoke `AssumeRoot` (e.g., `AssumeRole`, SSO/identity provider activity).
- Recent IAM policy updates that broadened its ability to perform cross-account administration.
- **Assess timing and operational alignment**
- Use `@timestamp`, `cloud.region`, and your change calendar to determine:
- Whether the event occurred during a documented maintenance window or deployment.
- Whether the region and account align with the caller’s normal operational scope.
- Compare with other events in the same time window:
- Organization-level changes, new account creation, or migration work.
- Other sensitive operations from the same `source.ip` or principal.
- **Validate with owners**
- Confirm with:
- Cloud/infra platform teams that normally operate organization-level admin roles.
- Security/IR teams if they were running an investigation workflow that legitimately uses `AssumeRoot`.
- Check whether the use of `AssumeRoot` is documented in CI/CD or automation designs that might have just expanded to this account, explaining the New Terms trigger.
### False positive analysis
- **Legitimate administrative cross-account access**
- Platform, security, or central operations teams may use `AssumeRoot` as part of sanctioned workflows for:
- New account onboarding.
- Centralized remediation or investigation.
- Complex deployment or migration tasks.
- If this is the first time a specific engineer or automation role is onboarded to a given member account, the rule will fire once because it is a New Terms rule. Validate and, if appropriate, document this as expected behavior.
- **Automation and scheduled workflows**
- CI/CD pipelines, organization-wide maintenance jobs, or incident response automation may use `AssumeRoot`:
- Identify automation roles and service principals that legitimately call `AssumeRoot`.
- Tune with rule exceptions based on `aws.cloudtrail.user_identity.arn`, `user_agent.original`, or specific `taskPolicyArn` values used only by trusted workflows.
If a pattern emerges where specific roles regularly and legitimately assume root into a consistent set of accounts, consider documenting those identities and, if appropriate, creating narrow exceptions — while preserving coverage for new, unexpected combinations.
### Response and remediation
- **Contain potentially unauthorized sessions**
- If the activity appears suspicious or unapproved:
- Invalidate the credentials issued by `AssumeRoot` (where supported) or constrain their impact by immediately tightening IAM, SCPs, or network controls in the affected member account.
- Rotate or revoke long-lived access keys associated with the calling principal.
- Temporarily restrict permissions on roles allowed to call `AssumeRoot` until the investigation is complete.
- **Investigate scope and impact**
- Using CloudTrail:
- Enumerate all actions performed with the `AssumeRoot` session access key and identify:
- Privilege changes (IAM users, roles, policies, permission boundaries, SCPs).
- Changes to logging and security controls (CloudTrail, GuardDuty, Security Hub, Config, firewall/WAF rules).
- Data-impacting operations on high-value services (S3, RDS, DynamoDB, Secrets Manager, KMS).
- Check if similar `AssumeRoot` activity has occurred recently from the same `source.ip`, principal, or member account.
- Engage application, data, and platform owners for the impacted account(s) to:
- Assess potential data exposure, integrity issues, or downtime.
- Determine whether any actions conflict with intended change plans.
- **Hardening and preventive controls**
- Restrict and monitor `AssumeRoot` usage:
- Limit which IAM roles and identities can call `sts:AssumeRoot`, using IAM conditions (e.g., `aws:PrincipalArn`, `aws:PrincipalOrgID`, `aws:RequestedRegion`).
- Where possible, require strong authentication on the initiating principal (MFA, federated SSO, device posture).
- Add guardrails and observability:
- Use AWS Config, Security Hub, and/or AWS Organizations SCPs to:
- Detect or constrain highly privileged cross-account actions.
- Ensure logging and monitoring services cannot be disabled or modified by assumed sessions without additional friction.
- Ensure `AssumeRoot` activity is included in your SIEM dashboards and investigation playbooks.
- **Post-incident improvements**
- If activity is confirmed malicious or unsafe:
- Rotate credentials for all involved principals and review recent STS session usage for anomalies.
- Update internal runbooks to clearly define when `AssumeRoot` is allowed, who can perform it, and how it should be documented.
- Refine this rule’s exceptions or tagging strategy so that legitimate, recurring workflows are well-understood, while preserving high-fidelity visibility into new or unexpected `AssumeRoot` behavior.
### Additional information
- **[AWS IR Playbooks](https://github.com/aws-samples/aws-incident-response-playbooks/blob/c151b0dc091755fffd4d662a8f29e2f6794da52c/playbooks/)**
- **[AWS Customer Playbook Framework](https://github.com/aws-samples/aws-customer-playbook-framework/tree/a8c7b313636b406a375952ac00b2d68e89a991f2/docs)**
- **Security Best Practices:** [AWS Knowledge Center – Security Best Practices](https://aws.amazon.com/premiumsupport/knowledge-center/security-best-practices/).
"""
references = ["https://docs.aws.amazon.com/STS/latest/APIReference/API_AssumeRoot.html"]
risk_score = 73
rule_id = "962a71ae-aac9-11ef-9348-f661ea17fbce"
severity = "high"
tags = [
"Domain: Cloud",
"Data Source: AWS",
"Data Source: Amazon Web Services",
"Data Source: AWS STS",
"Resources: Investigation Guide",
"Use Case: Identity and Access Audit",
"Tactic: Privilege Escalation",
]
timestamp_override = "event.ingested"
type = "new_terms"
query = '''
data_stream.dataset: "aws.cloudtrail"
and event.provider: "sts.amazonaws.com"
and event.action: "AssumeRoot"
and event.outcome: "success"
'''
[[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 = "T1548"
name = "Abuse Elevation Control Mechanism"
reference = "https://attack.mitre.org/techniques/T1548/"
[[rule.threat.technique.subtechnique]]
id = "T1548.005"
name = "Temporary Elevated Cloud Access"
reference = "https://attack.mitre.org/techniques/T1548/005/"
[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 = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.003"
name = "Additional Cloud Roles"
reference = "https://attack.mitre.org/techniques/T1098/003/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[[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.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.resources.account_id",
"aws.cloudtrail.resources.type",
"event.action",
"event.outcome",
"cloud.account.id",
"cloud.region",
"aws.cloudtrail.request_parameters",
"aws.cloudtrail.response_elements"
]
[rule.new_terms]
field = "new_terms_fields"
value = ["aws.cloudtrail.user_identity.arn", "aws.cloudtrail.resources.account_id"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-7d"
Stages and Predicates
Stage 1: new_terms
data_stream.dataset: "aws.cloudtrail"
and event.provider: "sts.amazonaws.com"
and event.action: "AssumeRoot"
and event.outcome: "success"
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"aws.cloudtrail" |
event.action | eq |
| field:"EventType" kind:eq value:"AssumeRoot" |
event.outcome | eq |
| field:"event.outcome" kind:eq value:"success" |
event.provider | eq |
| field:"Provider_Name" kind:eq value:"sts.amazonaws.com" |
Azure RBAC Built-In Administrator Roles Assigned
#Identifies when a user is assigned a built-in administrator role in Azure RBAC (Role-Based Access Control). These roles provide significant privileges and can be abused by attackers for lateral movement, persistence, or privilege escalation. The privileged built-in administrator roles include Owner, Contributor, User Access Administrator, Azure File Sync Administrator, Reservations Administrator, and Role Based Access Control Administrator.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation |
Telemetry Coverage
Rule Body
[metadata]
creation_date = "2025/09/15"
integration = ["azure"]
maturity = "production"
updated_date = "2026/08/26"
[rule]
author = ["Elastic"]
description = """
Identifies when a user is assigned a built-in administrator role in Azure RBAC (Role-Based Access Control). These roles
provide significant privileges and can be abused by attackers for lateral movement, persistence, or privilege
escalation. The privileged built-in administrator roles include Owner, Contributor, User Access Administrator, Azure
File Sync Administrator, Reservations Administrator, and Role Based Access Control Administrator.
"""
from = "now-9m"
index = ["filebeat-*", "logs-azure.activitylogs-*"]
language = "kuery"
license = "Elastic License v2"
name = "Azure RBAC Built-In Administrator Roles Assigned"
note = """## Triage and analysis
### Investigating Azure RBAC Built-In Administrator Roles Assigned
This rule identifies when a user is assigned a built-in administrator role in Azure RBAC (Role-Based Access Control). These roles provide significant privileges and can be abused by attackers for lateral movement, persistence, or privilege escalation. The privileged built-in administrator roles include Owner, Contributor, User Access Administrator, Azure File Sync Administrator, Reservations Administrator, and Role Based Access Control Administrator. Assignment can be done via the Azure portal, Azure CLI, PowerShell, or through API calls. Monitoring these assignments helps detect potential unauthorized privilege escalations.
#### Privileged Built-In Administrator Roles
- Contributor: b24988ac-6180-42a0-ab88-20f7382dd24c
- Owner: 8e3af657-a8ff-443c-a75c-2fe8c4bcb635
- Azure File Sync Administrator: 92b92042-07d9-4307-87f7-36a593fc5850
- Reservations Administrator: a8889054-8d42-49c9-bc1c-52486c10e7cd
- Role Based Access Control Administrator: f58310d9-a9f6-439a-9e8d-f62e7b41a168
- User Access Administrator: 18d7d88d-d35e-4fb5-a5c3-7773c20a72d9
### Possible investigation steps
- Identify the user who assigned the role and examine their recent activity for any suspicious actions.
- Review the source IP address and location associated with the role assignment event to assess if it aligns with expected user behavior or if it indicates potential unauthorized access.
- Check the history of role assignments for the user who was assigned the role to determine if this is a recurring pattern or a one-time event.
- Additionally, identify the lifetime of the targeted user account to determine if it is a newly created account or an existing one.
- Determine if the user assigning the role historically has the necessary permissions to assign such roles and has done so in the past.
- Investigate any recent changes or activities performed by the newly assigned administrator to identify any suspicious actions or configurations that may have been altered.
- Correlate with other logs, such as Microsoft Entra ID sign-in logs, to identify any unusual access patterns or behaviors for the user.
### False positive analysis
- Legitimate administrators may assign built-in administrator roles during routine operations, maintenance or as required for onboarding new staff.
- Azure Kubernetes Service control-plane operations may assign the Contributor role to service principals. Assignments initiated by the Microsoft-owned AzureContainerService application are excluded.
- Repeated writes for the same role assignment ID by the same initiating principal are suppressed for one hour.
- Review internal tickets, change logs, or admin activity dashboards for approved operations.
### Response and remediation
- If administrative assignment was not authorized:
- Immediately remove the built-in administrator role from the account.
- Disable or lock the account and begin credential rotation.
- Audit activity performed by the account after elevation, especially changes to role assignments and resource access.
- If suspicious:
- Notify the user and confirm whether they performed the action.
- Check for any automation or scripts that could be exploiting unused elevated access paths.
- Review conditional access and PIM (Privileged Identity Management) configurations to limit elevation without approval.
- Strengthen posture:
- Require MFA and approval for all privilege escalation actions.
- Consider enabling JIT (Just-in-Time) access with expiration.
"""
references = [
"https://learn.microsoft.com/en-us/azure/role-based-access-control/built-in-roles",
"https://orca.security/resources/research-pod/azure-identity-access-management-iam-active-directory-ad/",
"https://www.microsoft.com/en-us/security/blog/2025/08/27/storm-0501s-evolving-techniques-lead-to-cloud-based-ransomware/",
]
risk_score = 73
rule_id = "1a1046f4-9257-11f0-9a42-f661ea17fbce"
severity = "high"
tags = [
"Domain: Cloud",
"Domain: Identity",
"Data Source: Azure",
"Data Source: Azure Activity Logs",
"Platform: Azure",
"Rule Type: Custom Query (KQL)",
"Use Case: Identity and Access Audit",
"Tactic: Privilege Escalation",
"Tactic: Persistence",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset: azure.activitylogs and
event.action: "MICROSOFT.AUTHORIZATION/ROLEASSIGNMENTS/WRITE" and
azure.activitylogs.properties.requestbody.properties.roleDefinitionId:
(
*18d7d88d-d35e-4fb5-a5c3-7773c20a72d9* or
*f58310d9-a9f6-439a-9e8d-f62e7b41a168* or
*b24988ac-6180-42a0-ab88-20f7382dd24c* or
*8e3af657-a8ff-443c-a75c-2fe8c4bcb635* or
*92b92042-07d9-4307-87f7-36a593fc5850* or
*a8889054-8d42-49c9-bc1c-52486c10e7cd*
) and not (
azure.activitylogs.identity.claims.appid: "7319c514-987d-4e9b-ac3d-d38c4f427f4c" and
azure.activitylogs.identity.authorization.evidence.role: "Service Owner role" and
azure.activitylogs.identity.authorization.evidence.principal_type: "ServicePrincipal" and
azure.activitylogs.properties.requestbody.properties.roleDefinitionId: *b24988ac-6180-42a0-ab88-20f7382dd24c*
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.003"
name = "Additional Cloud Roles"
reference = "https://attack.mitre.org/techniques/T1098/003/"
[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 = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.003"
name = "Additional Cloud Roles"
reference = "https://attack.mitre.org/techniques/T1098/003/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[rule.alert_suppression]
group_by = [
"azure.activitylogs.identity.authorization.evidence.role_assignment_id",
"azure.activitylogs.identity.authorization.evidence.principal_id",
]
missing_fields_strategy = "doNotSuppress"
[rule.alert_suppression.duration]
unit = "h"
value = 1
Stages and Predicates
Stage 1: query
data_stream.dataset: azure.activitylogs and
event.action: "MICROSOFT.AUTHORIZATION/ROLEASSIGNMENTS/WRITE" and
azure.activitylogs.properties.requestbody.properties.roleDefinitionId:
(
*18d7d88d-d35e-4fb5-a5c3-7773c20a72d9* or
*f58310d9-a9f6-439a-9e8d-f62e7b41a168* or
*b24988ac-6180-42a0-ab88-20f7382dd24c* or
*8e3af657-a8ff-443c-a75c-2fe8c4bcb635* or
*92b92042-07d9-4307-87f7-36a593fc5850* or
*a8889054-8d42-49c9-bc1c-52486c10e7cd*
) and not (
azure.activitylogs.identity.claims.appid: "7319c514-987d-4e9b-ac3d-d38c4f427f4c" and
azure.activitylogs.identity.authorization.evidence.role: "Service Owner role" and
azure.activitylogs.identity.authorization.evidence.principal_type: "ServicePrincipal" and
azure.activitylogs.properties.requestbody.properties.roleDefinitionId: *b24988ac-6180-42a0-ab88-20f7382dd24c*
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
azure.activitylogs.properties.requestbody.properties.roleDefinitionId | wildcard |
| field:"azure.activitylogs.properties.requestbody.properties.roleDefinitionId" kind:wildcard |
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"azure.activitylogs" |
event.action | eq |
| field:"EventType" kind:eq value:"MICROSOFT.AUTHORIZATION/ROLEASSIGNMENTS/WRITE" |
Exclusions
The rule actively suppresses these predicates.
Entra ID Unusual Cloud Device Registration
#Detects a sequence of events in Microsoft Entra ID indicative of suspicious cloud-based device registration via automated tooling like ROADtools or similar frameworks. This behavior involves adding a device via the Device Registration Service, followed by the assignment of registered users and owners — a pattern consistent with techniques used to establish persistence or acquire a Primary Refresh Token (PRT). ROADtools and similar tooling leave distinct telemetry signatures such as the Microsoft.OData.Client user agent. These sequences are uncommon in typical user behavior and may reflect abuse of device trust for session hijacking or silent token replay.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence | |
| Privilege Escalation |
Telemetry Coverage
| Platform | Record / event type |
|---|---|
| Azure | Add device |
| Azure | Add registered owner to device |
| Azure | Add registered users to device |
Rules Detecting the Same Action
These rules filter on the same operation.
- Azure Device No Longer Managed or Compliant (Sigma)
- Azure Device or Configuration Modified or Deleted (Sigma)
- Entra ID AiTM Phishing-Kit Chain Detected (Elastic)
- Entra ID Device Registration with Phishing Kit Default OS Build (Elastic)
- Entra ID Device Registration with ROADtools Default OS Build (Elastic)
- Entra ID Deviceless Windows Hello Sign-in Followed by Device Registration (Elastic)
- Entra ID Multiple Device Registrations by a Single User (Elastic)
- Entra ID Protection User Alert and Device Registration (Elastic)
Rule Body
[metadata]
creation_date = "2025/06/13"
integration = ["azure"]
maturity = "production"
updated_date = "2026/04/10"
[rule]
author = ["Elastic"]
description = """
Detects a sequence of events in Microsoft Entra ID indicative of suspicious cloud-based device registration via automated
tooling like ROADtools or similar frameworks. This behavior involves adding a device via the Device Registration Service,
followed by the assignment of registered users and owners — a pattern consistent with techniques used to establish persistence or
acquire a Primary Refresh Token (PRT). ROADtools and similar tooling leave distinct telemetry signatures such as the
`Microsoft.OData.Client` user agent. These sequences are uncommon in typical user behavior and may reflect abuse of device
trust for session hijacking or silent token replay.
"""
from = "now-30m"
interval = "15m"
index = ["filebeat-*", "logs-azure.auditlogs-*"]
language = "eql"
license = "Elastic License v2"
name = "Entra ID Unusual Cloud Device Registration"
note = """## Triage and analysis
### Investigating Entra ID Unusual Cloud Device Registration
This rule detects a sequence of Microsoft Entra ID audit events consistent with cloud device registration abuse via ROADtools or similar automation frameworks. The activity includes three correlated events:
1. Add device operation from the Device Registration Service using suspicious user-agents (`Dsreg/*`, `DeviceRegistrationClient`, or `Microsoft.OData.Client/*`).
2. Addition of a registered user with an `enterprise registration` URN.
3. Assignment of a registered owner to the device.
This pattern has been observed in OAuth phishing and PRT abuse campaigns where adversaries silently register a cloud device to obtain persistent, trusted access.
### Possible investigation steps
- Identify the user principal associated with the device registration.
- Review the `azure.auditlogs.identity` field to confirm the Device Registration Service initiated the request.
- Check the user-agent in `azure.auditlogs.properties.additional_details.value`. Known attack tooling signatures include:
- `Dsreg/10.0 (Windows X.X.X)` - ROADtools Windows device registration
- `DeviceRegistrationClient` - ROADtools MacOS/Android device registration
- `Microsoft.OData.Client/*` - .NET-based tools or Graph SDK
- Examine the OS version in the modified properties to identify potentially suspicious or outdated versions.
- Verify the URN in the new value field (`urn:ms-drs:enterpriseregistration.windows.net`) is not being misused.
- Use `azure.correlation_id` to pivot across all three steps of the registration flow.
- Pivot to `azure.signinlogs` to detect follow-on activity using the new device, such as sign-ins involving refresh or primary refresh tokens.
- Look for signs of persistence or lateral movement enabled by the newly registered device.
- Identify the registered device name by reviewing `azure.auditlogs.properties.target_resources.0.display_name` and confirm it's expected for the user or organization.
- Use the correlation ID `azure.correlation_id` to pivot into registered user events from Entra ID audit logs and check `azure.auditlogs.properties.target_resources.0.user_principal_name` to identify the user associated with the device registration.
- Review any activity for this user from Entra ID sign-in logs, where the incoming token type is a `primaryRefreshToken`.
### False positive analysis
- Some MDM, autopilot provisioning flows, or third-party device management tools may generate similar sequences. Validate against known provisioning tools, expected rollout windows, and device inventory.
- Investigate whether the device name, OS version, and registration details align with normal IT workflows.
- Check if the user-agent corresponds to legitimate automation or tooling used by your organization.
### Response and remediation
- If confirmed malicious, remove the registered device from Entra ID.
- Revoke refresh tokens and primary refresh tokens associated with the user and device.
- Disable the user account and initiate password reset and identity verification procedures.
- Review audit logs and sign-in activity for additional indicators of persistence or access from the rogue device.
- Tighten conditional access policies to restrict device registration and enforce compliance or hybrid join requirements.
"""
references = [
"https://www.volexity.com/blog/2025/04/22/phishing-for-codes-russian-threat-actors-target-microsoft-365-oauth-workflows/",
"https://github.com/dirkjanm/ROADtools",
"https://dirkjanm.io/introducing-roadtools-token-exchange-roadtx/"
]
risk_score = 47
rule_id = "90efea04-5675-11f0-8f80-f661ea17fbcd"
severity = "medium"
tags = [
"Domain: Cloud",
"Domain: Identity",
"Data Source: Azure",
"Data Source: Microsoft Entra ID",
"Data Source: Microsoft Entra ID Audit Logs",
"Use Case: Identity and Access Audit",
"Tactic: Persistence",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
sequence by azure.correlation_id with maxspan=5m
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.identity == "Device Registration Service" and
azure.auditlogs.operation_name == "Add device" and
(
azure.auditlogs.properties.additional_details.value like "Microsoft.OData.Client/*" or
azure.auditlogs.properties.additional_details.value like "Dsreg/*" or
azure.auditlogs.properties.additional_details.value == "DeviceRegistrationClient"
) and
`azure.auditlogs.properties.target_resources.0.modified_properties.1.display_name` == "CloudAccountEnabled" and
`azure.auditlogs.properties.target_resources.0.modified_properties.1.new_value` == "[true]"]
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.operation_name == "Add registered users to device" and
`azure.auditlogs.properties.target_resources.0.modified_properties.2.new_value` like "*urn:ms-drs:enterpriseregistration.windows.net*"]
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.operation_name == "Add registered owner to device"]
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.005"
name = "Device Registration"
reference = "https://attack.mitre.org/techniques/T1098/005/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.005"
name = "Device Registration"
reference = "https://attack.mitre.org/techniques/T1098/005/"
[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"
Stages and Predicates
Ordered sequence: each step below must occur in order within 5m, correlated by azure.correlation_id.
Stage 1: any
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.identity == "Device Registration Service" and
azure.auditlogs.operation_name == "Add device" and
(
azure.auditlogs.properties.additional_details.value like "Microsoft.OData.Client/*" or
azure.auditlogs.properties.additional_details.value like "Dsreg/*" or
azure.auditlogs.properties.additional_details.value == "DeviceRegistrationClient"
) and
`azure.auditlogs.properties.target_resources.0.modified_properties.1.display_name` == "CloudAccountEnabled" and
`azure.auditlogs.properties.target_resources.0.modified_properties.1.new_value` == "[true]"]
Stage 2: any
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.operation_name == "Add registered users to device" and
`azure.auditlogs.properties.target_resources.0.modified_properties.2.new_value` like "*urn:ms-drs:enterpriseregistration.windows.net*"]
Stage 3: any
[any where data_stream.dataset == "azure.auditlogs" and
azure.auditlogs.operation_name == "Add registered owner to device"]
Indicators
These rows show field, operator, and value matches.
ExecuteWithPrivileges Prompt via Unsigned or Untrusted Application
#Detects the use of the AuthorizationExecuteWithPrivileges function to provide the user a password prompt via an unsigned or untrusted application. Threat actors have recently used this in order to trick users into providing their malicious application with higher privileges.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation |
Telemetry Coverage
Rule Body
[rule]
description = """
Detects the use of the AuthorizationExecuteWithPrivileges function to provide the user a password prompt via an unsigned
or untrusted application. Threat actors have recently used this in order to trick users into providing their malicious
application with higher privileges.
"""
id = "559fc9c7-f2fd-4fd9-af07-df8b7408e0b8"
license = "Elastic License v2"
name = "ExecuteWithPrivileges Prompt via Unsigned or Untrusted Application"
os_list = ["macos"]
reference = ["https://securelist.com/new-macos-backdoor-crypto-stealer/111778/"]
version = "1.0.3"
query = '''
process where event.type == "start" and event.action == "exec" and process.name == "security_authtrampoline" and
process.args like ("/Applications/*", "/Volumes/*") and process.args like "auth*" and
(process.parent.code_signature.exists == false or process.parent.code_signature.trusted == false) and
process.Ext.effective_parent.executable like ("/Applications/*", "/Volumes/*")
'''
min_endpoint_version = "8.10.2"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1548"
name = "Abuse Elevation Control Mechanism"
reference = "https://attack.mitre.org/techniques/T1548/"
[[threat.technique.subtechnique]]
id = "T1548.004"
name = "Elevated Execution with Prompt"
reference = "https://attack.mitre.org/techniques/T1548/004/"
[threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1548"
name = "Abuse Elevation Control Mechanism"
reference = "https://attack.mitre.org/techniques/T1548/"
[[threat.technique.subtechnique]]
id = "T1548.004"
name = "Elevated Execution with Prompt"
reference = "https://attack.mitre.org/techniques/T1548/004/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.10.2"
Stages and Predicates
Stage 1: process
process where event.type == "start" and event.action == "exec" and process.name == "security_authtrampoline" and
process.args like ("/Applications/*", "/Volumes/*") and process.args like "auth*" and
(process.parent.code_signature.exists == false or process.parent.code_signature.trusted == false) and
process.Ext.effective_parent.executable like ("/Applications/*", "/Volumes/*")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.Ext.effective_parent.executable | wildcard |
| field:"process.Ext.effective_parent.executable" kind:wildcard |
process.args | wildcard |
| field:"process.args" kind:wildcard |
process.name | eq |
| field:"process_basename" kind:eq value:"security_authtrampoline" |
process.parent.code_signature.exists | eq |
| field:"process.parent.code_signature.exists" kind:eq value:"false" |
process.parent.code_signature.trusted | eq |
| field:"process.parent.code_signature.trusted" kind:eq value:"false" |
Execution of Self-Signed Binary from Volume Mount
#Detects the execution of a binary, from a volume mount, that has been self-signed using the native Codesign tool. The specific code sign identifier scheme generated by this process matches on almost all North Korean payloads as they have used this method to sign their malware like AppleJeus, for example, and most recently the 3CX supply chain 2nd stage malware payload.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution |
Telemetry Coverage
Rule Body
[rule]
description = """
Detects the execution of a binary, from a volume mount, that has been self-signed using the native Codesign tool. The
specific code sign identifier scheme generated by this process matches on almost all North Korean payloads as they have
used this method to sign their malware like AppleJeus, for example, and most recently the 3CX supply chain 2nd stage
malware payload.
"""
id = "ac494288-08e1-4597-9a04-3526144de479"
license = "Elastic License v2"
name = "Execution of Self-Signed Binary from Volume Mount"
os_list = ["macos"]
version = "1.0.4"
query = '''
process where event.type == "start" and event.action == "exec" and
process.code_signature.signing_id regex~ """[A-Za-z0-9\_\s]{2,}\-[a-z0-9]{40}""" and
process.code_signature.trusted == false and
process.args_count <= 2 and
process.executable like "/Volumes/*"
'''
min_endpoint_version = "8.5.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1059"
name = "Command and Scripting Interpreter"
reference = "https://attack.mitre.org/techniques/T1059/"
[[threat.technique.subtechnique]]
id = "T1059.004"
name = "Unix Shell"
reference = "https://attack.mitre.org/techniques/T1059/004/"
[threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[internal]
min_endpoint_version = "8.5.0"
Stages and Predicates
Stage 1: process
process where event.type == "start" and event.action == "exec" and
process.code_signature.signing_id regex~ """[A-Za-z0-9\_\s]{2,}\-[a-z0-9]{40}""" and
process.code_signature.trusted == false and
process.args_count <= 2 and
process.executable like "/Volumes/*"
Indicators
These rows show field, operator, and value matches.
GKE Privileged Pod Created
#Detects successful GKE audit events where a pod is created with allowPrivilegeEscalation enabled. This weakens container isolation and can help an attacker escalate toward host access. Standalone pods are included; workloads owned by ReplicaSet, DaemonSet, or StatefulSet controllers are excluded.
Known False Positives
- Debug or break-glass pods may enable privilege escalation intentionally. Exclude trusted namespaces, users, or deployment patterns after baselining.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Privilege Escalation |
Telemetry Coverage
| Platform | Record / event type |
|---|---|
| Kubernetes | create-pods: create pods |
Rules Detecting the Same Action
These rules filter on the same operation.
- Azure AKS Attempted User Exec into Pod (Elastic)
- Container With A hostPath Mount Created (Sigma)
- Creation Of Pod In System Namespace (Sigma)
- Direct Interactive Kubernetes API Request by Unusual Utilities (Elastic)
- Exec into Pod (Panther)
- GCP Break-glass Container Workload Deployed (Sigma)
- GCP K8s Pod Attached To Node Host Network (Panther)
- GCP K8S Pod Create Or Modify Host Path Volume Mount (Panther)
Rule Body
[metadata]
creation_date = "2026/06/30"
integration = ["gcp"]
maturity = "production"
updated_date = "2026/06/30"
[rule]
author = ["Elastic"]
description = """
Detects successful GKE audit events where a pod is created with allowPrivilegeEscalation enabled. This weakens
container isolation and can help an attacker escalate toward host access. Standalone pods are included; workloads owned
by ReplicaSet, DaemonSet, or StatefulSet controllers are excluded.
"""
false_positives = [
"""
Debug or break-glass pods may enable privilege escalation intentionally. Exclude trusted namespaces, users, or
deployment patterns after baselining.
""",
]
index = ["logs-gcp.audit-*"]
language = "kuery"
license = "Elastic License v2"
name = "GKE Privileged Pod Created"
note = """## Triage and analysis
### Investigating GKE Privileged Pod Created
Review `user.email`, `orchestrator.resource.name`, `orchestrator.namespace`, and the pod spec in `gcp.audit.request`.
Confirm whether allowPrivilegeEscalation is required for the workload.
### Investigation steps
- Identify the actor and source (`user.email`, `source.ip`, `user_agent.original`).
- Inspect container images and securityContext in the audit request payload.
- Correlate with RBAC changes, secret access, or exec activity from the same identity.
### False positives
- One-off admin debugging pods; tune by user or namespace when documented.
## Setup
The GCP Fleet integration with GKE audit logs enabled is required to be compatible with this rule."""
references = [
"https://cloud.google.com/kubernetes-engine/docs/how-to/audit-logging",
"https://kubernetes.io/docs/tasks/configure-pod-container/security-context/",
]
risk_score = 47
rule_id = "a7b984e4-16ff-405b-80be-31a94a03e929"
severity = "medium"
tags = [
"Domain: Cloud",
"Domain: Kubernetes",
"Data Source: GCP",
"Data Source: Google Cloud Platform",
"Use Case: Threat Detection",
"Tactic: Privilege Escalation",
"Tactic: Execution",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset:gcp.audit and event.action:"io.k8s.core.v1.pods.create" and event.outcome:success and
gcp.audit.request.spec.containers.securityContext.allowPrivilegeEscalation:true and
not gcp.audit.request.metadata.ownerReferences.kind:("ReplicaSet" or "DaemonSet" or "StatefulSet")
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1611"
name = "Escape to Host"
reference = "https://attack.mitre.org/techniques/T1611/"
[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 = "T1610"
name = "Deploy Container"
reference = "https://attack.mitre.org/techniques/T1610/"
[rule.threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
Stages and Predicates
Stage 1: query
data_stream.dataset:gcp.audit and event.action:"io.k8s.core.v1.pods.create" and event.outcome:success and
gcp.audit.request.spec.containers.securityContext.allowPrivilegeEscalation:true and
not gcp.audit.request.metadata.ownerReferences.kind:("ReplicaSet" or "DaemonSet" or "StatefulSet")
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
gcp.audit.request.metadata.ownerReferences.kind | in | DaemonSet, ReplicaSet, StatefulSet | excludes:gcp.audit.request.metadata.ownerReferences.kind field:"gcp.audit.request.metadata.ownerReferences.kind" value:"DaemonSet" field:"gcp.audit.request.metadata.ownerReferences.kind" value:"ReplicaSet" field:"gcp.audit.request.metadata.ownerReferences.kind" value:"StatefulSet" |
Kernel Unpacking Activity
#This rule detects kernel unpacking activity through several built-in Linux utilities. Attackers may use these utilities to unpack kernel images and modules to search for vulnerabilities or to modify the kernel.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth | |
| Discovery |
Rule Body
[metadata]
creation_date = "2025/01/07"
integration = ["endpoint"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
description = """
This rule detects kernel unpacking activity through several built-in Linux utilities. Attackers may use these utilities
to unpack kernel images and modules to search for vulnerabilities or to modify the kernel.
"""
from = "now-9m"
index = ["logs-endpoint.events.process*"]
language = "eql"
license = "Elastic License v2"
name = "Kernel Unpacking Activity"
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 Kernel Unpacking Activity
Kernel unpacking involves using utilities to extract or inspect kernel images and modules, often for legitimate maintenance or updates. However, adversaries exploit this to identify vulnerabilities or alter the kernel for malicious purposes. The detection rule identifies suspicious unpacking by monitoring specific Linux utilities and command patterns, excluding benign processes like system updates, to flag potential threats.
### Possible investigation steps
- Review the process details to identify the specific utility used for unpacking, such as "file", "unlzma", "gunzip", etc., and verify if the usage aligns with typical system maintenance activities.
- Examine the parent process name and arguments, especially those involving "/boot/*", to determine if the unpacking activity is part of a legitimate system operation or an unauthorized action.
- Check the user account associated with the process to assess if the activity was initiated by a legitimate user or an unauthorized entity.
- Investigate the timing of the event to see if it coincides with scheduled maintenance or updates, which might explain the unpacking activity.
- Look for any related alerts or logs that might indicate further suspicious behavior, such as attempts to modify kernel modules or other system files following the unpacking activity.
- Cross-reference the event with recent system updates or patches to rule out false positives related to legitimate system operations.
### False positive analysis
- System updates and maintenance activities can trigger this rule when legitimate processes unpack kernel images. To manage this, exclude processes initiated by known update utilities like "mkinitramfs" from triggering alerts.
- Custom scripts or administrative tasks that involve unpacking kernel images for legitimate purposes may also cause false positives. Identify and whitelist these scripts or processes by their specific command patterns or parent process names.
- Backup or recovery operations that involve accessing or unpacking kernel files might be flagged. Review these operations and exclude them by specifying the responsible process names or arguments in the detection rule.
- Automated security tools that scan or analyze kernel images for compliance or vulnerability assessments can be mistaken for malicious activity. Exclude these tools by adding their process names to the exception list.
### Response and remediation
- Isolate the affected system from the network to prevent potential lateral movement or further exploitation by the adversary.
- Terminate any suspicious processes identified by the detection rule, especially those involving the unpacking of kernel images or modules.
- Conduct a thorough review of the system's kernel and module integrity using trusted tools to ensure no unauthorized modifications have been made.
- Restore the system from a known good backup if any unauthorized changes to the kernel or system files are detected.
- Update the system's kernel and all related packages to the latest versions to mitigate any known vulnerabilities that could be exploited.
- Monitor the system for any recurring suspicious activity, focusing on the use of utilities and command patterns identified in the detection rule.
- Escalate the incident to the security operations team for further investigation and to assess the potential impact on other systems within the network."""
references = ["https://www.elastic.co/security-labs/declawing-pumakit"]
risk_score = 47
rule_id = "4f725dc5-ae44-46c1-9ac5-99f6f7a70d8a"
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 = "medium"
tags = [
"Domain: Endpoint",
"OS: Linux",
"Use Case: Threat Detection",
"Tactic: Discovery",
"Tactic: Defense Evasion",
"Data Source: Elastic Defend",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "linux" and event.type == "start" and event.action == "exec" and
(process.parent.args like "/boot/*" or process.args like "/boot/*") and (
(process.name in ("file", "unlzma", "gunzip", "unxz", "bunzip2", "unzstd", "unzip", "tar")) or
(process.name == "grep" and process.args == "ELF") or
(process.name in ("lzop", "lz4") and process.args in ("-d", "--decode"))
) and
not (
process.parent.name == "mkinitramfs" or
process.parent.executable like (
"/usr/lib/needrestart/vmlinuz-get-version", "/usr/libexec/platform-python*", "/tmp/newroot/usr/libexec/platform-python*",
"/usr/bin/kdumpctl", "/usr/bin/stap-report", "/usr/sbin/nv-update-initrd"
) or
process.parent.command_line like "*ansible*" or
process.parent.args == "/usr/bin/kdumpctl"
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1082"
name = "System Information Discovery"
reference = "https://attack.mitre.org/techniques/T1082/"
[rule.threat.tactic]
id = "TA0007"
name = "Discovery"
reference = "https://attack.mitre.org/tactics/TA0007/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1014"
name = "Rootkit"
reference = "https://attack.mitre.org/techniques/T1014/"
[[rule.threat.technique]]
id = "T1140"
name = "Deobfuscate/Decode Files or Information"
reference = "https://attack.mitre.org/techniques/T1140/"
[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 == "linux" and event.type == "start" and event.action == "exec" and
(process.parent.args like "/boot/*" or process.args like "/boot/*") and (
(process.name in ("file", "unlzma", "gunzip", "unxz", "bunzip2", "unzstd", "unzip", "tar")) or
(process.name == "grep" and process.args == "ELF") or
(process.name in ("lzop", "lz4") and process.args in ("-d", "--decode"))
) and
not (
process.parent.name == "mkinitramfs" or
process.parent.executable like (
"/usr/lib/needrestart/vmlinuz-get-version", "/usr/libexec/platform-python*", "/tmp/newroot/usr/libexec/platform-python*",
"/usr/bin/kdumpctl", "/usr/bin/stap-report", "/usr/sbin/nv-update-initrd"
) or
process.parent.command_line like "*ansible*" or
process.parent.args == "/usr/bin/kdumpctl"
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.args | eq |
| field:"process.args" kind:eq value:"ELF" |
process.args | in |
| field:"process.args" kind:in |
process.args | wildcard |
| field:"process.args" kind:wildcard value:"/boot/*" |
process.name | eq |
| field:"process_basename" kind:eq value:"grep" |
process.name | in |
| field:"process_basename" kind:in |
process.parent.args | wildcard |
| field:"process.parent.args" kind:wildcard value:"/boot/*" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.parent.args | eq | /usr/bin/kdumpctl | excludes:process.parent.args field:"process.parent.args" value:"/usr/bin/kdumpctl" |
process.parent.command_line | match | ansible | excludes:process.parent.command_line field:"process.parent.command_line" value:"ansible" |
process.parent.executable | wildcard | /usr/lib/needrestart/vmlinuz-get-version, /usr/libexec/platform-python*, /tmp/newroot/usr/libexec/platform-python*, /usr/bin/kdumpctl, /usr/bin/stap-report, /usr/sbin/nv-update-initrd | excludes:process.parent.executable |
process.parent.name | eq | mkinitramfs | excludes:process.parent.name field:"process.parent.name" value:"mkinitramfs" |
Kubernetes RBAC Wildcard Elevation on Existing Role
#Flags an existing Role or ClusterRole being changed (patch or update) so the effective rules become cluster-admin-like: wildcard on every API resource and wildcard on every verb. That is usually a deliberate privilege expansion, not a typo. RequestResponse audit and the response body are required so the detection reads the merged role after apply; loopback source IPs are ignored.
Known False Positives
- Platform installers, GitOps controllers, and emergency break-glass roles sometimes ship or widen wildcard ClusterRoles; correlate with change records and narrow by user or service account when baselined.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation |
Telemetry Coverage
Rules Detecting the Same Action
These rules filter on the same operation.
- Direct Interactive Kubernetes API Request by Unusual Utilities (Elastic)
- GKE Creation or Modification of Sensitive Role (Elastic)
- GKE RBAC Wildcard Elevation on Existing Role (Elastic)
- GKE Sensitive RBAC Change Followed by Workload Modification (Elastic)
- GKE Service Account Modified RBAC Objects (Elastic)
- Kubernetes Creation or Modification of Sensitive Role (Elastic)
- Kubernetes Sensitive RBAC Change Followed by Workload Modification (Elastic)
- Kubernetes Service Account Modified RBAC Objects (Elastic)
Rule Body
[metadata]
creation_date = "2026/04/27"
integration = ["kubernetes"]
maturity = "production"
updated_date = "2026/04/27"
[rule]
author = ["Elastic"]
description = """
Flags an existing Role or ClusterRole being changed (patch or update) so the effective rules become cluster-admin-like:
wildcard on every API resource and wildcard on every verb. That is usually a deliberate privilege expansion, not a typo.
RequestResponse audit and the response body are required so the detection reads the merged role after apply; loopback
source IPs are ignored.
"""
false_positives = [
"""
Platform installers, GitOps controllers, and emergency break-glass roles sometimes ship or widen wildcard
ClusterRoles; correlate with change records and narrow by user or service account when baselined.
""",
]
from = "now-9m"
interval = "5m"
language = "esql"
license = "Elastic License v2"
name = "Kubernetes RBAC Wildcard Elevation on Existing Role"
note = """## Triage and analysis
### Investigating Kubernetes RBAC Wildcard Elevation on Existing Role
Someone patched or updated a Role or ClusterRole so the stored rules grant star verbs and star resources—near
cluster-admin breadth on that scope. Confirm the actor (user, group, impersonation), client, and non-loopback source
IP; then see who can bind that role.
### Possible investigation steps
- Diff the role YAML before and after; list RoleBindings and ClusterRoleBindings that reference it and which subjects
gained the widened access.
- In the same window, check secret reads, exec, and further RBAC changes from the same identity.
### False positive analysis
- Approved GitOps or vendor upgrades sometimes widen a known ClusterRole; allowlist stable automation when documented.
### Response and remediation
- Revert the role, drop unexpected bindings, rotate credentials for the actor, and block future wildcard RBAC outside
governed pipelines (policy-as-code, PR-only RBAC).
"""
references = [
"https://attack.mitre.org/techniques/T1098/006/",
"https://kubernetes.io/docs/reference/access-authn-authz/rbac/",
]
risk_score = 73
rule_id = "c8f4a2e1-9b3d-4c7e-8f2a-1d0e5b6c7a89"
severity = "high"
tags = [
"Data Source: Kubernetes",
"Domain: Kubernetes",
"Use Case: Threat Detection",
"Tactic: Privilege Escalation",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "esql"
query = '''
from logs-kubernetes.audit_logs-* metadata _id, _index, _version
| where
kubernetes.audit.objectRef.resource in ("roles", "clusterroles") and
kubernetes.audit.verb in ("update", "patch") and
`kubernetes.audit.annotations.authorization_k8s_io/decision` == "allow" and
kubernetes.audit.level == "RequestResponse" and
kubernetes.audit.stage == "ResponseComplete" and
kubernetes.audit.sourceIPs is not null and
not kubernetes.audit.sourceIPs in ("::1", "127.0.0.1") and
KQL(""" kubernetes.audit.responseObject.rules.verbs:"*" and kubernetes.audit.responseObject.rules.resources:"*" """)
| keep user.name, user_agent.original, event.action, source.ip, kubernetes.audit.verb, kubernetes.audit.objectRef.resource, kubernetes.audit.objectRef.name, kubernetes.audit.requestURI, kubernetes.audit.user.username, kubernetes.audit.user.groups, `kubernetes.audit.annotations.authorization_k8s_io/decision`, event.original, _id, _version, _index, data_stream.namespace
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1098"
name = "Account Manipulation"
reference = "https://attack.mitre.org/techniques/T1098/"
[[rule.threat.technique.subtechnique]]
id = "T1098.006"
name = "Additional Container Cluster Roles"
reference = "https://attack.mitre.org/techniques/T1098/006/"
[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"
Stages and Predicates
Stage 1: from
from logs-kubernetes.audit_logs-* metadata _id, _index, _version
Stage 2: where
| where
kubernetes.audit.objectRef.resource in ("roles", "clusterroles") and
kubernetes.audit.verb in ("update", "patch") and
`kubernetes.audit.annotations.authorization_k8s_io/decision` == "allow" and
kubernetes.audit.level == "RequestResponse" and
kubernetes.audit.stage == "ResponseComplete" and
kubernetes.audit.sourceIPs is not null and
not kubernetes.audit.sourceIPs in ("::1", "127.0.0.1") and
KQL(""" kubernetes.audit.responseObject.rules.verbs:"*" and kubernetes.audit.responseObject.rules.resources:"*" """)
Stage 3: keep
| keep user.name, user_agent.original, event.action, source.ip, kubernetes.audit.verb, kubernetes.audit.objectRef.resource, kubernetes.audit.objectRef.name, kubernetes.audit.requestURI, kubernetes.audit.user.username, kubernetes.audit.user.groups, `kubernetes.audit.annotations.authorization_k8s_io/decision`, event.original, _id, _version, _index, data_stream.namespace
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
kubernetes.audit.sourceIPs | in | 127.0.0.1, ::1 | excludes:kubernetes.audit.sourceIPs field:"kubernetes.audit.sourceIPs" value:"127.0.0.1" field:"kubernetes.audit.sourceIPs" value:"::1" |
Output Fields
These fields are emitted when the rule matches.
| Field | Source |
|---|---|
user.name | KEEP user.name |
user_agent.original | KEEP user_agent.original |
event.action | KEEP event.action |
source.ip | KEEP source.ip |
kubernetes.audit.verb | KEEP kubernetes.audit.verb |
kubernetes.audit.objectRef.resource | KEEP kubernetes.audit.objectRef.resource |
kubernetes.audit.objectRef.name | KEEP kubernetes.audit.objectRef.name |
kubernetes.audit.requestURI | KEEP kubernetes.audit.requestURI |
kubernetes.audit.user.username | KEEP kubernetes.audit.user.username |
kubernetes.audit.user.groups | KEEP kubernetes.audit.user.groups |
`kubernetes.audit.annotations.authorization_k8s_io/decision` | KEEP `kubernetes.audit.annotations.authorization_k8s_io/decision` |
event.original | KEEP event.original |
_id | KEEP _id |
_version | KEEP _version |
_index | KEEP _index |
data_stream.namespace | KEEP data_stream.namespace |
Loadable Kernel Module Load via Forked Memory File Descriptor
#This rule detects when a process creates a memory file descriptor using the memfd_create syscall followed by loading a loadable kernel module (LKM) via a fork. This activity indicates an active attempt to load a kernel module and should be considered highly abnormal or suspicious. This activity can occur when the modprobe userland utility is invoked, or when the underlying init_module/finit_module syscalls are used, to load a kernel module via a command and control channel.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Persistence | |
| Stealth |
Rule Body
[rule]
description = """
This rule detects when a process creates a memory file descriptor using the memfd_create syscall followed by loading a
loadable kernel module (LKM) via a fork. This activity indicates an active attempt to load a kernel module and should be
considered highly abnormal or suspicious. This activity can occur when the modprobe userland utility is invoked, or when
the underlying init_module/finit_module syscalls are used, to load a kernel module via a command and control channel.
"""
id = "76fac24d-7736-4aed-bcd0-feed2286385d"
license = "Elastic License v2"
name = "Loadable Kernel Module Load via Forked Memory File Descriptor"
os_list = ["linux"]
version = "1.0.4"
query = '''
sequence with maxspan=5s
[process where event.action == "memfd_create" and
not (
(
process.executable == "/opt/eset/efs/sbin/startd" and
process.command_line == "/opt/eset/efs/sbin/startd" and
process.parent.executable == "/usr/lib/systemd/systemd"
) or
(
process.executable == "/usr/lib/systemd/systemd" and
process.command_line == "/sbin/init" and
process.Ext.memfd.name == "memfd:system-environment-generators" and
process.parent.executable == "/usr/bin/runc"
) or
(
process.executable like "/usr/libexec/platform-python3*" and
process.parent.executable == "/usr/lib/systemd/systemd" and
process.Ext.memfd.name == "memfd:libffi"
) or
(process.parent.executable like "/snap/lxd/*/sbin/lxd" and process.command_line == "/sbin/modprobe -b zfs")
)] by process.entity_id
[process where event.action == "load_module"] by process.parent.entity_id
'''
min_endpoint_version = "9.1.4"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
tree = true
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1
tree = true
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
tree = true
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 1
tree = true
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1106"
name = "Native API"
reference = "https://attack.mitre.org/techniques/T1106/"
[threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[[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.006"
name = "Kernel Modules and Extensions"
reference = "https://attack.mitre.org/techniques/T1547/006/"
[threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1014"
name = "Rootkit"
reference = "https://attack.mitre.org/techniques/T1014/"
[[threat.technique]]
id = "T1055"
name = "Process Injection"
reference = "https://attack.mitre.org/techniques/T1055/"
[[threat.technique.subtechnique]]
id = "T1055.009"
name = "Proc Memory"
reference = "https://attack.mitre.org/techniques/T1055/009/"
[[threat.technique]]
id = "T1620"
name = "Reflective Code Loading"
reference = "https://attack.mitre.org/techniques/T1620/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "9.1.4"
Stages and Predicates
Ordered sequence: each step below must occur in order within 5s, correlated by process.entity_id, process.parent.entity_id.
Stage 1: process
[process where event.action == "memfd_create" and
not (
(
process.executable == "/opt/eset/efs/sbin/startd" and
process.command_line == "/opt/eset/efs/sbin/startd" and
process.parent.executable == "/usr/lib/systemd/systemd"
) or
(
process.executable == "/usr/lib/systemd/systemd" and
process.command_line == "/sbin/init" and
process.Ext.memfd.name == "memfd:system-environment-generators" and
process.parent.executable == "/usr/bin/runc"
) or
(
process.executable like "/usr/libexec/platform-python3*" and
process.parent.executable == "/usr/lib/systemd/systemd" and
process.Ext.memfd.name == "memfd:libffi"
) or
(process.parent.executable like "/snap/lxd/*/sbin/lxd" and process.command_line == "/sbin/modprobe -b zfs")
)] by process.entity_id
Stage 2: process
[process where event.action == "load_module"] by process.parent.entity_id
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq |
Exclusions
The rule actively suppresses these predicates.
MSBuild with Unusual Arguments
#Identifies the execution of the built-in MSBuild utility with a suspicious count of command line arguments (less than three). Adversaries may use MSBuild to proxy the execution of malicious code via a trusted Windows utility.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies the execution of the built-in MSBuild utility with a suspicious count of command line arguments (less than
three). Adversaries may use MSBuild to proxy the execution of malicious code via a trusted Windows utility.
"""
id = "6518cdaf-e6cd-4cf9-a51e-043117c3dbeb"
license = "Elastic License v2"
name = "MSBuild with Unusual Arguments"
os_list = ["windows"]
reference = ["https://lolbas-project.github.io/lolbas/Binaries/Msbuild/"]
version = "1.0.29"
query = '''
process where event.action == "start" and
process.pe.original_file_name == "MSBuild.exe" and process.args_count == 2 and
/* FP - expected developers msbuild installation directories */
not process.executable : ("?:\\Program Files (x86)\\Microsoft Visual Studio\\*",
"?:\\Program Files\\Microsoft Visual Studio\\*",
"?:\\Program Files (x86)\\MSBuild\\*",
"?:\\Program Files\\MSBuild\\*") and
not process.command_line : ("* /*", "* .\\*", "*.proj*", "*.sln*") and
/* FP - Third Party Programs except MS Office */
not (process.parent.executable : ("?:\\Program Files (x86)\\*.exe", "?:\\Program Files\\*.exe") and
not process.parent.name :
("winword.exe",
"excel.exe",
"outlook.exe",
"powerpnt.exe",
"eqnedt32.exe",
"fltldr.exe",
"mspub.exe",
"msaccess.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 = "T1127"
name = "Trusted Developer Utilities Proxy Execution"
reference = "https://attack.mitre.org/techniques/T1127/"
[[threat.technique.subtechnique]]
id = "T1127.001"
name = "MSBuild"
reference = "https://attack.mitre.org/techniques/T1127/001/"
[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: process
process where event.action == "start" and
process.pe.original_file_name == "MSBuild.exe" and process.args_count == 2 and
not process.executable : ("?:\\Program Files (x86)\\Microsoft Visual Studio\\*",
"?:\\Program Files\\Microsoft Visual Studio\\*",
"?:\\Program Files (x86)\\MSBuild\\*",
"?:\\Program Files\\MSBuild\\*") and
not process.command_line : ("* /*", "* .\\*", "*.proj*", "*.sln*") and
not (process.parent.executable : ("?:\\Program Files (x86)\\*.exe", "?:\\Program Files\\*.exe") and
not process.parent.name :
("winword.exe",
"excel.exe",
"outlook.exe",
"powerpnt.exe",
"eqnedt32.exe",
"fltldr.exe",
"mspub.exe",
"msaccess.exe"))
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"start" |
process.args_count | eq |
| field:"process.args_count" kind:eq value:"2" |
process.parent.name | wildcard |
| field:"parent_process_basename" kind:wildcard |
process.pe.original_file_name | eq |
| field:"OriginalFileName" kind:eq value:"MSBuild.exe" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.parent.name | eq | winword.exe, excel.exe, outlook.exe, powerpnt.exe, eqnedt32.exe, fltldr.exe, mspub.exe, msaccess.exe | excludes:process.parent.name |
process.parent.executable | wildcard | ?:\Program Files (x86)\*.exe, ?:\Program Files\*.exe | excludes:process.parent.executable field:"process.parent.executable" value:"?:\Program Files (x86)\*.exe" field:"process.parent.executable" value:"?:\Program Files\*.exe" |
process.command_line | match | /, .\, .proj, .sln | excludes:process.command_line |
process.executable | starts_with | ?:\Program Files (x86)\Microsoft Visual Studio\, ?:\Program Files\Microsoft Visual Studio\, ?:\Program Files (x86)\MSBuild\, ?:\Program Files\MSBuild\ | excludes:process.executable |
Potential Masquerading as VLC DLL
#Identifies instances of VLC-related DLLs which are not signed by the original developer. Attackers may name their payload as legitimate applications to blend into the environment, or embedding its malicious code within legitimate applications to deceive machine learning algorithms by incorporating authentic and benign code.
MITRE ATT&CK Coverage
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 7: Image loaded |
Rule Body
[metadata]
bypass_bbr_timing = true
creation_date = "2023/08/09"
integration = ["endpoint"]
maturity = "production"
updated_date = "2024/05/05"
[rule]
author = ["Elastic"]
building_block_type = "default"
description = """
Identifies instances of VLC-related DLLs which are not signed by the original developer. Attackers may name their
payload as legitimate applications to blend into the environment, or embedding its malicious code within legitimate
applications to deceive machine learning algorithms by incorporating authentic and benign code.
"""
from = "now-9m"
index = ["logs-endpoint.events.library-*"]
language = "eql"
license = "Elastic License v2"
name = "Potential Masquerading as VLC DLL"
risk_score = 21
rule_id = "4494c14f-5ff8-4ed2-8e99-bf816a1642fc"
severity = "low"
tags = [
"Domain: Endpoint",
"Data Source: Elastic Defend",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Defense Evasion",
"Tactic: Persistence",
"Rule Type: BBR",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
library where host.os.type == "windows" and event.action == "load" and
dll.name : ("libvlc.dll", "libvlccore.dll", "axvlc.dll") and
not (
dll.code_signature.subject_name : ("VideoLAN", "716F2E5E-A03A-486B-BC67-9B18474B9D51")
and dll.code_signature.trusted == true
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1036"
name = "Masquerading"
reference = "https://attack.mitre.org/techniques/T1036/"
[[rule.threat.technique.subtechnique]]
id = "T1036.001"
name = "Invalid Code Signature"
reference = "https://attack.mitre.org/techniques/T1036/001/"
[[rule.threat.technique.subtechnique]]
id = "T1036.005"
name = "Match Legitimate Resource Name or Location"
reference = "https://attack.mitre.org/techniques/T1036/005/"
[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 = "T1554"
name = "Compromise Host Software Binary"
reference = "https://attack.mitre.org/techniques/T1554/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
Stages and Predicates
Stage 1: library
library where host.os.type == "windows" and event.action == "load" and
dll.name : ("libvlc.dll", "libvlccore.dll", "axvlc.dll") and
not (
dll.code_signature.subject_name : ("VideoLAN", "716F2E5E-A03A-486B-BC67-9B18474B9D51")
and dll.code_signature.trusted == true
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
dll.name | wildcard |
| field:"dll.name" kind:wildcard |
event.action | eq |
| field:"EventType" kind:eq value:"load" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
dll.code_signature.subject_name | eq | VideoLAN, 716F2E5E-A03A-486B-BC67-9B18474B9D51 | excludes:dll.code_signature.subject_name field:"dll.code_signature.subject_name" value:"VideoLAN" field:"dll.code_signature.subject_name" value:"716F2E5E-A03A-486B-BC67-9B18474B9D51" |
dll.code_signature.trusted | eq | true | excludes:dll.code_signature.trusted field:"dll.code_signature.trusted" value:"true" |
PowerShell Script with Passwords Vault Access Capability
#Identifies access attempt to the Windows Passwords Vault via Powershell. Adversaries may acquire credentials from Vault files.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Credential Access |
Rule Body
[rule]
description = """
Identifies access attempt to the Windows Passwords Vault via Powershell. Adversaries may acquire credentials from Vault
files.
"""
id = "57bc4c03-7ed9-409e-971a-a0a03ea99ea0"
license = "Elastic License v2"
name = "PowerShell Script with Passwords Vault Access Capability"
os_list = ["windows"]
version = "1.0.5"
query = '''
api where process.Ext.api.name == "AmsiScanBuffer" and
(process.name in~ ("powershell.exe") or process.Ext.api.parameters.app_name == "PowerShell") and
process.Ext.api.parameters.buffer : "*Credentials.PasswordVault*" and process.Ext.api.parameters.buffer : ("*.RetrievePassword*", "*.RetrieveAll*") and
not process.Ext.api.parameters.content_name : ("?:\\Program Files (x86)\\*", "?:\\Program Files\\*") and
not (process.parent.executable : ("C:\\Program Files\\WindowsApps\\KeeperSecurityInc.KeeperPasswordManager_*\\app\\keeperpasswordmanager.exe", "C:\\Users\\*\\Downloads\\keeperimport*.exe") and
process.command_line : "C:\\WINDOWS\\system32\\windowspowershell\\v1.0\\powershell.exe \"[Windows.Security.Credentials.PasswordVault,Windows.Security.Credentials,ContentType=WindowsRuntime];(new-object Windows.Security.Credentials.PasswordVault).RetrieveAll() | % { $_.RetrievePassword(); $_ }\"")
'''
min_endpoint_version = "8.16.0"
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
tree = true
[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1059"
name = "Command and Scripting Interpreter"
reference = "https://attack.mitre.org/techniques/T1059/"
[[threat.technique.subtechnique]]
id = "T1059.001"
name = "PowerShell"
reference = "https://attack.mitre.org/techniques/T1059/001/"
[threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1555"
name = "Credentials from Password Stores"
reference = "https://attack.mitre.org/techniques/T1555/"
[[threat.technique.subtechnique]]
id = "T1555.004"
name = "Windows Credential Manager"
reference = "https://attack.mitre.org/techniques/T1555/004/"
[threat.tactic]
id = "TA0006"
name = "Credential Access"
reference = "https://attack.mitre.org/tactics/TA0006/"
[internal]
min_endpoint_version = "8.16.0"
Stages and Predicates
Stage 1: api
api where process.Ext.api.name == "AmsiScanBuffer" and
(process.name in~ ("powershell.exe") or process.Ext.api.parameters.app_name == "PowerShell") and
process.Ext.api.parameters.buffer : "*Credentials.PasswordVault*" and process.Ext.api.parameters.buffer : ("*.RetrievePassword*", "*.RetrieveAll*") and
not process.Ext.api.parameters.content_name : ("?:\\Program Files (x86)\\*", "?:\\Program Files\\*") and
not (process.parent.executable : ("C:\\Program Files\\WindowsApps\\KeeperSecurityInc.KeeperPasswordManager_*\\app\\keeperpasswordmanager.exe", "C:\\Users\\*\\Downloads\\keeperimport*.exe") and
process.command_line : "C:\\WINDOWS\\system32\\windowspowershell\\v1.0\\powershell.exe \"[Windows.Security.Credentials.PasswordVault,Windows.Security.Credentials,ContentType=WindowsRuntime];(new-object Windows.Security.Credentials.PasswordVault).RetrieveAll() | % { $_.RetrievePassword(); $_ }\"")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
process.Ext.api.name | eq |
| field:"process.Ext.api.name" kind:eq value:"AmsiScanBuffer" |
process.Ext.api.parameters.app_name | eq |
| field:"process.Ext.api.parameters.app_name" kind:eq value:"PowerShell" |
process.Ext.api.parameters.buffer | wildcard |
| field:"process.Ext.api.parameters.buffer" kind:wildcard |
process.name | in |
| field:"process_basename" kind:in value:"powershell.exe" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.command_line | eq | C:\WINDOWS\system32\windowspowershell\v1.0\powershell.exe "[Windows.Security.Credentials.PasswordVault,Windows.Security.Credentials,ContentType=WindowsRuntime];(new-object Windows.Security.Credentials.PasswordVault).RetrieveAll() | % { $_.RetrievePassword(); $_ }" | excludes:process.command_line |
process.parent.executable | wildcard | C:\Program Files\WindowsApps\KeeperSecurityInc.KeeperPasswordManager_*\app\keeperpasswordmanager.exe, C:\Users\*\Downloads\keeperimport*.exe | excludes:process.parent.executable field:"process.parent.executable" value:"C:\Program Files\WindowsApps\KeeperSecurityInc.KeeperPasswordManager_*\app\keeperpasswordmanager.exe" field:"process.parent.executable" value:"C:\Users\*\Downloads\keeperimport*.exe" |
process.Ext.api.parameters.content_name | starts_with | ?:\Program Files (x86)\, ?:\Program Files\ | excludes:process.Ext.api.parameters.content_name field:"process.Ext.api.parameters.content_name" value:"?:\Program Files (x86)\" field:"process.Ext.api.parameters.content_name" value:"?:\Program Files\" |
Self-Deleted Python Script Outbound Network Connection
#Detects an outbound network connection by a Python script that was executed and deleted from disk. A recent DPRK initial access campaign that resulted in the theft of $1.5 billion dollars used a Python application that self deletes and continues operating in memory.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth | |
| Command & Control |
Telemetry Coverage
Rule Body
[rule]
description = """
Detects an outbound network connection by a Python script that was executed and deleted from disk. A recent DPRK initial
access campaign that resulted in the theft of $1.5 billion dollars used a Python application that self deletes and
continues operating in memory.
"""
id = "fdaa3c78-6df7-4c87-be78-1acadecc908a"
license = "Elastic License v2"
name = "Self-Deleted Python Script Outbound Network Connection"
os_list = ["macos"]
reference = [
"https://unit42.paloaltonetworks.com/slow-pisces-new-custom-malware/",
"https://slowmist.medium.com/cryptocurrency-apt-intelligence-unveiling-lazarus-groups-intrusion-techniques-a1a6efda7d34",
]
version = "1.0.5"
query = '''
sequence by process.entity_id with maxspan=15s
[process where event.type == "start" and event.action == "exec" and process.name like~ "python*" and process.args_count == 2] as event0
[file where event.action == "deletion" and file.extension in ("py", "pyc") and process.name like~ "python*" and
stringcontains~(event0.process.command_line, file.path)]
[network where event.type == "start" and
not cidrmatch(destination.ip,
"240.0.0.0/4", "233.252.0.0/24", "224.0.0.0/4", "198.19.0.0/16", "192.18.0.0/15",
"192.0.0.0/24", "10.0.0.0/8", "127.0.0.0/8", "169.254.0.0/16", "172.16.0.0/12",
"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",
"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",
"::1", "FE80::/10", "FF00::/8")]
'''
min_endpoint_version = "8.16.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1059"
name = "Command and Scripting Interpreter"
reference = "https://attack.mitre.org/techniques/T1059/"
[[threat.technique.subtechnique]]
id = "T1059.006"
name = "Python"
reference = "https://attack.mitre.org/techniques/T1059/006/"
[threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1070"
name = "Indicator Removal"
reference = "https://attack.mitre.org/techniques/T1070/"
[[threat.technique.subtechnique]]
id = "T1070.004"
name = "File Deletion"
reference = "https://attack.mitre.org/techniques/T1070/004/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[[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 15s, correlated by process.entity_id.
Stage 1: process
[process where event.type == "start" and event.action == "exec" and process.name like~ "python*" and process.args_count == 2] as event0
Stage 2: file
[file where event.action == "deletion" and file.extension in ("py", "pyc") and process.name like~ "python*" and
stringcontains~(event0.process.command_line, file.path)]
Stage 3: network
[network where event.type == "start" and
not cidrmatch(destination.ip,
"240.0.0.0/4", "233.252.0.0/24", "224.0.0.0/4", "198.19.0.0/16", "192.18.0.0/15",
"192.0.0.0/24", "10.0.0.0/8", "127.0.0.0/8", "169.254.0.0/16", "172.16.0.0/12",
"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",
"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",
"::1", "FE80::/10", "FF00::/8")]
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
event0.process.command_line | contains |
| field:"event0.process.command_line" kind:contains value:"file.path" |
file.extension | in |
| field:"file.extension" kind:in |
process.args_count | eq |
| field:"process.args_count" kind:eq value:"2" |
process.name | wildcard |
| field:"process_basename" kind:wildcard value:"python*" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
destination.ip | cidr_match | 240.0.0.0/4, 233.252.0.0/24, 224.0.0.0/4, 198.19.0.0/16, 192.18.0.0/15, 192.0.0.0/24, 10.0.0.0/8, 127.0.0.0/8, 169.254.0.0/16, 172.16.0.0/12, 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, 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, ::1, FE80::/10, FF00::/8 | excludes:destination.ip |
Suspicious Execution from a WebDav Share
#Identifies attempts to execute or invoke content from remote WebDAV shares. Adversaries may abuse WebDAV paths, public tunnels, or host@port UNC paths to run tools or scripts while reducing local staging on the victim file system.
Known False Positives
- Trusted WebDAV content when the command namespace, parent, utility identity, signer, user/host scope, and child/artifact/destination evidence align with a recognized workflow
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Lateral Movement | |
| Command & Control |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
| Security-Auditing | Event ID 4688: A new process has been created. |
Rule Body
[metadata]
creation_date = "2025/08/19"
integration = ["endpoint", "windows", "system", "m365_defender", "sentinel_one_cloud_funnel", "crowdstrike"]
maturity = "production"
updated_date = "2026/05/03"
[rule]
author = ["Elastic"]
description = """
Identifies attempts to execute or invoke content from remote WebDAV shares. Adversaries may abuse WebDAV paths,
public tunnels, or host@port UNC paths to run tools or scripts while reducing local staging on the victim file system.
"""
false_positives = [
"Trusted WebDAV content when the command namespace, parent, utility identity, signer, user/host scope, and child/artifact/destination evidence align with a recognized workflow"
]
from = "now-9m"
index = [
"endgame-*",
"logs-crowdstrike.fdr*",
"logs-endpoint.events.process-*",
"logs-m365_defender.event-*",
"logs-sentinel_one_cloud_funnel.*",
"logs-system.security*",
"logs-windows.forwarded*",
"logs-windows.sysmon_operational-*",
"winlogbeat-*",
]
language = "eql"
license = "Elastic License v2"
name = "Suspicious Execution from a WebDav Share"
risk_score = 73
rule_id = "ee7726cc-babc-4885-988c-f915173ac0c0"
severity = "high"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Execution",
"Data Source: Elastic Endgame",
"Data Source: Elastic Defend",
"Data Source: Windows Security Event Logs",
"Data Source: Microsoft Defender XDR",
"Data Source: Sysmon",
"Data Source: SentinelOne",
"Data Source: Crowdstrike",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "windows" and event.type == "start" and
process.name : ("cmd.exe", "powershell.exe", "conhost.exe", "wscript.exe", "mshta.exe", "curl.exe", "msiexec.exe", "bitsadmin.exe", "net.exe") and
process.command_line : ("*trycloudflare.com*", "*@SSL\\*", "*\\webdav\\*", "*\\DavWWWRoot\\*", "*\\\\*.*@8080\\*", "*\\\\*.*@80\\*", "*\\\\*.*@8443\\*", "*\\\\*.*@443\\*") and
not (process.name : "cmd.exe" and process.args : "\\\\?\\UNC\\*.sharepoint.com@SSL\\DavWWWRoot\\*")
'''
note = """## Triage and analysis
### Investigating Suspicious Execution from a WebDav Share
#### Possible investigation steps
- Does the alert command line show direct WebDAV execution, and external delivery vs internal transfer?
- Focus: `process.command_line`, `process.name`, and `process.executable`; separate public tunnel or tenant paths from internal host@port UNC, "@SSL", "DavWWWRoot", or high-port paths.
- Implication: escalate when a script host, installer, shell, transfer tool, or net.exe points to public WebDAV content or an unrelated internal transfer host; lower concern when path maps to one recognized internal tenant, vendor, or deployment namespace for that role.
- Do the launcher identity and parent lineage match that exact workflow?
- Focus: `process.executable`, `process.code_signature.subject_name`, `process.code_signature.trusted`, `process.parent.executable`, and `process.parent.command_line`.
- Implication: escalate when a signed utility proxies execution from a browser, Office app, chat client, archive tool, or unexplained service context. Public paths from user-facing parents suggest user delivery; internal host@port paths or net.exe share activity suggest lateral transfer. Lower concern when signer, parent, path, host, and user recur as one recognized collaboration, deployment, or support workflow; identity alone does not clear remote execution.
- Did the alerting process spawn follow-on execution or share-mount activity?
- Focus: child or sibling process starts on `host.id` where `process.parent.entity_id` matches `process.entity_id`; check shells, downloaders, installers, schedulers, net.exe, or user-writable `process.executable` paths. $investigate_2
- Hint: if `process.entity_id` is unavailable, use `host.id`, `process.pid`, and a tight alert-time window; PID lineage is weaker because of reuse.
- Implication: escalate when the launcher spawns download, install, persistence, or share-mapping tied to the same path; narrow scope when the chain ends cleanly inside one recognized workflow.
- Did file telemetry show local staging or later execution from the WebDAV launch?
- Focus: if file telemetry exists, query `host.id` plus `process.entity_id` for `file.path`, `file.origin_url`, `file.Ext.windows.zone_identifier`, and later starts where `process.executable` matches a written path. $investigate_3
- Hint: if WebDAV content is copied locally or to a mapped drive before execution, treat it as the same delivery chain and keep original-process scope.
- Range: start with the alert window; expand only after a suspicious write to confirm later execution.
- Implication: escalate when the chain writes scripts, installers, renamed payloads, or startup material in user-writable paths. Missing file telemetry is unresolved, not benign; direct WebDAV execution may leave few local artifacts.
- Did DNS or connection telemetry confirm the WebDAV endpoint or delivery infrastructure?
- Focus: if network telemetry exists, separate DNS events (`dns.question.name`, `dns.resolved_ip`) from connection events (`destination.ip`, `destination.port`) for the same `host.id` and `process.entity_id`. $investigate_4
- Hint: use DNS lookup_result events to map `dns.resolved_ip` to later `destination.ip` before tying a domain to a connection. Missing network telemetry is unresolved, not benign.
- Implication: escalate when the process reaches public tunnels, rare external domains, high-port WebDAV services, or destinations unrelated to the signer and parent workflow; lower concern when the endpoint matches the command line's recognized tenant, internal share, or vendor.
- If local evidence is suspicious or unresolved, do related alerts show the same WebDAV delivery or transfer pattern?
- Focus: related alerts for `user.id` over 48 hours, checking reused WebDAV path, launcher, destination, or follow-on artifact. $investigate_0
- Hint: if user scope is quiet or ambiguous, check `host.id` for whether the path stays local or appears with other execution or download alerts. $investigate_1
- Implication: broaden scope when the same path, domain, launcher, or artifact pattern appears beyond one recognized workflow; keep the case local when related-alert history is confined to that workflow.
- Escalate on direct remote WebDAV execution plus suspicious launcher, lineage, child, artifact, destination, or related-alert evidence; close only when process evidence and recovery align to one exact recognized workflow; preserve and escalate when answers conflict or visibility is incomplete.
### False positive analysis
- Tenant collaboration portals, internal WebDAV shares, and vendor content portals can trigger when `process.command_line` namespace, `process.parent.executable`, `process.executable`, signer, `user.id`, and `host.id` converge on one recognized workflow. Close only when telemetry shows parent, path, utility, user, and host stable across prior rule alerts and no child, artifact, or destination evidence contradicts the portal workflow. Use portal allowlists or owner records as corroboration, not substitutes.
- Deployment or remote-support tooling can run msiexec.exe, powershell.exe, cmd.exe, or bitsadmin.exe against WebDAV-hosted packages. Confirm only when a management-agent or support-console parent, utility identity, signer, package namespace, written-artifact pattern, and host/user scope fit the same workflow. Public tunnel paths, renamed payloads, unexpected children, or one-off standard-user launches remain suspicious unless externally confirmed with no telemetry contradictions.
- Before creating an exception, use the minimum confirmed workflow pattern: stable `process.code_signature.subject_name` or `process.executable`, `process.parent.executable`, specific `process.command_line` namespace or destination pattern, and proving `user.id` or `host.id` scope. Avoid exceptions on `process.name`, `user.name`, "@SSL", or "DavWWWRoot" alone.
### Response and remediation
- If confirmed benign, reverse temporary containment and document the command-line namespace, parent launcher, utility identity, signer, available destination or artifact evidence, and `user.id` / `host.id` scope that validated the workflow. Create an exception only after the same scoped pattern is stable across prior rule alerts.
- If suspicious but unconfirmed, preserve the alert export, process tree, `process.entity_id`, `process.command_line`, `process.parent.command_line`, remote path, staged artifacts, and destination indicators before containment. First apply reversible containment, such as temporarily blocking the confirmed WebDAV namespace or increasing monitoring on affected `host.id` and `user.id`; avoid termination or deletion until child execution, payload staging, or repeated suspicious destinations indicate active compromise.
- If confirmed malicious, isolate the host when feasible or terminate the alerting process after evidence capture. If identity evidence suggests account misuse, contain or reset the affected account with identity owners. If direct endpoint response is unavailable, hand off preserved process, artifact, destination, host, and user evidence to the team able to contain the host or account.
- Block confirmed malicious domains, destination IPs, hashes, executable paths, and staged artifact paths. Review other hosts and users for the same `process.parent.executable` plus `process.command_line` plus destination pattern, then remove only staged scripts, installers, startup material, or persistence changes tied to the chain.
- Post-incident hardening: restrict unnecessary WebDAV and WebClient usage, limit direct execution from remote shares by script hosts and installers, use application control or attack surface reduction where feasible, retain file and network telemetry for this workflow, and document variants such as mapped-drive execution, copied-local execution, and alternate script-host launchers.
"""
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:
- [CrowdStrike](https://ela.st/crowdstrike-integration)
- [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)
- [Windows Process Creation Logs](https://ela.st/audit-process-creation)
"""
[rule.investigation_fields]
field_names = [
"@timestamp",
"host.name",
"host.id",
"user.id",
"process.entity_id",
"process.pid",
"process.name",
"process.executable",
"process.command_line",
"process.parent.executable",
"process.parent.command_line",
"process.code_signature.subject_name",
"process.code_signature.trusted",
]
[transform]
[[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 from the WebDAV launcher"
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.parent.entity_id", queryType = "phrase", value = "{{process.entity_id}}", valueType = "string" }
]
]
relativeFrom = "now-1h"
relativeTo = "now"
[[transform.investigate]]
label = "File events from the WebDAV launcher"
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 from the WebDAV launcher"
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"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[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/"
[[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.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 = "T1071"
name = "Application Layer Protocol"
reference = "https://attack.mitre.org/techniques/T1071/"
[[rule.threat.technique.subtechnique]]
id = "T1071.001"
name = "Web Protocols"
reference = "https://attack.mitre.org/techniques/T1071/001/"
[[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/"
Stages and Predicates
Stage 1: process
process where host.os.type == "windows" and event.type == "start" and
process.name : ("cmd.exe", "powershell.exe", "conhost.exe", "wscript.exe", "mshta.exe", "curl.exe", "msiexec.exe", "bitsadmin.exe", "net.exe") and
process.command_line : ("*trycloudflare.com*", "*@SSL\\*", "*\\webdav\\*", "*\\DavWWWRoot\\*", "*\\\\*.*@8080\\*", "*\\\\*.*@80\\*", "*\\\\*.*@8443\\*", "*\\\\*.*@443\\*") and
not (process.name : "cmd.exe" and process.args : "\\\\?\\UNC\\*.sharepoint.com@SSL\\DavWWWRoot\\*")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.command_line | wildcard |
| field:"CommandLine" kind:wildcard |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.args | wildcard | \\?\UNC\*.sharepoint.com@SSL\DavWWWRoot\* | excludes:process.args field:"process.args" value:"\\?\UNC\*.sharepoint.com@SSL\DavWWWRoot\*" |
process.name | eq | cmd.exe | excludes:process.name field:"process.name" value:"cmd.exe" |
Suspicious Execution from an Oversized Executable
#Identifies the execution of commonly abused Microsoft binaries from an oversized parent executable. Malwares tend to increase the size of the binary payload beyond what some security tools are capable of handling due to file size limitations.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies the execution of commonly abused Microsoft binaries from an oversized parent executable. Malwares tend to
increase the size of the binary payload beyond what some security tools are capable of handling due to file size
limitations.
"""
id = "7a804cf1-aec7-474d-a776-7e78f6b14658"
license = "Elastic License v2"
name = "Suspicious Execution from an Oversized Executable"
os_list = ["windows"]
reference = ["https://attack.mitre.org/techniques/T1027/001/"]
version = "1.0.8"
query = '''
sequence with maxspan=5m
[file where event.action != "deletion" and
(file.extension : ("exe", "com", "pif", "scr", "dll", "cpl", "ocx") or file.Ext.header_bytes : "4d5a*") and
/* larger than 10MB */
file.size >= 100000000 and
(
/* common initial access and execution processes */
process.name : ("winword.exe", "excel.exe", "powerpnt.exe", "cmd.exe", "powershell.exe", "cscript.exe", "wscript.exe",
"mshta.exe", "rundll32.exe", "regsvr32.exe", "certutil.exe", "CertReq.exe", "curl.exe", "msbuild.exe",
"installutil.exe", "regasm.exe", "expand.exe", "xcopy.exe", "chrome.exe", "brave.exe", "firefox.exe",
"msedge.exe", "whale.exe", "browser.exe", "dragon.exe", "vivaldi.exe", "opera.exe") or
/* suspicious or user writable paths and unsigned processes */
(process.executable : ("?:\\Users\\*", "?:\\ProgramData\\*", "?:\\Windows\\Temp\\*", "?:\\Windows\\Tasks\\*", "\\Device\\Mup\\*") and
(process.code_signature.trusted == false or process.code_signature.exists == false))
) and
/* excluding noisy patterns */
not file.path : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*") and not user.id : ("S-1-5-18", "S-1-5-19", "S-1-5-20") and
not process.executable :
("?:\\Users\\*\\AppData\\Local\\electron-builder\\Cache\\winCodeSign\\winCodeSign-2.6.0\\rcedit-x64.exe",
"?:\\Users\\*\\Electron\\dist\\StrigoTool-Electron Setup 1.0.0.exe")
] by file.path
[process where event.action == "start" and
process.name : ("cmd.exe", "powershell.exe", "wscript.exe", "mshta.exe", "rundll32.exe", "regsvr32.exe",
"certutil.exe", "CertReq.exe", "curl.exe", "msbuild.exe") and
not (process.name : "wscript.exe" and process.args : "C:\\Prntdrvr\\SFX\\silent.vbs") and
not (process.name : "cmd.exe" and
process.args : ("C:\\WINDOWS\\system32\\reg.exe ADD HKCU\\Software\\Classes\\GoSignDesktop.p7m /f",
"USERNAME eq %USERNAME%", "lms version --json", "--output-encoding=bser",
"imagename eq SteelSeriesGG.exe")) and
not (process.parent.code_signature.subject_name : ("KOBIL GmbH", "Shenzhen Tuozhu Technology Co., Ltd.", "Bose Professional") and
process.parent.code_signature.trusted == true) and
not process.parent.code_signature.trusted == true and not process.parent.args == "--squirrel-firstrun" and
not process.command_line :
("C:\\Windows\\system32\\cmd.exe /d /s /c \"node -v\"",
"C:\\Windows\\system32\\cmd.exe /d /s /c \"chcp\"",
"C:\\windows\\system32\\cmd.exe /c az version -o=json",
"C:\\WINDOWS\\system32\\cmd.exe /d /s /c \"wmic CsProduct Get UUID\"",
"C:\\windows\\system32\\cmd.exe /d /s /c \"wsl.exe -l -q\"",
"C:\\WINDOWS\\system32\\cmd.exe /d /s /c *",
"cmd /c dir") and
not (process.name : "cmd.exe" and process.args : ("*.bat", "*.cmd", "rmdir", "*.bat ", "*.cmd ")) and
not (process.name : "cmd.exe" and process.args : ("*reg.exe QUERY*", "netstat -r", "net session", "wsl.exe -l -q",
"C:\\Program Files (x86)\\Annke Vision Site\\Nginx",
"route print 0.0.0.0 mask 0.0.0.0",
"powershell -command Get-Culture",
"powershell -Command Get-Host")) and
not (process.name : "powershell.exe" and
process.command_line : "C:\\Windows\\system32\\WindowsPowerShell\\v1.0\\powershell.exe -NoProfile -NoLogo -InputFormat Text -NoExit -ExecutionPolicy Unrestricted -Command -")
] by process.parent.executable
'''
min_endpoint_version = "8.14.0"
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1
[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1027"
name = "Obfuscated Files or Information"
reference = "https://attack.mitre.org/techniques/T1027/"
[[threat.technique.subtechnique]]
id = "T1027.001"
name = "Binary Padding"
reference = "https://attack.mitre.org/techniques/T1027/001/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.14.0"
Stages and Predicates
Ordered sequence: each step below must occur in order within 5m, correlated by file.path, process.parent.executable.
Stage 1: file
[file where event.action != "deletion" and
(file.extension : ("exe", "com", "pif", "scr", "dll", "cpl", "ocx") or file.Ext.header_bytes : "4d5a*") and
file.size >= 100000000 and
(
process.name : ("winword.exe", "excel.exe", "powerpnt.exe", "cmd.exe", "powershell.exe", "cscript.exe", "wscript.exe",
"mshta.exe", "rundll32.exe", "regsvr32.exe", "certutil.exe", "CertReq.exe", "curl.exe", "msbuild.exe",
"installutil.exe", "regasm.exe", "expand.exe", "xcopy.exe", "chrome.exe", "brave.exe", "firefox.exe",
"msedge.exe", "whale.exe", "browser.exe", "dragon.exe", "vivaldi.exe", "opera.exe") or
(process.executable : ("?:\\Users\\*", "?:\\ProgramData\\*", "?:\\Windows\\Temp\\*", "?:\\Windows\\Tasks\\*", "\\Device\\Mup\\*") and
(process.code_signature.trusted == false or process.code_signature.exists == false))
) and
not file.path : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*") and not user.id : ("S-1-5-18", "S-1-5-19", "S-1-5-20") and
not process.executable :
("?:\\Users\\*\\AppData\\Local\\electron-builder\\Cache\\winCodeSign\\winCodeSign-2.6.0\\rcedit-x64.exe",
"?:\\Users\\*\\Electron\\dist\\StrigoTool-Electron Setup 1.0.0.exe")
] by file.path
Stage 2: process
[process where event.action == "start" and
process.name : ("cmd.exe", "powershell.exe", "wscript.exe", "mshta.exe", "rundll32.exe", "regsvr32.exe",
"certutil.exe", "CertReq.exe", "curl.exe", "msbuild.exe") and
not (process.name : "wscript.exe" and process.args : "C:\\Prntdrvr\\SFX\\silent.vbs") and
not (process.name : "cmd.exe" and
process.args : ("C:\\WINDOWS\\system32\\reg.exe ADD HKCU\\Software\\Classes\\GoSignDesktop.p7m /f",
"USERNAME eq %USERNAME%", "lms version --json", "--output-encoding=bser",
"imagename eq SteelSeriesGG.exe")) and
not (process.parent.code_signature.subject_name : ("KOBIL GmbH", "Shenzhen Tuozhu Technology Co., Ltd.", "Bose Professional") and
process.parent.code_signature.trusted == true) and
not process.parent.code_signature.trusted == true and not process.parent.args == "--squirrel-firstrun" and
not process.command_line :
("C:\\Windows\\system32\\cmd.exe /d /s /c \"node -v\"",
"C:\\Windows\\system32\\cmd.exe /d /s /c \"chcp\"",
"C:\\windows\\system32\\cmd.exe /c az version -o=json",
"C:\\WINDOWS\\system32\\cmd.exe /d /s /c \"wmic CsProduct Get UUID\"",
"C:\\windows\\system32\\cmd.exe /d /s /c \"wsl.exe -l -q\"",
"C:\\WINDOWS\\system32\\cmd.exe /d /s /c *",
"cmd /c dir") and
not (process.name : "cmd.exe" and process.args : ("*.bat", "*.cmd", "rmdir", "*.bat ", "*.cmd ")) and
not (process.name : "cmd.exe" and process.args : ("*reg.exe QUERY*", "netstat -r", "net session", "wsl.exe -l -q",
"C:\\Program Files (x86)\\Annke Vision Site\\Nginx",
"route print 0.0.0.0 mask 0.0.0.0",
"powershell -command Get-Culture",
"powershell -Command Get-Host")) and
not (process.name : "powershell.exe" and
process.command_line : "C:\\Windows\\system32\\WindowsPowerShell\\v1.0\\powershell.exe -NoProfile -NoLogo -InputFormat Text -NoExit -ExecutionPolicy Unrestricted -Command -")
] by process.parent.executable
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
file.path | starts_with | ?:\Program Files\, ?:\Program Files (x86)\ | excludes:file.path field:"file.path" value:"?:\Program Files\" field:"file.path" value:"?:\Program Files (x86)\" |
process.executable | wildcard | ?:\Users\*\AppData\Local\electron-builder\Cache\winCodeSign\winCodeSign-2.6.0\rcedit-x64.exe, ?:\Users\*\Electron\dist\StrigoTool-Electron Setup 1.0.0.exe | excludes:process.executable field:"process.executable" value:"?:\Users\*\AppData\Local\electron-builder\Cache\winCodeSign\winCodeSign-2.6.0\rcedit-x64.exe" field:"process.executable" value:"?:\Users\*\Electron\dist\StrigoTool-Electron Setup 1.0.0.exe" |
user.id | eq | S-1-5-18, S-1-5-19, S-1-5-20 | excludes: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" |
process.args | eq | C:\Prntdrvr\SFX\silent.vbs | excludes:process.args field:"process.args" value:"C:\Prntdrvr\SFX\silent.vbs" |
process.name | eq | wscript.exe | excludes:process.name field:"process.name" value:"wscript.exe" |
process.args | eq | C:\WINDOWS\system32\reg.exe ADD HKCU\Software\Classes\GoSignDesktop.p7m /f, USERNAME eq %USERNAME%, lms version --json, --output-encoding=bser, imagename eq SteelSeriesGG.exe | excludes:process.args |
process.name | eq | cmd.exe | excludes:process.name field:"process.name" value:"cmd.exe" |
process.args | wildcard | *.bat, *.cmd, rmdir, *.bat , *.cmd | excludes:process.args |
process.args | wildcard | *reg.exe QUERY*, netstat -r, net session, wsl.exe -l -q, C:\Program Files (x86)\Annke Vision Site\Nginx, route print 0.0.0.0 mask 0.0.0.0, powershell -command Get-Culture, powershell -Command Get-Host | excludes:process.args |
process.command_line | eq | C:\Windows\system32\WindowsPowerShell\v1.0\powershell.exe -NoProfile -NoLogo -InputFormat Text -NoExit -ExecutionPolicy Unrestricted -Command - | excludes:process.command_line field:"process.command_line" value:"C:\Windows\system32\WindowsPowerShell\v1.0\powershell.exe -NoProfile -NoLogo -InputFormat Text -NoExit -ExecutionPolicy Unrestricted -Command -" |
process.name | eq | powershell.exe | excludes:process.name field:"process.name" value:"powershell.exe" |
process.parent.code_signature.subject_name | eq | KOBIL GmbH, Shenzhen Tuozhu Technology Co., Ltd., Bose Professional | excludes:process.parent.code_signature.subject_name field:"process.parent.code_signature.subject_name" value:"KOBIL GmbH" field:"process.parent.code_signature.subject_name" value:"Shenzhen Tuozhu Technology Co., Ltd." field:"process.parent.code_signature.subject_name" value:"Bose Professional" |
process.parent.code_signature.trusted | eq | true | excludes:process.parent.code_signature.trusted field:"process.parent.code_signature.trusted" value:"true" |
process.command_line | wildcard | C:\Windows\system32\cmd.exe /d /s /c "node -v", C:\Windows\system32\cmd.exe /d /s /c "chcp", C:\windows\system32\cmd.exe /c az version -o=json, C:\WINDOWS\system32\cmd.exe /d /s /c "wmic CsProduct Get UUID", C:\windows\system32\cmd.exe /d /s /c "wsl.exe -l -q", C:\WINDOWS\system32\cmd.exe /d /s /c *, cmd /c dir | excludes:process.command_line |
process.parent.args | eq | --squirrel-firstrun | excludes:process.parent.args field:"process.parent.args" value:"--squirrel-firstrun" |
Suspicious MS Outlook Child Process
#Identifies suspicious child processes of Microsoft Outlook. These child processes are often associated with spear phishing activity.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Execution | |
| Stealth |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
| Security-Auditing | Event ID 4688: A new process has been created. |
Rule Body
[metadata]
creation_date = "2020/02/18"
integration = ["endpoint", "windows", "system", "sentinel_one_cloud_funnel", "m365_defender", "crowdstrike"]
maturity = "production"
updated_date = "2026/05/04"
[rule]
author = ["Elastic"]
description = """
Identifies suspicious child processes of Microsoft Outlook. These child processes are often associated with spear
phishing activity.
"""
from = "now-9m"
index = [
"endgame-*",
"logs-crowdstrike.fdr*",
"logs-endpoint.events.process-*",
"logs-m365_defender.event-*",
"logs-sentinel_one_cloud_funnel.*",
"logs-system.security*",
"logs-windows.forwarded*",
"logs-windows.sysmon_operational-*",
"winlogbeat-*",
]
language = "eql"
license = "Elastic License v2"
name = "Suspicious MS Outlook Child Process"
note = """## Triage and analysis
### Investigating Suspicious MS Outlook Child Process
Microsoft Outlook is an email client that provides contact, email calendar, and task management features. Outlook is widely used, either standalone or as part of the Office suite.
This rule looks for suspicious processes spawned by MS Outlook, which can be the result of the execution of malicious documents and/or exploitation for initial access.
#### Possible investigation steps
- Investigate the process execution chain (parent process tree) for unknown processes. Examine their executable files for prevalence, whether they are located in expected locations, and if they are signed with valid digital signatures.
- Investigate other alerts associated with the user/host during the past 48 hours.
- Retrieve recently opened files received via email and opened by the user that could cause this behavior. Common locations include but are not limited to, the Downloads and Document folders and the folder configured at the email client.
- Determine if the collected files are malicious:
- Use a private sandboxed malware analysis system to perform analysis.
- Observe and collect information about the following activities:
- Attempts to contact external domains and addresses.
- File and registry access, modification, and creation activities.
- Service creation and launch activities.
- Scheduled task creation.
- Use the PowerShell Get-FileHash cmdlet to get the files' SHA-256 hash values.
- Search for the existence and reputation of the hashes in resources like VirusTotal, Hybrid-Analysis, CISCO Talos, Any.run, etc.
### False positive analysis
- This activity is unlikely to happen legitimately. Benign true positives (B-TPs) can be added as exceptions if necessary.
### Response and remediation
- Initiate the incident response process based on the outcome of the triage.
- Isolate the involved host to prevent further post-compromise behavior.
- Investigate credential exposure on systems compromised or used by the attacker to ensure all compromised accounts are identified. Reset passwords for these accounts and other potentially compromised credentials, such as email, business systems, and web services.
- If the triage identified malware, search the environment for additional compromised hosts.
- Implement temporary network rules, procedures, and segmentation to contain the malware.
- Stop suspicious processes.
- Immediately block the identified indicators of compromise (IoCs).
- Inspect the affected systems for additional malware backdoors like reverse shells, reverse proxies, or droppers that attackers could use to reinfect the system.
- Remove and block malicious artifacts identified during triage.
- Run a full antimalware scan. This may reveal additional artifacts left in the system, persistence mechanisms, and malware components.
- Determine the initial vector abused by the attacker and take action to prevent reinfection through the same vector.
- If the malicious file was delivered via phishing:
- Block the email sender from sending future emails.
- Block the malicious web pages.
- Remove emails from the sender from mailboxes.
- Consider improvements to the security awareness program.
- Using the incident response data, update logging and audit policies to improve the mean time to detect (MTTD) and the mean time to respond (MTTR).
"""
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:
- [CrowdStrike](https://ela.st/crowdstrike-integration)
- [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)
- [Windows Process Creation Logs](https://ela.st/audit-process-creation)
"""
risk_score = 21
rule_id = "32f4675e-6c49-4ace-80f9-97c9259dca2e"
severity = "low"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Initial Access",
"Tactic: Defense Evasion",
"Tactic: Execution",
"Resources: Investigation Guide",
"Data Source: Elastic Endgame",
"Data Source: Elastic Defend",
"Data Source: SentinelOne",
"Data Source: Microsoft Defender XDR",
"Data Source: Windows Security Event Logs",
"Data Source: Crowdstrike",
"Data Source: Sysmon",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "windows" and event.type == "start" and
process.parent.name : "outlook.exe" and
process.name : ("Microsoft.Workflow.Compiler.exe", "arp.exe", "atbroker.exe", "bginfo.exe", "bitsadmin.exe",
"cdb.exe", "certutil.exe", "cmd.exe", "cmstp.exe", "cscript.exe", "csi.exe", "dnx.exe", "dsget.exe",
"dsquery.exe", "forfiles.exe", "fsi.exe", "ftp.exe", "gpresult.exe", "hostname.exe", "ieexec.exe",
"iexpress.exe", "installutil.exe", "ipconfig.exe", "mshta.exe", "msxsl.exe", "nbtstat.exe", "net.exe",
"net1.exe", "netsh.exe", "netstat.exe", "nltest.exe", "odbcconf.exe", "ping.exe", "powershell.exe",
"pwsh.exe", "qprocess.exe", "quser.exe", "qwinsta.exe", "rcsi.exe", "reg.exe", "regasm.exe",
"regsvcs.exe", "regsvr32.exe", "sc.exe", "schtasks.exe", "systeminfo.exe", "tasklist.exe",
"tracert.exe", "whoami.exe", "wmic.exe", "wscript.exe", "xwizard.exe")
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1566"
name = "Phishing"
reference = "https://attack.mitre.org/techniques/T1566/"
[[rule.threat.technique.subtechnique]]
id = "T1566.001"
name = "Spearphishing Attachment"
reference = "https://attack.mitre.org/techniques/T1566/001/"
[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 = "T1059"
name = "Command and Scripting Interpreter"
reference = "https://attack.mitre.org/techniques/T1059/"
[[rule.threat.technique.subtechnique]]
id = "T1059.001"
name = "PowerShell"
reference = "https://attack.mitre.org/techniques/T1059/001/"
[[rule.threat.technique.subtechnique]]
id = "T1059.003"
name = "Windows Command Shell"
reference = "https://attack.mitre.org/techniques/T1059/003/"
[[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/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1218"
name = "System Binary Proxy Execution"
reference = "https://attack.mitre.org/techniques/T1218/"
[[rule.threat.technique.subtechnique]]
id = "T1218.003"
name = "CMSTP"
reference = "https://attack.mitre.org/techniques/T1218/003/"
[[rule.threat.technique.subtechnique]]
id = "T1218.004"
name = "InstallUtil"
reference = "https://attack.mitre.org/techniques/T1218/004/"
[[rule.threat.technique.subtechnique]]
id = "T1218.005"
name = "Mshta"
reference = "https://attack.mitre.org/techniques/T1218/005/"
[[rule.threat.technique.subtechnique]]
id = "T1218.008"
name = "Odbcconf"
reference = "https://attack.mitre.org/techniques/T1218/008/"
[[rule.threat.technique.subtechnique]]
id = "T1218.009"
name = "Regsvcs/Regasm"
reference = "https://attack.mitre.org/techniques/T1218/009/"
[[rule.threat.technique.subtechnique]]
id = "T1218.010"
name = "Regsvr32"
reference = "https://attack.mitre.org/techniques/T1218/010/"
[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 == "windows" and event.type == "start" and
process.parent.name : "outlook.exe" and
process.name : ("Microsoft.Workflow.Compiler.exe", "arp.exe", "atbroker.exe", "bginfo.exe", "bitsadmin.exe",
"cdb.exe", "certutil.exe", "cmd.exe", "cmstp.exe", "cscript.exe", "csi.exe", "dnx.exe", "dsget.exe",
"dsquery.exe", "forfiles.exe", "fsi.exe", "ftp.exe", "gpresult.exe", "hostname.exe", "ieexec.exe",
"iexpress.exe", "installutil.exe", "ipconfig.exe", "mshta.exe", "msxsl.exe", "nbtstat.exe", "net.exe",
"net1.exe", "netsh.exe", "netstat.exe", "nltest.exe", "odbcconf.exe", "ping.exe", "powershell.exe",
"pwsh.exe", "qprocess.exe", "quser.exe", "qwinsta.exe", "rcsi.exe", "reg.exe", "regasm.exe",
"regsvcs.exe", "regsvr32.exe", "sc.exe", "schtasks.exe", "systeminfo.exe", "tasklist.exe",
"tracert.exe", "whoami.exe", "wmic.exe", "wscript.exe", "xwizard.exe")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
process.parent.name | wildcard |
| field:"parent_process_basename" kind:wildcard value:"outlook.exe" |
Suspicious Remote Executable Memory Mapping
#Identifies cross-process MapViewOfFile-family calls that map a full section (zero byte length) with an executable page protection and where the thread call stack final user module is not trusted. This can indicate remote mapping of code or an image into another process for injection or defense evasion.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies cross-process MapViewOfFile-family calls that map a full section (zero byte length) with an executable page
protection and where the thread call stack final user module is not trusted. This can indicate remote mapping of code or
an image into another process for injection or defense evasion.
"""
id = "c4e8a2f1-6b3d-4c9e-a7f2-1e8d0c5b4a3f"
license = "Elastic License v2"
name = "Suspicious Remote Executable Memory Mapping"
os_list = ["windows"]
reference = [
"https://learn.microsoft.com/en-us/windows/win32/api/memoryapi/nf-memoryapi-mapviewoffile",
"https://learn.microsoft.com/en-us/windows/win32/api/memoryapi/nf-memoryapi-mapviewoffile2",
"https://learn.microsoft.com/en-us/windows/win32/api/memoryapi/nf-memoryapi-mapviewoffileex",
"https://www.elastic.co/security-labs/doubling-down-etw-callstacks",
]
version = "1.0.2"
query = '''
api where process.executable != null and
process.Ext.api.name in ("MapViewOfFile", "MapViewOfFile2", "MapViewOfFileEx") and
process.Ext.api.behaviors == "cross-process" and
process.Ext.api.parameters.protection : "*X*" and
process.Ext.api.parameters.size == 0 and Target.process.Ext.token.integrity_level_name != "low" and
/* final user module is unsigned or signed with an untrusted code signature */
_arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.trusted == false or $entry.exists == false) and
not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.status like "errorCode_endpoint*") and
not process.thread.Ext.call_stack_final_user_module.protection_provenance in ("Kernel", "Unknown", "Undetermined") and
not process.thread.Ext.call_stack_final_user_module.name in ("Kernel", "Unknown") and
not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.trusted == true and $entry.subject_name in ("Microsoft Windows Hardware Compatibility Publisher", "ESET, spol. s r.o.")) and
not process.thread.Ext.call_stack_final_user_module.hash.sha256 in ("d21b7ba659478d1b54d5dc841d0a96ae2de56581af25525011090795512168a0", "dc98b14cbb25ef1937217da4fde5e2cc13f4702b31a6bc481d8de2bd87ac0525") and
not (process.Ext.api.summary == "MapViewOfFile2( firefox.exe, 0x0, R-X )" and
process.thread.Ext.call_stack_final_user_module.path like ("c:\\windows\\system32\\spool\\drivers\\x64\\3\\ricoh_drv\\*.dll", "c:\\program files (x86)\\mozilla firefox\\mozglue.dll", "c:\\program files\\mozilla firefox\\mozglue.dll"))
'''
min_endpoint_version = "8.12.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1055"
name = "Process Injection"
reference = "https://attack.mitre.org/techniques/T1055/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.12.0"
Stages and Predicates
Stage 1: api
api where process.executable != null and
process.Ext.api.name in ("MapViewOfFile", "MapViewOfFile2", "MapViewOfFileEx") and
process.Ext.api.behaviors == "cross-process" and
process.Ext.api.parameters.protection : "*X*" and
process.Ext.api.parameters.size == 0 and Target.process.Ext.token.integrity_level_name != "low" and
_arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.trusted == false or $entry.exists == false) and
not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.status like "errorCode_endpoint*") and
not process.thread.Ext.call_stack_final_user_module.protection_provenance in ("Kernel", "Unknown", "Undetermined") and
not process.thread.Ext.call_stack_final_user_module.name in ("Kernel", "Unknown") and
not _arraysearch(process.thread.Ext.call_stack_final_user_module.code_signature, $entry, $entry.trusted == true and $entry.subject_name in ("Microsoft Windows Hardware Compatibility Publisher", "ESET, spol. s r.o.")) and
not process.thread.Ext.call_stack_final_user_module.hash.sha256 in ("d21b7ba659478d1b54d5dc841d0a96ae2de56581af25525011090795512168a0", "dc98b14cbb25ef1937217da4fde5e2cc13f4702b31a6bc481d8de2bd87ac0525") and
not (process.Ext.api.summary == "MapViewOfFile2( firefox.exe, 0x0, R-X )" and
process.thread.Ext.call_stack_final_user_module.path like ("c:\\windows\\system32\\spool\\drivers\\x64\\3\\ricoh_drv\\*.dll", "c:\\program files (x86)\\mozilla firefox\\mozglue.dll", "c:\\program files\\mozilla firefox\\mozglue.dll"))
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
Suspicious Svchost Registry Modification
#Identifies modification of the Windows shared services registry key. Adversaries may use this technique to maintain persistence or run with System privileges.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence |
Rule Body
[rule]
description = """
Identifies modification of the Windows shared services registry key. Adversaries may use this technique to maintain
persistence or run with System privileges.
"""
id = "055ce112-f2ad-418b-bce1-5fbe46e703fc"
license = "Elastic License v2"
name = "Suspicious Svchost Registry Modification"
os_list = ["windows"]
version = "1.0.21"
query = '''
registry where registry.key : "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost" and
registry.data.type : "REG_MULTI_SZ" and process.executable : ("?:\\*", "\\Device\\Mup\\*") and registry.data.strings != null and
not (registry.value : "print" and registry.data.strings : "PrintNotify") and
not (process.executable : "?:\\Windows\\System32\\poqexec.exe" and user.id : "S-1-5-18") and
not (process.executable : "?:\\Program Files*\\Microsoft\\AzureAttestService\\AzureAttestServiceInstaller.exe" and
registry.value : "AzureAttestService") and
not process.executable :
("?:\\Windows\\System32\\msiexec.exe",
"?:\\Windows\\System32\\svchost.exe",
"?:\\Windows\\WinSxS\\*\\TiWorker.exe",
"?:\\Windows\\System32\\drvinst.exe",
"?:\\Windows\\System32\\spoolsv.exe",
"?:\\Windows\\System32\\regsvr32.exe",
"?:\\Windows\\System32\\wbem\\WinMgmt.exe",
"C:\\Windows\\System32\\PrintIsolationHost.exe",
"?:\\Windows\\Regedit.exe",
"?:\\Windows\\VeeamVssSupport\\VeeamGuestHelper.exe",
"?:\\Program Files\\ForeScout SecureConnector\\SecureConnector.exe",
"?:\\Program Files\\UVK - Ultra Virus Killer\\UVK_en64.exe",
"C:\\Windows\\SoftwareDistribution\\Download\\Install\\osrssinst.exe") and
not (process.code_signature.subject_name == "Arcadia Laboratories Inc." and process.code_signature.trusted == true)
'''
min_endpoint_version = "8.1.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 = "T1543"
name = "Create or Modify System Process"
reference = "https://attack.mitre.org/techniques/T1543/"
[[threat.technique.subtechnique]]
id = "T1543.003"
name = "Windows Service"
reference = "https://attack.mitre.org/techniques/T1543/003/"
[threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[internal]
min_endpoint_version = "8.1.0"
Stages and Predicates
Stage 1: registry
registry where registry.key : "SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Svchost" and
registry.data.type : "REG_MULTI_SZ" and process.executable : ("?:\\*", "\\Device\\Mup\\*") and registry.data.strings != null and
not (registry.value : "print" and registry.data.strings : "PrintNotify") and
not (process.executable : "?:\\Windows\\System32\\poqexec.exe" and user.id : "S-1-5-18") and
not (process.executable : "?:\\Program Files*\\Microsoft\\AzureAttestService\\AzureAttestServiceInstaller.exe" and
registry.value : "AzureAttestService") and
not process.executable :
("?:\\Windows\\System32\\msiexec.exe",
"?:\\Windows\\System32\\svchost.exe",
"?:\\Windows\\WinSxS\\*\\TiWorker.exe",
"?:\\Windows\\System32\\drvinst.exe",
"?:\\Windows\\System32\\spoolsv.exe",
"?:\\Windows\\System32\\regsvr32.exe",
"?:\\Windows\\System32\\wbem\\WinMgmt.exe",
"C:\\Windows\\System32\\PrintIsolationHost.exe",
"?:\\Windows\\Regedit.exe",
"?:\\Windows\\VeeamVssSupport\\VeeamGuestHelper.exe",
"?:\\Program Files\\ForeScout SecureConnector\\SecureConnector.exe",
"?:\\Program Files\\UVK - Ultra Virus Killer\\UVK_en64.exe",
"C:\\Windows\\SoftwareDistribution\\Download\\Install\\osrssinst.exe") and
not (process.code_signature.subject_name == "Arcadia Laboratories Inc." and process.code_signature.trusted == true)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
process.executable | wildcard |
| field:"Image" kind:wildcard |
registry.data.strings | is_not_null | field:"Details" kind:is_not_null | |
registry.data.type | wildcard |
| field:"registry.data.type" kind:wildcard value:"REG_MULTI_SZ" |
registry.key | wildcard |
| field:"TargetObject" kind:wildcard value:"SOFTWARE\Microsoft\Windows NT\CurrentVersion\Svchost" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.code_signature.subject_name | eq | Arcadia Laboratories Inc. | excludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Arcadia Laboratories Inc." |
process.code_signature.trusted | eq | true | excludes:process.code_signature.trusted field:"process.code_signature.trusted" value:"true" |
process.executable | eq | ?:\Windows\System32\poqexec.exe | excludes:process.executable field:"process.executable" value:"?:\Windows\System32\poqexec.exe" |
user.id | eq | S-1-5-18 | excludes:user.id field:"user.id" value:"S-1-5-18" |
process.executable | wildcard | ?:\Program Files*\Microsoft\AzureAttestService\AzureAttestServiceInstaller.exe | excludes:process.executable field:"process.executable" value:"?:\Program Files*\Microsoft\AzureAttestService\AzureAttestServiceInstaller.exe" |
registry.value | eq | AzureAttestService | excludes:registry.value field:"registry.value" value:"AzureAttestService" |
registry.data.strings | eq | PrintNotify | excludes:registry.data.strings field:"registry.data.strings" value:"PrintNotify" |
registry.value | eq | print | excludes:registry.value field:"registry.value" value:"print" |
process.executable | wildcard | ?:\Windows\System32\msiexec.exe, ?:\Windows\System32\svchost.exe, ?:\Windows\WinSxS\*\TiWorker.exe, ?:\Windows\System32\drvinst.exe, ?:\Windows\System32\spoolsv.exe, ?:\Windows\System32\regsvr32.exe, ?:\Windows\System32\wbem\WinMgmt.exe, C:\Windows\System32\PrintIsolationHost.exe, ?:\Windows\Regedit.exe, ?:\Windows\VeeamVssSupport\VeeamGuestHelper.exe, ?:\Program Files\ForeScout SecureConnector\SecureConnector.exe, ?:\Program Files\UVK - Ultra Virus Killer\UVK_en64.exe, C:\Windows\SoftwareDistribution\Download\Install\osrssinst.exe | excludes:process.executable |
System Binary Proxy Execution via ScriptRunner
#Identifies the execution of a command or binary via the Windows Script Runner utility. Adversaries may bypass process and signature-based defenses by proxying execution of malicious content with signed, or otherwise trusted, binaries.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies the execution of a command or binary via the Windows Script Runner utility. Adversaries may bypass process
and signature-based defenses by proxying execution of malicious content with signed, or otherwise trusted, binaries.
"""
id = "06773783-0083-429d-863e-a85719a6cb05"
license = "Elastic License v2"
name = "System Binary Proxy Execution via ScriptRunner"
os_list = ["windows"]
reference = ["https://lolbas-project.github.io/lolbas/Binaries/Scriptrunner/"]
version = "1.0.4"
query = '''
process where event.action == "start" and
(process.parent.name : "ScriptRunner.exe" and process.parent.args : "-appvscript") and
not (process.executable : "?:\\Windows\\Sys*\\conhost.exe" and process.args : "0xffffffff")
'''
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 = "T1218"
name = "System Binary Proxy Execution"
reference = "https://attack.mitre.org/techniques/T1218/"
[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: process
process where event.action == "start" and
(process.parent.name : "ScriptRunner.exe" and process.parent.args : "-appvscript") and
not (process.executable : "?:\\Windows\\Sys*\\conhost.exe" and process.args : "0xffffffff")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"start" |
process.parent.args | wildcard |
| field:"process.parent.args" kind:wildcard value:"-appvscript" |
process.parent.name | wildcard |
| field:"parent_process_basename" kind:wildcard value:"ScriptRunner.exe" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.args | eq | 0xffffffff | excludes:process.args field:"process.args" value:"0xffffffff" |
process.executable | wildcard | ?:\Windows\Sys*\conhost.exe | excludes:process.executable field:"process.executable" value:"?:\Windows\Sys*\conhost.exe" |
Timestomping using Touch Command
#Timestomping is an anti-forensics technique which is used to modify the timestamps of a file, often to mimic files that are in the same folder.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Telemetry Coverage
Rule Body
[metadata]
creation_date = "2020/11/03"
integration = ["endpoint"]
maturity = "production"
updated_date = "2025/12/23"
[rule]
author = ["Elastic"]
description = """
Timestomping is an anti-forensics technique which is used to modify the timestamps of a file, often to mimic files that
are in the same folder.
"""
from = "now-9m"
index = ["auditbeat-*", "logs-endpoint.events.*"]
language = "eql"
license = "Elastic License v2"
max_signals = 33
name = "Timestomping using Touch Command"
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 Timestomping using Touch Command
Timestomping is a technique used by adversaries to alter file timestamps, making malicious files blend with legitimate ones. The 'touch' command, prevalent in Linux and macOS, can modify access and modification times. Attackers exploit this to evade detection. The detection rule identifies suspicious 'touch' usage by non-root users, focusing on specific arguments and excluding benign processes, thus highlighting potential timestomping activities.
### Possible investigation steps
- Review the process details to identify the user who executed the 'touch' command, focusing on the user.id field to determine if the user is legitimate and authorized to perform such actions.
- Examine the process.args field to understand the specific arguments used with the 'touch' command, particularly looking for the use of "-r", "-t", "-a*", or "-m*" which indicate potential timestomping activity.
- Investigate the parent process of the 'touch' command by checking the process.parent.name field to determine if it was initiated by a suspicious or unexpected process, excluding known benign processes like "pmlogger_daily", "pmlogger_janitor", and "systemd".
- Cross-reference the file paths and names involved in the 'touch' command with known system files and directories to assess if the files are legitimate or potentially malicious.
- Check for any recent alerts or logs related to the same user or process to identify patterns or repeated attempts at timestomping or other suspicious activities.
### False positive analysis
- Non-root users running legitimate scripts or applications that use the touch command with similar arguments may trigger false positives. To mitigate this, identify and whitelist these specific scripts or applications by adding their paths to the exclusion list.
- Automated system maintenance tasks that involve file timestamp modifications can be mistaken for malicious activity. Review and exclude known maintenance processes by adding them to the exclusion criteria, ensuring they do not match the suspicious argument patterns.
- Development tools or environments that utilize the touch command for file management during build processes might be flagged. Analyze these tools and exclude their typical usage patterns by specifying their paths or parent processes in the exclusion list.
- User-initiated file management activities, such as organizing or backing up files, can inadvertently match the rule's criteria. Educate users on the implications of using touch with specific arguments and consider excluding common user directories from the rule if they are frequently involved in such activities.
### Response and remediation
- Immediately isolate the affected system from the network to prevent further malicious activity and potential lateral movement by the attacker.
- Conduct a thorough review of the affected system's file system to identify and document any files with suspicious timestamp modifications, focusing on those altered by non-root users.
- Restore any critical files with altered timestamps from known good backups to ensure data integrity and system reliability.
- Revoke or reset credentials for any non-root users involved in the suspicious 'touch' command activity to prevent unauthorized access.
- 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 on the affected system and similar environments to detect any further attempts at timestomping or related suspicious activities.
- Review and update access controls and permissions to ensure that only authorized users have the ability to modify file timestamps, reducing the risk of future timestomping attempts."""
risk_score = 47
rule_id = "b0046934-486e-462f-9487-0d4cf9e429c6"
setup = """## Setup
If enabling an EQL rule on a non-elastic-agent index (such as beats) for versions <8.2,
events will not define `event.ingested` and default fallback for EQL rules was not added until version 8.2.
Hence for this rule to work effectively, users will need to add a custom ingest pipeline to populate
`event.ingested` to @timestamp.
For more details on adding a custom ingest pipeline refer - https://www.elastic.co/guide/en/fleet/current/data-streams-pipeline-tutorial.html
"""
severity = "medium"
tags = [
"Domain: Endpoint",
"OS: Linux",
"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 event.type == "start" and event.action == "exec" and process.name == "touch" and
process.parent.executable != null and process.args like (
"-t*", "-d*", "-a*", "-m*", "-r*", "--date=*", "--reference=*", "--time=*"
) and not (
process.parent.executable in (
"/usr/local/bin/manage_omnimesh_logs", "/pro/bin/sys/install/packageUtils.sh", "/bin/dracut",
"/usr/libexec/postfix/aliasesdb", "pwsh-preview", "/usr/bin/dracut", "/usr/share/initramfs-tools/hooks/amd64_microcode",
"/usr/local/bin/start-mailserver.sh", "/usr/bin/ssm-agent-worker", "/bin/ssm-agent-worker", "/usr/local/cpanel/scripts/restartsrv_bind"
) or
process.parent.executable like ("/opt/sw/tomcat/rc_scripts/*", "/tmp/newroot/var/lib/docker/overlay2/*", "/snap/*", "/opt/zeek/*") or
process.parent.name in (
"xargs", "find", "sudo", "make", "pmlogger_check", "pmlogger_daily", "pmlogger_janitor", "autoupdate", "pmlogctl",
"spyglass", "desktop-launch", "pmiectl", "systemd"
) or
process.parent.args like (
"/home/*/scripts/auto_download_process.py", "/home/*/scripts/perl_python_eagu1p.py", "/var/lib/dpkg/info/*",
"bazel-out/k8-dbg/bin/dependencies/thirdparty/libjansson_foreign_cc/build_script.sh", "/usr/lib/portage/python*/ebuild.sh",
"/var/tmp/rpm-tmp.*", "/usr/lib/pcp/bin/pmlogger_janitor", "/usr/libexec/pcp/bin/pmlogger_janitor",
"/usr/libexec/pcp/bin/pmlogger_daily", "/usr/lib/pcp/bin/pmlogger_daily", "/opt/oracle.ExaWatcher/GetExaWatcherResults.sh"
) or
process.args in (
"/usr/bin/coreutils", "--no-create", "/etc/opt/lumu/lumud.conf", "/opt/vuso*", "/opt/diff", "/etc/aliases.db", "/opt/cursor/cursor"
) or
process.args like (
"--checkpoint=*", "/root/.config/envman/*", "/var/tmp/dracut*", "/var/tmp/portage*", "/snap/*", "/var/tmp/pmlogger_*/stamp", "/opt/ubki/*.jar",
"/usr/lib/go-*/bin/go", "/usr/lib/dracut/dracut-functions.sh", "/tmp/KSInstallAction.*/m/.patch/*"
) or
process.command_line in ("/bin/touch -a /tmp/au_status", "touch -d 2 seconds ago /etc/postfix/main.cf") or
process.parent.command_line == "runc init" or
process.working_directory in ("/opt/libexec", "/opt/local/src/connectxx/build/src/mdp")
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1070"
name = "Indicator Removal"
reference = "https://attack.mitre.org/techniques/T1070/"
[[rule.threat.technique.subtechnique]]
id = "T1070.006"
name = "Timestomp"
reference = "https://attack.mitre.org/techniques/T1070/006/"
[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
Stages and Predicates
Stage 1: process
process where event.type == "start" and event.action == "exec" and process.name == "touch" and
process.parent.executable != null and process.args like (
"-t*", "-d*", "-a*", "-m*", "-r*", "--date=*", "--reference=*", "--time=*"
) and not (
process.parent.executable in (
"/usr/local/bin/manage_omnimesh_logs", "/pro/bin/sys/install/packageUtils.sh", "/bin/dracut",
"/usr/libexec/postfix/aliasesdb", "pwsh-preview", "/usr/bin/dracut", "/usr/share/initramfs-tools/hooks/amd64_microcode",
"/usr/local/bin/start-mailserver.sh", "/usr/bin/ssm-agent-worker", "/bin/ssm-agent-worker", "/usr/local/cpanel/scripts/restartsrv_bind"
) or
process.parent.executable like ("/opt/sw/tomcat/rc_scripts/*", "/tmp/newroot/var/lib/docker/overlay2/*", "/snap/*", "/opt/zeek/*") or
process.parent.name in (
"xargs", "find", "sudo", "make", "pmlogger_check", "pmlogger_daily", "pmlogger_janitor", "autoupdate", "pmlogctl",
"spyglass", "desktop-launch", "pmiectl", "systemd"
) or
process.parent.args like (
"/home/*/scripts/auto_download_process.py", "/home/*/scripts/perl_python_eagu1p.py", "/var/lib/dpkg/info/*",
"bazel-out/k8-dbg/bin/dependencies/thirdparty/libjansson_foreign_cc/build_script.sh", "/usr/lib/portage/python*/ebuild.sh",
"/var/tmp/rpm-tmp.*", "/usr/lib/pcp/bin/pmlogger_janitor", "/usr/libexec/pcp/bin/pmlogger_janitor",
"/usr/libexec/pcp/bin/pmlogger_daily", "/usr/lib/pcp/bin/pmlogger_daily", "/opt/oracle.ExaWatcher/GetExaWatcherResults.sh"
) or
process.args in (
"/usr/bin/coreutils", "--no-create", "/etc/opt/lumu/lumud.conf", "/opt/vuso*", "/opt/diff", "/etc/aliases.db", "/opt/cursor/cursor"
) or
process.args like (
"--checkpoint=*", "/root/.config/envman/*", "/var/tmp/dracut*", "/var/tmp/portage*", "/snap/*", "/var/tmp/pmlogger_*/stamp", "/opt/ubki/*.jar",
"/usr/lib/go-*/bin/go", "/usr/lib/dracut/dracut-functions.sh", "/tmp/KSInstallAction.*/m/.patch/*"
) or
process.command_line in ("/bin/touch -a /tmp/au_status", "touch -d 2 seconds ago /etc/postfix/main.cf") or
process.parent.command_line == "runc init" or
process.working_directory in ("/opt/libexec", "/opt/local/src/connectxx/build/src/mdp")
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.args | wildcard |
| field:"process.args" kind:wildcard |
process.name | eq |
| field:"process_basename" kind:eq value:"touch" |
process.parent.executable | is_not_null | field:"ParentImage" kind:is_not_null |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.args | in | --no-create, /etc/aliases.db, /etc/opt/lumu/lumud.conf, /opt/cursor/cursor, /opt/diff, /opt/vuso*, /usr/bin/coreutils | excludes:process.args |
process.args | wildcard | --checkpoint=*, /root/.config/envman/*, /var/tmp/dracut*, /var/tmp/portage*, /snap/*, /var/tmp/pmlogger_*/stamp, /opt/ubki/*.jar, /usr/lib/go-*/bin/go, /usr/lib/dracut/dracut-functions.sh, /tmp/KSInstallAction.*/m/.patch/* | excludes:process.args |
process.command_line | in | /bin/touch -a /tmp/au_status, touch -d 2 seconds ago /etc/postfix/main.cf | excludes:process.command_line field:"process.command_line" value:"/bin/touch -a /tmp/au_status" field:"process.command_line" value:"touch -d 2 seconds ago /etc/postfix/main.cf" |
process.parent.args | wildcard | /home/*/scripts/auto_download_process.py, /home/*/scripts/perl_python_eagu1p.py, /var/lib/dpkg/info/*, bazel-out/k8-dbg/bin/dependencies/thirdparty/libjansson_foreign_cc/build_script.sh, /usr/lib/portage/python*/ebuild.sh, /var/tmp/rpm-tmp.*, /usr/lib/pcp/bin/pmlogger_janitor, /usr/libexec/pcp/bin/pmlogger_janitor, /usr/libexec/pcp/bin/pmlogger_daily, /usr/lib/pcp/bin/pmlogger_daily, /opt/oracle.ExaWatcher/GetExaWatcherResults.sh | excludes:process.parent.args |
process.parent.command_line | eq | runc init | excludes:process.parent.command_line field:"process.parent.command_line" value:"runc init" |
process.parent.executable | in | /bin/dracut, /bin/ssm-agent-worker, /pro/bin/sys/install/packageUtils.sh, /usr/bin/dracut, /usr/bin/ssm-agent-worker, /usr/libexec/postfix/aliasesdb, /usr/local/bin/manage_omnimesh_logs, /usr/local/bin/start-mailserver.sh, /usr/local/cpanel/scripts/restartsrv_bind, /usr/share/initramfs-tools/hooks/amd64_microcode, pwsh-preview | excludes:process.parent.executable |
process.parent.executable | starts_with | /opt/sw/tomcat/rc_scripts/, /tmp/newroot/var/lib/docker/overlay2/, /snap/, /opt/zeek/ | excludes:process.parent.executable |
process.parent.name | in | autoupdate, desktop-launch, find, make, pmiectl, pmlogctl, pmlogger_check, pmlogger_daily, pmlogger_janitor, spyglass, sudo, systemd, xargs | excludes:process.parent.name |
process.working_directory | in | /opt/libexec, /opt/local/src/connectxx/build/src/mdp | excludes:process.working_directory field:"process.working_directory" value:"/opt/libexec" field:"process.working_directory" value:"/opt/local/src/connectxx/build/src/mdp" |
Unusual DPKG Execution
#This rule detects the execution of the DPKG command by processes not associated with the DPKG package manager. The DPKG command is used to install, remove, and manage Debian packages on a Linux system. Attackers can abuse the DPKG command to install malicious packages on a system.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Execution | |
| Persistence | |
| Privilege Escalation | |
| Stealth |
Rule Body
[metadata]
creation_date = "2024/07/09"
integration = ["endpoint"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
description = """
This rule detects the execution of the DPKG command by processes not associated with the DPKG package manager. The DPKG
command is used to install, remove, and manage Debian packages on a Linux system. Attackers can abuse the DPKG command
to install malicious packages on a system.
"""
from = "now-9m"
index = ["logs-endpoint.events.process*"]
language = "eql"
license = "Elastic License v2"
name = "Unusual DPKG Execution"
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 Unusual DPKG Execution
DPKG is a core utility in Debian-based Linux systems for managing software packages. While essential for legitimate software management, adversaries can exploit DPKG to install or manipulate packages for malicious purposes, potentially gaining persistence or executing unauthorized code. The detection rule identifies anomalies by flagging DPKG executions initiated by unexpected processes, which may indicate unauthorized package management activities.
### Possible investigation steps
- Review the process details to identify the unexpected process that initiated the DPKG execution. Pay attention to the process.executable field to understand which script or binary was executed.
- Examine the process.parent.name and process.parent.executable fields to determine the parent process that launched the DPKG command. This can provide insights into whether the execution was part of a legitimate process chain or potentially malicious.
- Investigate the process.session_leader.name and process.group_leader.name fields to understand the broader context of the session and group leaders involved in the execution. This can help identify if the execution was part of a larger, coordinated activity.
- Check the system logs and any available audit logs around the time of the alert to gather additional context on the activities occurring on the system. Look for any other suspicious or related events.
- Assess the system for any unauthorized or unexpected package installations or modifications that may have occurred as a result of the DPKG execution. This can help determine if the system has been compromised.
### False positive analysis
- System maintenance scripts may trigger the rule if they execute DPKG commands outside of typical package management processes. To handle this, identify and whitelist these scripts by adding their parent process names or executables to the exception list.
- Automated software update tools, other than the ones specified in the rule, might cause false positives. Review the tools used in your environment and consider adding their executables to the exclusion criteria if they are verified as safe.
- Custom administrative scripts that manage packages could be flagged. Ensure these scripts are reviewed for legitimacy and then exclude their process names or paths from the rule to prevent unnecessary alerts.
- Development or testing environments where package manipulation is frequent might generate alerts. In such cases, consider creating environment-specific exceptions to reduce noise while maintaining security in production systems.
### Response and remediation
- Immediately isolate the affected system from the network to prevent further unauthorized package installations or potential lateral movement by the adversary.
- Terminate any suspicious processes identified as executing the DPKG command from unexpected sources to halt any ongoing malicious activities.
- Conduct a thorough review of recently installed or modified packages on the affected system to identify and remove any unauthorized or malicious software.
- Restore the system from a known good backup if malicious packages have been installed and cannot be safely removed without compromising system integrity.
- Update and patch the affected system to ensure all software is up-to-date, reducing the risk of exploitation through known vulnerabilities.
- Implement stricter access controls and monitoring on package management utilities to prevent unauthorized use, ensuring only trusted processes can execute DPKG commands.
- Escalate the incident to the security operations team for further investigation and to assess the potential impact on other systems within the network."""
references = ["https://www.makeuseof.com/how-deb-packages-are-backdoored-how-to-detect-it/"]
risk_score = 47
rule_id = "d6241c90-99f2-44db-b50f-299b6ebd7ee9"
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 = "medium"
tags = [
"Domain: Endpoint",
"OS: Linux",
"Use Case: Threat Detection",
"Tactic: Persistence",
"Data Source: Elastic Defend",
"Resources: Investigation Guide"
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "linux" and event.type == "start" and event.action == "exec" and
process.executable : "/var/lib/dpkg/info/*" and process.session_leader.name != null and
process.group_leader.name != null and not (
process.parent.name in ("dpkg", "dpkg-reconfigure", "frontend") or
process.session_leader.name == "dpkg" or
process.group_leader.name == "dpkg" or
process.parent.executable in ("/usr/share/debconf/frontend", "/usr/bin/unattended-upgrade")
)
'''
[[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.technique]]
id = "T1195"
name = "Supply Chain Compromise"
reference = "https://attack.mitre.org/techniques/T1195/"
[[rule.threat.technique.subtechnique]]
id = "T1195.002"
name = "Compromise Software Supply Chain"
reference = "https://attack.mitre.org/techniques/T1195/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 = "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: process
process where host.os.type == "linux" and event.type == "start" and event.action == "exec" and
process.executable : "/var/lib/dpkg/info/*" and process.session_leader.name != null and
process.group_leader.name != null and not (
process.parent.name in ("dpkg", "dpkg-reconfigure", "frontend") or
process.session_leader.name == "dpkg" or
process.group_leader.name == "dpkg" or
process.parent.executable in ("/usr/share/debconf/frontend", "/usr/bin/unattended-upgrade")
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.executable | wildcard |
| field:"Image" kind:wildcard value:"/var/lib/dpkg/info/*" |
process.group_leader.name | is_not_null | field:"process.group_leader.name" kind:is_not_null | |
process.session_leader.name | is_not_null | field:"process.session_leader.name" kind:is_not_null |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.group_leader.name | eq | dpkg | excludes:process.group_leader.name field:"process.group_leader.name" value:"dpkg" |
process.parent.executable | in | /usr/bin/unattended-upgrade, /usr/share/debconf/frontend | excludes:process.parent.executable field:"process.parent.executable" value:"/usr/bin/unattended-upgrade" field:"process.parent.executable" value:"/usr/share/debconf/frontend" |
process.parent.name | in | dpkg, dpkg-reconfigure, frontend | excludes:process.parent.name field:"process.parent.name" value:"dpkg" field:"process.parent.name" value:"dpkg-reconfigure" field:"process.parent.name" value:"frontend" |
process.session_leader.name | eq | dpkg | excludes:process.session_leader.name field:"process.session_leader.name" value:"dpkg" |
Volume Shadow Copy Deleted or Resized via VssAdmin
#Identifies use of vssadmin.exe for shadow copy deletion or resizing on endpoints. This commonly occurs in tandem with ransomware or other destructive attacks.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Impact |
Telemetry Coverage
| Provider | Record / event type |
|---|---|
| Sysmon | Event ID 1: Process creation |
| Security-Auditing | Event ID 4688: A new process has been created. |
Rule Body
[metadata]
creation_date = "2020/02/18"
integration = ["endpoint", "windows", "system", "m365_defender", "sentinel_one_cloud_funnel", "crowdstrike"]
maturity = "production"
updated_date = "2026/05/03"
[rule]
author = ["Elastic"]
description = """
Identifies use of vssadmin.exe for shadow copy deletion or resizing on endpoints. This commonly occurs in tandem with
ransomware or other destructive attacks.
"""
from = "now-9m"
index = [
"endgame-*",
"logs-crowdstrike.fdr*",
"logs-endpoint.events.process-*",
"logs-m365_defender.event-*",
"logs-sentinel_one_cloud_funnel.*",
"logs-system.security*",
"logs-windows.forwarded*",
"logs-windows.sysmon_operational-*",
"winlogbeat-*",
]
language = "eql"
license = "Elastic License v2"
name = "Volume Shadow Copy Deleted or Resized via VssAdmin"
risk_score = 73
rule_id = "b5ea4bfe-a1b2-421f-9d47-22a75a6f2921"
severity = "high"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Impact",
"Resources: Investigation Guide",
"Data Source: Elastic Endgame",
"Data Source: Elastic Defend",
"Data Source: Windows Security Event Logs",
"Data Source: Microsoft Defender XDR",
"Data Source: Sysmon",
"Data Source: SentinelOne",
"Data Source: Crowdstrike",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "windows" and event.type == "start" and
(process.name : "vssadmin.exe" or ?process.pe.original_file_name == "VSSADMIN.EXE") and
process.args : ("delete", "resize") and process.args : "shadows*"
'''
note = """## Triage and analysis
### Investigating Volume Shadow Copy Deleted or Resized via VssAdmin
#### Possible investigation steps
- What recovery-inhibition path does the alert-local command express?
- Focus: `process.command_line` and `process.args`; separate "delete shadows" with "/all", "/quiet", "/for=", "/oldest", or "/shadow=" from "resize shadowstorage" with "/for=", "/on=", and "/maxsize=".
- Implication: escalate faster when the command deletes all shadows, suppresses prompts, targets broad restore scope, or forces a tiny maximum; lower suspicion when it targets one volume, one shadow ID, or capacity-aligned resize inside a recognized retention, storage, or reset workflow.
- Is the VssAdmin binary identity consistent with the tool being invoked?
- Focus: `process.executable`, `process.pe.original_file_name`, and, when available, `process.hash.sha256`, `process.code_signature.subject_name`, and `process.code_signature.trusted`.
- Implication: escalate when path, PE metadata, hash, signer, or trust does not fit Microsoft VssAdmin; lower suspicion when identity matches the expected Microsoft tool, but identity never clears broad deletion or forced shrinkage.
- Does the launcher and account explain why VssAdmin changed shadow-copy state?
- Focus: `process.parent.executable`, `process.parent.command_line`, `user.id`, `user.name`, and `user.domain`.
- Implication: escalate when Office, a browser, script host, remote-access tool, or unusual account launches the command; lower suspicion when the parent and account match the same backup agent, deployment runner, storage-management console, image-prep script, or lab-reset workflow.
- Are surrounding process events part of the same recovery-inhibition or impact chain?
- Why: destructive operators often pair VssAdmin with recovery tampering ("wmic shadowcopy delete", "diskshadow", "wbadmin delete catalog", "bcdedit recoveryenabled no", "reagentc /disable"), service stops, or encryption launchers.
- Focus: same-parent starts by `host.id` plus `process.parent.entity_id`; compare `process.name`, `process.command_line`, parent context, and timing. $investigate_2
- Range: start with the alert window through the next 15 minutes; expand only if the same lineage shows recovery tampering or encryption prep.
- Implication: escalate when the same lineage or short window shows backup deletion, recovery disablement, service stops, security-tool interference, or encryption tooling; lower suspicion when activity stays within one coherent maintenance or reset sequence.
- If endpoint file telemetry is available, is destructive file impact already visible from this process or host?
- Focus: file events by `host.id` plus `process.entity_id`; fallback to `host.id`, `process.pid`, and a tight alert window, checking `file.path`, `file.extension`, and `file.Ext.original.extension`. $investigate_3
- Implication: escalate when file activity shows mass renames, unfamiliar extensions, ransom-note drops, or destructive cleanup after VssAdmin starts; absence of file telemetry is unresolved, not benign.
- Do same-user or same-host alerts show spread beyond this VssAdmin event?
- Focus: same-`user.id` related alerts, especially impact, backup tampering, execution, credential, or lateral-movement activity. $investigate_0
- Hint: if local scope, lineage, process activity, or file impact remains suspicious or unresolved, review the same `host.id` for other shadow-copy, backup-catalog, service-stop, encryption, or ransom-note alerts. $investigate_1
- Implication: broaden containment when same-user or same-host alerts show additional recovery inhibition, encryption, credential access, or lateral movement; keep scope local when both pivots match the same exact retention, storage-maintenance, image-prep, or lab-reset pattern.
- Escalate when command intent plus launch context or surrounding process/file evidence supports unauthorized recovery inhibition; close only when command scope, identity, lineage, account, host, and follow-on telemetry bind to one exact recognized workflow, with outside confirmation if telemetry cannot prove legitimacy. Preserve evidence and escalate on conflict or incomplete visibility.
### False positive analysis
- Backup retention, storage maintenance, disaster-recovery testing, image preparation, and lab resets can delete one shadow copy or resize shadow storage. Confirm command scope (`process.command_line`), lineage (`process.parent.executable` and `process.parent.command_line`), actor/asset (`user.id`, `host.id`, `host.name`), and follow-on evidence with no same-window recovery tampering, encryption, ransom-note, or destructive cleanup outside that workflow. External records can corroborate after telemetry matches; otherwise require recurring command scope, parent, account, and host pattern across prior alerts without contradictory process or file evidence.
- Before creating an exception, validate recurring `process.executable`, `process.pe.original_file_name`, `process.parent.executable`, stable `process.command_line` scope, `user.id` or `user.name`, and `host.id` for the confirmed workflow. Keep it constrained to that workflow and avoid exceptions on `process.name`, "vssadmin.exe", "resize", "delete", or "shadows" alone.
### Response and remediation
- If confirmed benign, reverse temporary controls and record the command scope, parent lineage, account, host, and external evidence that tied the event to recognized maintenance or reset activity. Create an exception only if the same command scope, lineage, account, and host recur consistently across prior alerts from this rule.
- If suspicious but unconfirmed, preserve the alert document, raw process event, parent tree, full command line, account and host identifiers, same-window process activity, and any file-impact artifacts before containment. Apply reversible containment first: isolate the host if destructive activity appears and host criticality allows it; otherwise restrict the implicated admin channel or account while scope is confirmed. Broaden containment only if same-user or same-host pivots show spread.
- If confirmed malicious, keep the preserved evidence and isolate the endpoint to stop further impact while retaining telemetry. Suspend related accounts or admin channels when session, lineage, or related-alert evidence shows misuse. Record `process.entity_id` and `process.command_line` before termination. Remove only malicious scripts, payloads, scheduled tasks, services, ransom notes, and backup-tampering changes identified during the investigation.
- Restore affected VSS, backup, and recovery settings, validate that snapshots or backup jobs work again, and recover impacted data from trusted backups after containment and eradication are complete.
- Post-incident hardening: restrict VSS-management workflows on sensitive hosts, limit backup-administration rights, protect offline or out-of-band backups from the same accounts, and validate controls for adjacent recovery-inhibition variants such as "wmic shadowcopy delete", "diskshadow", "wbadmin delete catalog", "bcdedit", and "reagentc".
"""
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:
- [CrowdStrike](https://ela.st/crowdstrike-integration)
- [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)
- [Windows Process Creation Logs](https://ela.st/audit-process-creation)
"""
[rule.investigation_fields]
field_names = [
"@timestamp",
"host.name",
"host.id",
"user.id",
"process.entity_id",
"process.pid",
"process.executable",
"process.command_line",
"process.pe.original_file_name",
"process.parent.entity_id",
"process.parent.executable",
"process.parent.command_line",
]
[transform]
[[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 = "Process events from the same parent"
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.parent.entity_id", queryType = "phrase", value = "{{process.parent.entity_id}}", valueType = "string" }
]
]
relativeFrom = "now-1h"
relativeTo = "now"
[[transform.investigate]]
label = "File events from VssAdmin"
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"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1490"
name = "Inhibit System Recovery"
reference = "https://attack.mitre.org/techniques/T1490/"
[rule.threat.tactic]
id = "TA0040"
name = "Impact"
reference = "https://attack.mitre.org/tactics/TA0040/"
Stages and Predicates
Stage 1: process
process where host.os.type == "windows" and event.type == "start" and
(process.name : "vssadmin.exe" or ?process.pe.original_file_name == "VSSADMIN.EXE") and
process.args : ("delete", "resize") and process.args : "shadows*"
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.args | wildcard |
| field:"process.args" kind:wildcard |
process.name | wildcard |
| field:"process_basename" kind:wildcard value:"vssadmin.exe" |
process.pe.original_file_name | eq |
| field:"OriginalFileName" kind:eq value:"VSSADMIN.EXE" |
Windows Socket Creation from Stomped Module
#Identifies the creation of a Windows network socket from a potentially stomped module.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = "Identifies the creation of a Windows network socket from a potentially stomped module."
id = "46b3b2f8-d876-4344-8fff-8c86103bf8e2"
license = "Elastic License v2"
name = "Windows Socket Creation from Stomped Module"
os_list = ["windows"]
version = "1.0.2"
query = '''
api where process.Ext.api.name == "VirtualProtect" and
process.Ext.api.metadata.target_address_name == "mswsock.dll" and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "c:\\windows\\sys?????\\ws2_32.dll!WSASocket*") and
(
(process.thread.Ext.call_stack_summary regex """ntdll.dll\|apphelp.dll\|ntdll.dll\|kernelbase.dll\|ws2_32.dll\|[a-z]+\.dll""" and
_arraysearch(process.thread.Ext.call_stack, $entry,
stringcontains~($entry.symbol_info, substring(process.thread.Ext.call_stack_summary, 58, length(process.thread.Ext.call_stack_summary))) and $entry.callsite_trailing_bytes : "?*")) or
(process.thread.Ext.call_stack_summary regex """ntdll.dll\|wow64.dll\|wow64cpu.dll\|wow64.dll\|ntdll.dll\|apphelp.dll\|ntdll.dll\|kernelbase.dll\|ws2_32.dll\|[a-z]+\.dll""" and
_arraysearch(process.thread.Ext.call_stack, $entry,
stringcontains~($entry.symbol_info, substring(process.thread.Ext.call_stack_summary, 101, length(process.thread.Ext.call_stack_summary))) and $entry.callsite_trailing_bytes : "?*"))
) and
not _arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info like "c:\\windows\\syswow64\\rapi.dll*" and $entry.callsite_trailing_bytes like "8b450c8b0850ff5108eb1066837f50027509ff77548b0656ff500cb9a0725e67e8b23a0000eb0e8b0656*")
'''
min_endpoint_version = "8.10.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
tree = true
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1055"
name = "Process Injection"
reference = "https://attack.mitre.org/techniques/T1055/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.10.0"
Stages and Predicates
Stage 1: api
api where process.Ext.api.name == "VirtualProtect" and
process.Ext.api.metadata.target_address_name == "mswsock.dll" and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "c:\\windows\\sys?????\\ws2_32.dll!WSASocket*") and
(
(process.thread.Ext.call_stack_summary regex """ntdll.dll\|apphelp.dll\|ntdll.dll\|kernelbase.dll\|ws2_32.dll\|[a-z]+\.dll""" and
_arraysearch(process.thread.Ext.call_stack, $entry,
stringcontains~($entry.symbol_info, substring(process.thread.Ext.call_stack_summary, 58, length(process.thread.Ext.call_stack_summary))) and $entry.callsite_trailing_bytes : "?*")) or
(process.thread.Ext.call_stack_summary regex """ntdll.dll\|wow64.dll\|wow64cpu.dll\|wow64.dll\|ntdll.dll\|apphelp.dll\|ntdll.dll\|kernelbase.dll\|ws2_32.dll\|[a-z]+\.dll""" and
_arraysearch(process.thread.Ext.call_stack, $entry,
stringcontains~($entry.symbol_info, substring(process.thread.Ext.call_stack_summary, 101, length(process.thread.Ext.call_stack_summary))) and $entry.callsite_trailing_bytes : "?*"))
) and
not _arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info like "c:\\windows\\syswow64\\rapi.dll*" and $entry.callsite_trailing_bytes like "8b450c8b0850ff5108eb1066837f50027509ff77548b0656ff500cb9a0725e67e8b23a0000eb0e8b0656*")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
process.Ext.api.metadata.target_address_name | eq |
| field:"process.Ext.api.metadata.target_address_name" kind:eq value:"mswsock.dll" |
process.Ext.api.name | eq |
| field:"process.Ext.api.name" kind:eq value:"VirtualProtect" |
process.thread.Ext.call_stack_summary | regex_match |
| field:"process.thread.Ext.call_stack_summary" kind:regex_match |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.thread.Ext.call_stack | array_any | excludes:process.thread.Ext.call_stack |