Detection rules › Elastic
Elastic rules: 2g
AWS CloudTrail Management Events Disabled via PutEventSelectors
#Detects CloudTrail PutEventSelectors calls where the legacy event selectors explicitly set includeManagementEvents to false, disabling capture of all management API calls for that trail. Unlike StopLogging or DeleteTrail — which leave an obvious trace of the trail being stopped or removed entirely — this technique leaves the trail appearing active and healthy in the console while silently blinding defenders to subsequent IAM changes, credential operations, and resource abuse. This technique is documented in Stratus Red Team as aws.defense-evasion.cloudtrail-event-selectors and is a known pre-exfiltration step.
Known False Positives
- IaC pipelines setting event selectors during trail creation always set includeManagementEvents to true — the rule will not fire on those calls. The remaining FP vector is an administrator intentionally restricting a trail to data-events-only for cost reasons. Validate the caller, change management ticket, and confirm this is not a multi-region or organization-wide trail where the coverage impact would be severe.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Defense Impairment |
Telemetry Coverage
Rule Body
[metadata]
creation_date = "2026/07/13"
integration = ["aws"]
maturity = "production"
updated_date = "2026/07/13"
[rule]
author = ["Elastic"]
description = """
Detects CloudTrail PutEventSelectors calls where the legacy event selectors explicitly set includeManagementEvents to
false, disabling capture of all management API calls for that trail. Unlike StopLogging or DeleteTrail — which
leave an obvious trace of the trail being stopped or removed entirely — this technique leaves the trail appearing
active and healthy in the console while silently blinding defenders to subsequent IAM changes, credential operations,
and resource abuse. This technique is documented in Stratus Red Team as aws.defense-evasion.cloudtrail-event-selectors
and is a known pre-exfiltration step.
"""
false_positives = [
"""
IaC pipelines setting event selectors during trail creation always set includeManagementEvents to true — the rule
will not fire on those calls. The remaining FP vector is an administrator intentionally restricting a trail to
data-events-only for cost reasons. Validate the caller, change management ticket, and confirm this is not a
multi-region or organization-wide trail where the coverage impact would be severe.
""",
]
from = "now-6m"
index = ["logs-aws.cloudtrail-*"]
language = "kuery"
license = "Elastic License v2"
name = "AWS CloudTrail Management Events Disabled via PutEventSelectors"
note = """## Triage and analysis
### Investigating AWS CloudTrail Management Events Disabled via PutEventSelectors
`PutEventSelectors` controls which CloudTrail events a trail captures. This rule fires when the
new event selectors explicitly set `includeManagementEvents` to `false` — disabling capture of
all management API calls for that trail while leaving it appearing active in the console. This is
a surgical evasion technique that does not trigger the existing `StopLogging` or `DeleteTrail`
alerts, and can persist silently for days before detection.
### Possible investigation steps
- **Confirm the intent**: `aws.cloudtrail.request_parameters` contains the full JSON of the new
event selectors. The rule has already matched `includeManagementEvents: false`. Confirm whether
ALL selectors have management events disabled or only some, and whether `ExcludeManagementEventSources`
further filters specific services.
- **Check for other narrowing**: Also inspect `ReadWriteType` and `DataResources` in the same
event — switching to `ReadOnly` or removing data event entries compounds the coverage gap.
- **Verify the caller**: `aws.cloudtrail.user_identity.arn` — IaC automation (Terraform,
CloudFormation, CDK) uses AssumedRole/ASIA* credentials and legitimately sets management event
selectors to `true` during trail creation. An AKIA* key or Root identity making this change
outside of a deployment pipeline is high-confidence adversarial.
- **Check trail scope**: Was this a multi-region trail or organization-wide trail? Changes to
broad-scope trails have the largest visibility impact.
- **Correlate activity**: Look for high-impact API calls in the 30–60 minutes following this
event — particularly IAM changes, credential operations, or S3/KMS data access — that would
now be invisible to the trail.
- **Prior access**: Check for `GetTrailStatus`, `GetEventSelectors`, or `DescribeTrails` calls
from the same identity before this event, indicating reconnaissance of the trail configuration.
### Response and remediation
- Immediately call `PutEventSelectors` to restore `includeManagementEvents: true` on all selectors.
- Confirm that `GetTrailStatus` shows `IsLogging: true`.
- Review all API activity from the time the selectors were modified until detection using
alternative sources (CloudWatch, other regional trails) for the gap window.
- Restrict `cloudtrail:PutEventSelectors` to break-glass roles and enforce via SCP.
"""
references = [
"https://docs.aws.amazon.com/awscloudtrail/latest/APIReference/API_PutEventSelectors.html",
"https://stratus-red-team.cloud/attack-techniques/AWS/aws.defense-evasion.cloudtrail-event-selectors/",
"https://attack.mitre.org/techniques/T1562/008/",
]
risk_score = 47
rule_id = "20b79388-3225-4a98-b19f-17de8feaa39c"
severity = "medium"
tags = [
"Domain: Cloud",
"Data Source: AWS",
"Data Source: Amazon Web Services",
"Data Source: AWS CloudTrail",
"Use Case: Log Auditing",
"Tactic: Defense Evasion",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset: "aws.cloudtrail"
and event.provider: "cloudtrail.amazonaws.com"
and event.action: "PutEventSelectors"
and event.outcome: "success"
and aws.cloudtrail.request_parameters: *includeManagementEvents*false*
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1562"
name = "Impair Defenses"
reference = "https://attack.mitre.org/techniques/T1562/"
[[rule.threat.technique.subtechnique]]
id = "T1562.008"
name = "Disable or Modify Cloud Logs"
reference = "https://attack.mitre.org/techniques/T1562/008/"
[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",
"event.action",
"event.provider",
"event.outcome",
"cloud.account.id",
"cloud.region",
"aws.cloudtrail.request_parameters",
]
Stages and Predicates
Stage 1: query
data_stream.dataset: "aws.cloudtrail"
and event.provider: "cloudtrail.amazonaws.com"
and event.action: "PutEventSelectors"
and event.outcome: "success"
and aws.cloudtrail.request_parameters: *includeManagementEvents*false*
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
aws.cloudtrail.request_parameters | wildcard |
| field:"aws::requestParameters" kind:wildcard value:"*includeManagementEvents*false*" |
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"aws.cloudtrail" |
event.action | eq |
| field:"EventType" kind:eq value:"PutEventSelectors" |
event.outcome | eq |
| field:"event.outcome" kind:eq value:"success" |
event.provider | eq |
| field:"Provider_Name" kind:eq value:"cloudtrail.amazonaws.com" |
Command Line Obfuscation via Whitespace Padding
#Identifies process execution events where the command line value contains a long sequence of whitespace characters or multiple occurrences of contiguous whitespace. Attackers may attempt to evade signature-based detections by padding their malicious command with unnecessary whitespace characters. These observations should be investigated for malicious behavior.
MITRE ATT&CK Coverage
Rule Body
[metadata]
creation_date = "2025/06/30"
integration = ["endpoint", "system", "windows", "auditd_manager", "m365_defender", "crowdstrike", "sentinel_one_cloud_funnel"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
description = """
Identifies process execution events where the command line value contains a long sequence of whitespace characters or
multiple occurrences of contiguous whitespace. Attackers may attempt to evade signature-based detections by padding
their malicious command with unnecessary whitespace characters. These observations should be investigated for malicious
behavior.
"""
from = "now-9m"
language = "esql"
license = "Elastic License v2"
name = "Command Line Obfuscation via Whitespace Padding"
note = """## Triage and analysis
### Investigating Command Line Obfuscation via Whitespace Padding
This rule identifies process execution events where the command line value contains a long sequence of whitespace
characters or multiple occurrences of contiguous whitespace. Attackers may attempt to evade signature-based detections
by padding their malicious command with unnecessary whitespace characters.
#### Possible investigation steps
- Analyze the command line of the process in question for evidence of malicious code execution.
- 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.
- Investigate abnormal behaviors observed by the subject process such as network connections, registry or file
modifications, and any spawned child processes.
- Retrieve the process executable and determine if it is 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 tasks 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
- Alerts derived from this rule are not inherently malicious. Analysts can dismiss the alert if they don't find enough
evidence of further suspicious activity.
### 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.
- 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 the malicious certificate from the root certificate store.
- 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.
- 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.
- Determine the initial vector abused by the attacker and take action to prevent reinfection through the same vector.
- 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).
"""
risk_score = 47
rule_id = "5a876e0d-d39a-49b9-8ad8-19c9b622203b"
severity = "medium"
tags = [
"Domain: Endpoint",
"OS: Windows",
"OS: macOS",
"OS: Linux",
"Use Case: Threat Detection",
"Tactic: Defense Evasion",
"Tactic: Execution",
"Resources: Investigation Guide"
]
timestamp_override = "event.ingested"
type = "esql"
query = '''
FROM logs-* metadata _id, _version, _index
| where event.category == "process" and event.type == "start" and event.action != "fork"
// more than 100 spaces in process.command_line
| eval multi_spaces = LOCATE(process.command_line, space(100))
| where multi_spaces > 0
| keep user.name, host.id, host.name, process.command_line, process.executable, process.parent.executable, _id, _version, _index
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1027"
name = "Obfuscated Files or Information"
reference = "https://attack.mitre.org/techniques/T1027/"
[[rule.threat.technique.subtechnique]]
id = "T1027.010"
name = "Command Obfuscation"
reference = "https://attack.mitre.org/techniques/T1027/010/"
[[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/"
[[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.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
Stages and Predicates
Stage 1: from
FROM logs-* metadata _id, _version, _index
Stage 2: where
| where event.category == "process" and event.type == "start" and event.action != "fork"
Stage 3: eval
| eval multi_spaces = LOCATE(process.command_line, space(100))
Stage 4: where
| where multi_spaces > 0
Stage 5: keep
| keep user.name, host.id, host.name, process.command_line, process.executable, process.parent.executable, _id, _version, _index
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 |
host.id | KEEP host.id |
host.name | KEEP host.name |
process.command_line | KEEP process.command_line |
process.executable | KEEP process.executable |
process.parent.executable | KEEP process.parent.executable |
_id | KEEP _id |
_version | KEEP _version |
_index | KEEP _index |
Entra ID OAuth Device Code Grant by Unusual User
#Identifies when a user is observed for the first time authenticating using the device code authentication workflow. This authentication workflow can be abused by attackers to phish users and steal access tokens to impersonate the victim. By its very nature, device code should only be used when logging in to devices without keyboards, where it is difficult to enter emails and passwords. This rule only applies to Entra ID user types and detects new users leveraging this flow.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Stealth | |
| Lateral Movement |
Telemetry Coverage
Rule Body
[metadata]
creation_date = "2024/10/14"
integration = ["azure"]
maturity = "production"
updated_date = "2026/04/10"
[rule]
author = ["Elastic", "Matteo Potito Giorgio"]
description = """
Identifies when a user is observed for the first time authenticating using the device code authentication workflow. This
authentication workflow can be abused by attackers to phish users and steal access tokens to impersonate the victim. By
its very nature, device code should only be used when logging in to devices without keyboards, where it is difficult to
enter emails and passwords. This rule only applies to Entra ID user types and detects new users leveraging this flow.
"""
from = "now-9m"
index = ["filebeat-*", "logs-azure.signinlogs-*", "logs-azure.activitylogs-*"]
language = "kuery"
license = "Elastic License v2"
name = "Entra ID OAuth Device Code Grant by Unusual User"
note = """## Triage and analysis
### Investigating Entra ID OAuth Device Code Grant by Unusual User
This rule detects the first instance of a user authenticating via the DeviceCode authentication protocol within the historical window. The DeviceCode authentication workflow is designed for devices that lack keyboards, such as IoT devices and smart TVs. However, adversaries can abuse this mechanism by phishing users and stealing authentication tokens, leading to unauthorized access.
### Possible investigation steps
- Review `azure.signinlogs.properties.user_principal_name` and `azure.signinlogs.properties.user_id` to identify the user involved.
- Confirm that `azure.signinlogs.properties.authentication_protocol` is set to `deviceCode`.
- Verify the application through `azure.signinlogs.properties.app_display_name` and `azure.signinlogs.properties.app_id` to determine if it is expected.
- Check `source.ip` and compare it with previous authentication logs to determine whether the login originated from a trusted location.
- Analyze `source.geo.city_name`, `source.geo.region_name`, and `source.geo.country_name` to confirm whether the login location is suspicious.
- Review `source.as.organization.name` to check if the IP is associated with a known organization or cloud provider.
- Review `azure.signinlogs.properties.applied_conditional_access_policies` and `azure.signinlogs.properties.conditional_access_status` to determine if MFA or conditional access policies were enforced or bypassed.
- Look at `azure.signinlogs.properties.authentication_details` to confirm how authentication was satisfied.
- Review `azure.signinlogs.properties.device_detail.browser` and `user_agent.original` to determine if the login aligns with expected device behavior.
- Verify `azure.signinlogs.properties.client_app_used` to confirm whether the login was performed using a known client.
- Check if the user recently reported phishing attempts or suspicious emails.
- Look for recent changes in the user’s account settings, including password resets, role changes, or delegation of access.
- Review if other users in the environment have triggered similar DeviceCode authentication events within the same timeframe.
### False positive analysis
- If the user is setting up a new device (e.g., a smart TV or kiosk), this authentication may be expected.
- Some legitimate applications or scripts may leverage the DeviceCode authentication protocol for non-interactive logins.
- In cases where shared workstations or conference room devices are in use, legitimate users may trigger alerts.
- If the user is traveling or accessing from a new location, confirm legitimacy before taking action.
### Response and remediation
- Immediately revoke any access tokens associated with this authentication event.
- Review additional authentication logs, application access, and recent permission changes for signs of compromise.
- Reset the affected user’s credentials and enforce stricter MFA policies for sensitive accounts.
- Restrict DeviceCode authentication to only required applications.
- Enable additional logging and anomaly detection for DeviceCode logins.
- If phishing is suspected, notify the affected user and provide security awareness training on how to recognize and report phishing attempts.
- Limit DeviceCode authentication to approved users and applications via conditional access policies.
"""
references = [
"https://aadinternals.com/post/phishing/",
"https://www.blackhillsinfosec.com/dynamic-device-code-phishing/",
"https://www.volexity.com/blog/2025/02/13/multiple-russian-threat-actors-targeting-microsoft-device-code-authentication/",
"https://learn.microsoft.com/en-us/entra/identity/conditional-access/concept-authentication-flows",
"https://www.microsoft.com/en-us/security/blog/2025/02/13/storm-2372-conducts-device-code-phishing-campaign/"
]
risk_score = 47
rule_id = "af22d970-7106-45b4-b5e3-460d15333727"
setup = """#### Required Microsoft Entra ID Sign-In Logs
This rule requires the Azure integration with Microsoft Entra ID Sign-In logs to be enabled and configured to collect audit and activity logs via Azure Event Hub.
"""
severity = "medium"
tags = [
"Domain: Cloud",
"Domain: Identity",
"Data Source: Azure",
"Data Source: Microsoft Entra ID",
"Data Source: Microsoft Entra ID Sign-In Logs",
"Use Case: Identity and Access Audit",
"Tactic: Initial Access",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "new_terms"
query = '''
data_stream.dataset:(azure.activitylogs or azure.signinlogs)
and (
azure.signinlogs.properties.authentication_protocol:deviceCode or
azure.signinlogs.properties.original_transfer_method:deviceCodeFlow or
azure.activitylogs.properties.authentication_protocol:deviceCode
)
and event.outcome:success
and azure.signinlogs.properties.user_type:*
and not azure.signinlogs.properties.app_id:(
"29d9ed98-a469-4536-ade2-f981bc1d605e" or
"d5a56ea4-7369-46b8-a538-c370805301bf" or
"80faf920-1908-4b52-b5ef-a8e7bedfc67a" or
"97877f11-0fc6-4aee-b1ff-febb0519dd00" or
"245e1dee-74ef-4257-a8c8-8208296e1dfd" or
"9ba1a5c7-f17a-4de9-a1f1-6178c8d51223" or
"74bcdadc-2fdc-4bb3-8459-76d06952a0e9" or
"4813382a-8fa7-425e-ab75-3b753aab3abb" or
"a850aaae-d5a5-4e82-877c-ce54ff916282"
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1078"
name = "Valid Accounts"
reference = "https://attack.mitre.org/techniques/T1078/"
[[rule.threat.technique.subtechnique]]
id = "T1078.004"
name = "Cloud Accounts"
reference = "https://attack.mitre.org/techniques/T1078/004/"
[[rule.threat.technique]]
id = "T1566"
name = "Phishing"
reference = "https://attack.mitre.org/techniques/T1566/"
[[rule.threat.technique.subtechnique]]
id = "T1566.002"
name = "Spearphishing Link"
reference = "https://attack.mitre.org/techniques/T1566/002/"
[rule.threat.tactic]
id = "TA0001"
name = "Initial Access"
reference = "https://attack.mitre.org/tactics/TA0001/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1550"
name = "Use Alternate Authentication Material"
reference = "https://attack.mitre.org/techniques/T1550/"
[[rule.threat.technique.subtechnique]]
id = "T1550.001"
name = "Application Access Token"
reference = "https://attack.mitre.org/techniques/T1550/001/"
[rule.threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[rule.new_terms]
field = "new_terms_fields"
value = ["azure.signinlogs.properties.user_principal_name"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-7d"
Stages and Predicates
Stage 1: new_terms
data_stream.dataset:(azure.activitylogs or azure.signinlogs)
and (
azure.signinlogs.properties.authentication_protocol:deviceCode or
azure.signinlogs.properties.original_transfer_method:deviceCodeFlow or
azure.activitylogs.properties.authentication_protocol:deviceCode
)
and event.outcome:success
and azure.signinlogs.properties.user_type:*
and not azure.signinlogs.properties.app_id:(
"29d9ed98-a469-4536-ade2-f981bc1d605e" or
"d5a56ea4-7369-46b8-a538-c370805301bf" or
"80faf920-1908-4b52-b5ef-a8e7bedfc67a" or
"97877f11-0fc6-4aee-b1ff-febb0519dd00" or
"245e1dee-74ef-4257-a8c8-8208296e1dfd" or
"9ba1a5c7-f17a-4de9-a1f1-6178c8d51223" or
"74bcdadc-2fdc-4bb3-8459-76d06952a0e9" or
"4813382a-8fa7-425e-ab75-3b753aab3abb" or
"a850aaae-d5a5-4e82-877c-ce54ff916282"
)
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
azure.signinlogs.properties.app_id | in | 245e1dee-74ef-4257-a8c8-8208296e1dfd, 29d9ed98-a469-4536-ade2-f981bc1d605e, 4813382a-8fa7-425e-ab75-3b753aab3abb, 74bcdadc-2fdc-4bb3-8459-76d06952a0e9, 80faf920-1908-4b52-b5ef-a8e7bedfc67a, 97877f11-0fc6-4aee-b1ff-febb0519dd00, 9ba1a5c7-f17a-4de9-a1f1-6178c8d51223, a850aaae-d5a5-4e82-877c-ce54ff916282, d5a56ea4-7369-46b8-a538-c370805301bf | excludes:azure.signinlogs.properties.app_id |
Entra ID Phishing Kit Default OS Build (Entity Analytics)
#Identifies the first occurrence of a Microsoft Entra ID device, surfaced through the Entra ID Entity Analytics device inventory, whose host name follows the default "DESKTOP-" pattern and whose operating system build is "10.0.19045.2006". This is the frozen default device profile observed when adversary-in-the-middle (AiTM) phishing kits such as Tycoon2FA and Kali365 register Azure AD-joined devices after capturing a victim session, in order to acquire a Primary Refresh Token (PRT) and establish persistence. The build is hardcoded by the tooling and differs from legitimate hosts: a patched Windows 10 22H2 device reports a far higher "10.0.19045.<revision>" value, so a device frozen at ".2006" with a default name is a high-fidelity, though evadable, indicator.
Known False Positives
- Unmanaged or never-patched Windows 10 22H2 hosts may legitimately report the `10.0.19045.2006` build with a default "DESKTOP-" host name. Validate against your device inventory and patch baseline before escalating.
- Authorized red team or penetration testing engagements that register devices with this OS profile will appear in the device inventory and match this rule. If this is expected, add exceptions for the specific host names or device IDs.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Persistence |
Rule Body
[metadata]
creation_date = "2026/06/29"
integration = ["entityanalytics_entra_id"]
maturity = "production"
updated_date = "2026/06/29"
[rule]
author = ["Elastic"]
description = """
Identifies the first occurrence of a Microsoft Entra ID device, surfaced through the Entra ID Entity Analytics device
inventory, whose host name follows the default "DESKTOP-" pattern and whose operating system build is "10.0.19045.2006".
This is the frozen default device profile observed when adversary-in-the-middle (AiTM) phishing kits such as Tycoon2FA
and Kali365 register Azure AD-joined devices after capturing a victim session, in order to acquire a Primary Refresh
Token (PRT) and establish persistence. The build is hardcoded by the tooling and differs from legitimate hosts: a
patched Windows 10 22H2 device reports a far higher "10.0.19045.<revision>" value, so a device frozen at ".2006" with a
default name is a high-fidelity, though evadable, indicator.
"""
false_positives = [
"""
Unmanaged or never-patched Windows 10 22H2 hosts may legitimately report the `10.0.19045.2006` build with a default
"DESKTOP-" host name. Validate against your device inventory and patch baseline before escalating.
""",
"""
Authorized red team or penetration testing engagements that register devices with this OS profile will appear in the
device inventory and match this rule. If this is expected, add exceptions for the specific host names or device IDs.
""",
]
from = "now-6h"
index = ["logs-entityanalytics_entra_id.device-*"]
interval = "1h"
language = "kuery"
license = "Elastic License v2"
name = "Entra ID Phishing Kit Default OS Build (Entity Analytics)"
note = """## Triage and analysis
### Investigating Entra ID Phishing Kit Default OS Build (Entity Analytics)
AiTM phishing kits including Tycoon2FA and Kali365 register a device in Entra ID with a frozen default operating system build of `10.0.19045.2006` and a default name of `DESKTOP-<random characters>`. This build is hardcoded by the tooling and differs from the OS version of legitimate, patched hosts (a current Windows 10 22H2 device reports a much higher `10.0.19045.<revision>` value), making the build a useful indicator of kit-driven device registration. This rule runs against the Entra ID Entity Analytics device inventory and fires the first time a device matching this fingerprint appears, so an alert generally represents a newly observed rogue device rather than a real-time registration event. Rogue device registration is typically a precursor to Primary Refresh Token (PRT) acquisition, MFA/Conditional Access bypass, and persistent token-based access.
### Possible investigation steps
- Confirm the device identity via `host.name`, `host.os.version`, `entityanalytics_entra_id.device.display_name`, and `entityanalytics_entra_id.device.id` (or `device.id`). Default `DESKTOP-` names that do not match your naming convention are suspicious; kit-registered names are commonly `DESKTOP-` followed by 6 alphanumeric (Tycoon2FA) or 6 hexadecimal (Kali365) characters.
- Review `entityanalytics_entra_id.device.registration_date_time` and `entityanalytics_entra_id.device.trust_type` to establish when and how the device was registered; kit devices are typically `AzureAd` joined.
- Identify the registered owner via `entityanalytics_entra_id.device.registered_owners.user_principal_name` and determine whether that user is expected to register a new device.
- Check `entityanalytics_entra_id.device.is_managed` and `entityanalytics_entra_id.device.is_compliant`; kit-registered devices are typically unmanaged and non-compliant.
- Pivot to `logs-azure.auditlogs-*` for the corresponding `Add device` and `Register device` events (initiated by the `Device Registration Service` via the `Microsoft Authentication Broker`). Inspect the `Register device` user agent, which is frequently a spoofed `Dsreg/10.0 (Windows 10.0.19045.2006)` string or a raw HTTP client such as `axios/*` or `python-requests/*`.
- Check whether the same owner registered multiple devices in a short window (a single piece of kit infrastructure registering several devices is common for PRT persistence at scale) and whether the broker was subsequently used to mint tokens for other resources such as Microsoft Graph.
- Pivot to `logs-azure.signinlogs-*` for sign-ins by the device owner where the incoming token type is a `primaryRefreshToken`.
### False positive analysis
- Unmanaged or never-patched Windows 10 22H2 hosts may legitimately report the `10.0.19045.2006` build with a default `DESKTOP-` host name. Validate against device inventory and patch baseline.
- Authorized security assessments that register devices with this OS profile will appear in inventory. Document the engagement and add scoped exceptions.
### Response and remediation
- If confirmed malicious, remove the device from Entra ID and revoke the owner's refresh tokens and primary refresh tokens. Remove the device BEFORE revoking sessions, because device-bound PRTs survive `revokeSignInSessions`.
- Disable the account or reset credentials per policy and review for additional persistence (attacker-registered MFA methods, added owners, app registrations, or service principal credentials).
- Tighten device registration and join controls via Conditional Access (restrict who can register/join devices and require MFA for registration).
"""
references = [
"https://any.run/malware-trends/tycoon/",
"https://www.huntress.com/blog/kali365-device-code-phishing-kit",
"https://any.run/malware-trends/kali365/",
"https://arcticwolf.com/resources/blog/token-bingo-dont-let-your-code-be-the-winner/",
"https://www.ic3.gov/PSA/2026/PSA260521",
]
risk_score = 47
rule_id = "47f1d35c-8ee2-43c9-9651-90f840a0630f"
severity = "medium"
tags = [
"Domain: Cloud",
"Domain: Identity",
"Data Source: Microsoft Entra ID",
"Data Source: Microsoft Entra ID Entity Analytics",
"Use Case: Asset Visibility",
"Use Case: Threat Detection",
"Threat: Tycoon2FA",
"Threat: Kali365",
"Tactic: Persistence",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "new_terms"
query = '''
data_stream.dataset:"entityanalytics_entra_id.device" and
event.provider:"Microsoft Entra ID" and
host.name:DESKTOP-* and host.os.version:"10.0.19045.2006" and
host.id: *
'''
[[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.investigation_fields]
field_names = [
"@timestamp",
"host.name",
"host.id",
"host.os.version",
"event.provider",
"entityanalytics_entra_id.device.display_name",
"entityanalytics_entra_id.device.operating_system",
"entityanalytics_entra_id.device.operating_system_version",
"entityanalytics_entra_id.device.trust_type",
"entityanalytics_entra_id.device.profile_type",
"entityanalytics_entra_id.device.is_managed",
"entityanalytics_entra_id.device.is_compliant",
"entityanalytics_entra_id.device.registration_date_time",
"entityanalytics_entra_id.device.registered_owners.user_principal_name",
"entityanalytics_entra_id.device.id",
"device.id",
]
[rule.new_terms]
field = "new_terms_fields"
value = ["host.id"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-5d"
Stages and Predicates
Stage 1: new_terms
data_stream.dataset:"entityanalytics_entra_id.device" and
event.provider:"Microsoft Entra ID" and
host.name:DESKTOP-* and host.os.version:"10.0.19045.2006" and
host.id: *
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"entityanalytics_entra_id.device" |
event.provider | eq |
| field:"Provider_Name" kind:eq value:"Microsoft Entra ID" |
host.id | is_not_null | field:"host.id" kind:is_not_null | |
host.name | wildcard |
| field:"Computer" kind:wildcard value:"DESKTOP-*" |
host.os.version | eq |
| field:"host.os.version" kind:eq value:"10.0.19045.2006" |
Enumeration of Kernel Modules via Proc
#Loadable Kernel Modules (or LKMs) are pieces of code that can be loaded and unloaded into the kernel upon demand. They extend the functionality of the kernel without the need to reboot the system. This identifies attempts to enumerate information about a kernel module using the /proc/modules filesystem. This filesystem is used by utilities such as lsmod and kmod to list the available kernel modules.
Known False Positives
- Security tools and device drivers may run these programs in order to enumerate kernel modules. Use of these programs by ordinary users is uncommon. These can be exempted by process name or username.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Discovery |
Rule Body
[metadata]
creation_date = "2020/04/12"
integration = ["auditd_manager"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
building_block_type = "default"
description = """
Loadable Kernel Modules (or LKMs) are pieces of code that can be loaded and unloaded into the kernel upon demand. They
extend the functionality of the kernel without the need to reboot the system. This identifies attempts to enumerate
information about a kernel module using the /proc/modules filesystem. This filesystem is used by utilities such as lsmod
and kmod to list the available kernel modules.
"""
false_positives = [
"""
Security tools and device drivers may run these programs in order to enumerate kernel modules. Use of these programs
by ordinary users is uncommon. These can be exempted by process name or username.
""",
]
from = "now-119m"
index = ["auditbeat-*", "logs-auditd_manager.auditd-*"]
interval = "60m"
language = "kuery"
license = "Elastic License v2"
name = "Enumeration of Kernel Modules via Proc"
risk_score = 21
rule_id = "80084fa9-8677-4453-8680-b891d3c0c778"
setup = """## Setup
This rule requires the use of the `auditd_manager` integration. `Auditd_manager` is a tool designed to simplify and enhance the management of the audit subsystem in Linux systems. It provides a user-friendly interface and automation capabilities for configuring and monitoring system auditing through the auditd daemon. With `auditd_manager`, administrators can easily define audit rules, track system events, and generate comprehensive audit reports, improving overall security and compliance in the system. The following steps should be executed in order to install and deploy `auditd_manager` on a Linux system.
```
Kibana -->
Management -->
Integrations -->
Auditd Manager -->
Add Auditd Manager
```
`Auditd_manager` subscribes to the kernel and receives events as they occur without any additional configuration. However, if more advanced configuration is required to detect specific behavior, audit rules can be added to the integration in either the "audit rules" configuration box or the "auditd rule files" box by specifying a file to read the audit rules from.
For this detection rule to trigger, the following additional audit rules are required to be added to the integration:
```
-w /proc/ -p r -k audit_proc
```
Add the newly installed `auditd manager` to an agent policy, and deploy the agent on a Linux system from which auditd log files are desirable.
"""
severity = "low"
tags = [
"Data Source: Auditd Manager",
"OS: Linux",
"Use Case: Threat Detection",
"Tactic: Discovery",
"Rule Type: BBR",
]
timestamp_override = "event.ingested"
type = "new_terms"
query = '''
host.os.type:linux and event.category:file and event.action:"opened-file" and file.path:"/proc/modules" and
not (
process.name:(python* or chef-client) or
process.executable:(/opt/eset/*/esets_eia or /opt/Elastic/Agent/* or "/opt/jfrog/artifactory/app/metadata/bin/jf-metadata")
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1082"
name = "System Information Discovery"
reference = "https://attack.mitre.org/techniques/T1082/"
[[rule.threat.technique]]
id = "T1518"
name = "Software Discovery"
reference = "https://attack.mitre.org/techniques/T1518/"
[rule.threat.tactic]
id = "TA0007"
name = "Discovery"
reference = "https://attack.mitre.org/tactics/TA0007/"
[rule.new_terms]
field = "new_terms_fields"
value = ["process.executable"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-5d"
Stages and Predicates
Stage 1: new_terms
host.os.type:linux and event.category:file and event.action:"opened-file" and file.path:"/proc/modules" and
not (
process.name:(python* or chef-client) or
process.executable:(/opt/eset/*/esets_eia or /opt/Elastic/Agent/* or "/opt/jfrog/artifactory/app/metadata/bin/jf-metadata")
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"opened-file" |
event.category | eq |
| field:"event.category" kind:eq value:"file" |
file.path | eq |
| field:"TargetFilename" kind:eq value:"/proc/modules" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.executable | eq | /opt/jfrog/artifactory/app/metadata/bin/jf-metadata | excludes:process.executable field:"process.executable" value:"/opt/jfrog/artifactory/app/metadata/bin/jf-metadata" |
process.executable | starts_with | /opt/Elastic/Agent/ | excludes:process.executable field:"process.executable" value:"/opt/Elastic/Agent/" |
process.executable | wildcard | /opt/eset/*/esets_eia | excludes:process.executable field:"process.executable" value:"/opt/eset/*/esets_eia" |
process.name | eq | chef-client | excludes:process.name field:"process.name" value:"chef-client" |
process.name | starts_with | python | excludes:process.name field:"process.name" value:"python" |
Execution of a File Written by a Signed Binary Proxy
#Identifies the execution of a file written or modified by a signed Microsoft binary proxy utility such as MSHTA.exe, CertReq.exe or CertUtil.exe. Adversaries may bypass process and/or signature-based defenses by proxying execution of malicious content with signed binaries.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth | |
| Command & Control |
Rule Body
[rule]
description = """
Identifies the execution of a file written or modified by a signed Microsoft binary proxy utility such as MSHTA.exe,
CertReq.exe or CertUtil.exe. Adversaries may bypass process and/or signature-based defenses by proxying execution of
malicious content with signed binaries.
"""
id = "ccbc4a79-3bae-4623-aaef-e28a96bf538b"
license = "Elastic License v2"
name = "Execution of a File Written by a Signed Binary Proxy"
os_list = ["windows"]
version = "1.0.32"
query = '''
sequence with maxspan=5m
[file where event.action != "deletion" and
(process.name : ("MSHTA.EXE", "CertUtil.exe", "CertReq.exe", "PrintBrm.exe") or
process.executable : "?:\\Windows\\sys*\\OpenSSH\\sftp.exe") and
not file.path : ("?:\\Program Files (x86)\\*.exe", "?:\\Program Files\\*.exe")] as event0
[process where event.action == "start" and
startswith~(process.executable, event0.file.path) and
not process.parent.executable : ("?:\\Windows\\System32\\drvinst.exe") and
not (process.code_signature.subject_name: "Bentley Systems, Incorporated" and process.code_signature.trusted == true)]
'''
min_endpoint_version = "8.4.0"
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1
[[optional_actions]]
action = "rollback"
field = "process.entity_id"
state = 1
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1218"
name = "System Binary Proxy Execution"
reference = "https://attack.mitre.org/techniques/T1218/"
[[threat.technique.subtechnique]]
id = "T1218.005"
name = "Mshta"
reference = "https://attack.mitre.org/techniques/T1218/005/"
[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.4.0"
Stages and Predicates
Stage 1: file
[file where event.action != "deletion" and
(process.name : ("MSHTA.EXE", "CertUtil.exe", "CertReq.exe", "PrintBrm.exe") or
process.executable : "?:\\Windows\\sys*\\OpenSSH\\sftp.exe") and
not file.path : ("?:\\Program Files (x86)\\*.exe", "?:\\Program Files\\*.exe")] as event0
Stage 2: process
[process where event.action == "start" and
startswith~(process.executable, event0.file.path) and
not process.parent.executable : ("?:\\Windows\\System32\\drvinst.exe") and
not (process.code_signature.subject_name: "Bentley Systems, Incorporated" and process.code_signature.trusted == true)]
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"start" |
event.action | ne |
| field:"EventType" kind:ne value:"deletion" |
process.executable | starts_with |
| field:"Image" kind:starts_with value:"event0.file.path" |
process.executable | wildcard |
| field:"Image" kind:wildcard value:"?:\Windows\sys*\OpenSSH\sftp.exe" |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
file.path | wildcard | ?:\Program Files (x86)\*.exe, ?:\Program Files\*.exe | excludes:file.path field:"file.path" value:"?:\Program Files (x86)\*.exe" field:"file.path" value:"?:\Program Files\*.exe" |
process.code_signature.subject_name | eq | Bentley Systems, Incorporated | excludes:process.code_signature.subject_name field:"process.code_signature.subject_name" value:"Bentley Systems, Incorporated" |
process.code_signature.trusted | eq | true | excludes:process.code_signature.trusted field:"process.code_signature.trusted" value:"true" |
process.parent.executable | eq | ?:\Windows\System32\drvinst.exe | excludes:process.parent.executable field:"process.parent.executable" value:"?:\Windows\System32\drvinst.exe" |
Indirect Command Execution via Console Window Host
#Identifies abuse of the Console Window Host (conhost.exe) to execute an arbitrary executable. This behavior is used as a defense evasion technique to blend-in malicious activity with legitimate Windows software.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies abuse of the Console Window Host (conhost.exe) to execute an arbitrary executable. This behavior is used as a
defense evasion technique to blend-in malicious activity with legitimate Windows software.
"""
id = "4b61b37d-c569-444a-bafa-e29d221ee55c"
license = "Elastic License v2"
name = "Indirect Command Execution via Console Window Host"
os_list = ["windows"]
reference = ["https://lolbas-project.github.io/lolbas/Binaries/Conhost/"]
version = "1.0.32"
query = '''
process where event.action == "start" and
process.parent.name : "conhost.exe" and process.parent.args_count >= 2 and
process.parent.command_line : ("*conhost* *.exe*", "*cmd /c *", "*powershell*", "*script*", "*mshta*", "* curl *") and
not process.command_line :
("?:\\windows\\system32\\cmd.exe",
"?:\\windows\\SysWOW64\\cmd.exe", "cmd.exe",
"?:\\windows\\system32\\windowspowershell\\*\\powershell.exe",
"powershell.exe -NoProfile -ExecutionPolicy Bypass -File winget-upgrade.ps1",
"powershell.exe -NoProfile -ExecutionPolicy Bypass -File WAU-Notify.ps1") and
not process.parent.executable : "\\Device\\Mup\\*\\IBM\\ClientSolutions\\Start_Programs\\Windows*\\acslaunch_win-*.exe" and
not process.hash.sha256 : "b37565fabde8680ef7d0de3c808096b7512f42c62071f2fb486da14b773ec04a" and
not process.executable : ("?:\\Program Files\\*.exe", "?:\\Program Files (x86)\\*.exe") and
not (process.code_signature.subject_name == "International Business Machines Corporation" and process.code_signature.trusted == true) and
not (process.name : "powershell.exe" and process.args : "-ExecutionPolicy" and process.args : ("-F", "Stop-Process*")) and
not (process.args in ("/bin/sh", "bash") and process.parent.args == "--height" and process.parent.args == "24")
'''
min_endpoint_version = "7.15.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 = "T1202"
name = "Indirect Command Execution"
reference = "https://attack.mitre.org/techniques/T1202/"
[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 : "conhost.exe" and process.parent.args_count >= 2 and
process.parent.command_line : ("*conhost* *.exe*", "*cmd /c *", "*powershell*", "*script*", "*mshta*", "* curl *") and
not process.command_line :
("?:\\windows\\system32\\cmd.exe",
"?:\\windows\\SysWOW64\\cmd.exe", "cmd.exe",
"?:\\windows\\system32\\windowspowershell\\*\\powershell.exe",
"powershell.exe -NoProfile -ExecutionPolicy Bypass -File winget-upgrade.ps1",
"powershell.exe -NoProfile -ExecutionPolicy Bypass -File WAU-Notify.ps1") and
not process.parent.executable : "\\Device\\Mup\\*\\IBM\\ClientSolutions\\Start_Programs\\Windows*\\acslaunch_win-*.exe" and
not process.hash.sha256 : "b37565fabde8680ef7d0de3c808096b7512f42c62071f2fb486da14b773ec04a" and
not process.executable : ("?:\\Program Files\\*.exe", "?:\\Program Files (x86)\\*.exe") and
not (process.code_signature.subject_name == "International Business Machines Corporation" and process.code_signature.trusted == true) and
not (process.name : "powershell.exe" and process.args : "-ExecutionPolicy" and process.args : ("-F", "Stop-Process*")) and
not (process.args in ("/bin/sh", "bash") and process.parent.args == "--height" and process.parent.args == "24")
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_count | ge |
| field:"process.parent.args_count" kind:ge value:"2" |
process.parent.command_line | wildcard |
| field:"ParentCommandLine" kind:wildcard |
process.parent.name | wildcard |
| field:"parent_process_basename" kind:wildcard value:"conhost.exe" |
Exclusions
The rule actively suppresses these predicates.
Kernel Seeking Activity
#This rule detects kernel seeking activity through several built-in Linux utilities. Attackers may use these utilities to search the Linux kernel for available symbols, functions, and other information that can be used to exploit the kernel.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth | |
| Discovery | |
| Collection |
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 seeking activity through several built-in Linux utilities. Attackers may use these utilities
to search the Linux kernel for available symbols, functions, and other information that can be used to exploit the
kernel.
"""
from = "now-9m"
index = ["logs-endpoint.events.process*"]
language = "eql"
license = "Elastic License v2"
name = "Kernel Seeking 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 Seeking Activity
Kernel seeking involves probing the Linux kernel for symbols and functions, often using utilities like `tail`, `cmp`, `hexdump`, `xxd`, and `dd`. Adversaries exploit this to discover vulnerabilities for kernel exploitation. The detection rule identifies suspicious execution patterns of these utilities, particularly when accessing kernel-related paths, signaling potential malicious reconnaissance or exploitation attempts.
### Possible investigation steps
- Review the process execution details to confirm the use of utilities like `tail`, `cmp`, `hexdump`, `xxd`, or `dd` with the specified arguments, focusing on the `process.name` and `process.args` fields.
- Examine the `process.parent.args` and `process.args` fields to identify the specific kernel-related paths accessed, such as those under `/boot/*`, to understand the context of the access.
- Investigate the parent process of the suspicious activity by analyzing the `process.parent` field to determine if it was initiated by a legitimate or potentially malicious process.
- Check the timeline of events around the alert to identify any preceding or subsequent suspicious activities that might indicate a broader attack pattern.
- Correlate the alert with other security events or logs from the same host to assess if there are additional indicators of compromise or related malicious activities.
- Evaluate the user account associated with the process execution to determine if it aligns with expected behavior or if it might be compromised.
### False positive analysis
- System administrators or automated scripts may use utilities like `tail`, `cmp`, `hexdump`, `xxd`, and `dd` for legitimate maintenance tasks involving kernel files. To mitigate this, identify and whitelist specific scripts or processes that are known to perform these actions regularly.
- Backup or recovery operations might involve accessing kernel-related paths with these utilities. Exclude these operations by defining exceptions for known backup tools or processes that interact with the `/boot` directory.
- Developers working on kernel modules or custom kernel builds may trigger this rule during their normal workflow. Consider excluding specific user accounts or development environments from this rule to prevent false positives.
- Security tools or monitoring solutions that perform regular checks on kernel files could be mistakenly flagged. Review and whitelist these tools to ensure they are not incorrectly identified as threats.
### Response and remediation
- Isolate the affected system from the network to prevent further unauthorized access or data exfiltration.
- Terminate any suspicious processes identified by the detection rule, particularly those involving the utilities `tail`, `cmp`, `hexdump`, `xxd`, and `dd` accessing kernel paths.
- Conduct a thorough review of system logs and process execution history to identify any additional suspicious activities or related indicators of compromise.
- Restore the system from a known good backup if any unauthorized modifications to the kernel or system files are detected.
- Update the Linux kernel and all related packages to the latest versions to patch any known vulnerabilities that could be exploited.
- Implement enhanced monitoring and alerting for similar activities, focusing on the execution of the specified utilities with kernel-related arguments.
- Escalate the incident to the security operations team for further investigation and to determine if additional systems may be affected."""
references = ["https://www.elastic.co/security-labs/declawing-pumakit"]
risk_score = 47
rule_id = "3c9f7901-01d8-465d-8dc0-5d46671035fa"
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 == "tail" and (process.args like "-c*" or process.args == "--bytes")) or
(process.name == "cmp" and process.args == "-i") or
(process.name in ("hexdump", "xxd") and process.args == "-s") or
(process.name == "dd" and process.args like "seek*")
) and process.parent.executable != null and
not (
process.parent.executable in (
"/usr/lib/needrestart/vmlinuz-get-version", "/bin/dracut", "/sbin/dracut", "/usr/sbin/dracut"
) or
process.parent.args in (
"/usr/bin/dracut", "/usr/lib/needrestart/vmlinuz-get-version", "/sbin/dracut", "/bin/dracut",
"/usr/sbin/dracut", "/usr/bin/spectre-meltdown-checker", "/usr/lib/module-init-tools/lsinitrd-quick"
)
)
'''
[[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.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1005"
name = "Data from Local System"
reference = "https://attack.mitre.org/techniques/T1005/"
[rule.threat.tactic]
id = "TA0009"
name = "Collection"
reference = "https://attack.mitre.org/tactics/TA0009/"
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 == "tail" and (process.args like "-c*" or process.args == "--bytes")) or
(process.name == "cmp" and process.args == "-i") or
(process.name in ("hexdump", "xxd") and process.args == "-s") or
(process.name == "dd" and process.args like "seek*")
) and process.parent.executable != null and
not (
process.parent.executable in (
"/usr/lib/needrestart/vmlinuz-get-version", "/bin/dracut", "/sbin/dracut", "/usr/sbin/dracut"
) or
process.parent.args in (
"/usr/bin/dracut", "/usr/lib/needrestart/vmlinuz-get-version", "/sbin/dracut", "/bin/dracut",
"/usr/sbin/dracut", "/usr/bin/spectre-meltdown-checker", "/usr/lib/module-init-tools/lsinitrd-quick"
)
)
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 |
process.args | wildcard |
| field:"process.args" kind:wildcard |
process.name | eq |
| field:"process_basename" kind:eq |
process.name | in |
| field:"process_basename" kind:in |
process.parent.args | wildcard |
| field:"process.parent.args" kind:wildcard value:"/boot/*" |
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.parent.args | in | /bin/dracut, /sbin/dracut, /usr/bin/dracut, /usr/bin/spectre-meltdown-checker, /usr/lib/module-init-tools/lsinitrd-quick, /usr/lib/needrestart/vmlinuz-get-version, /usr/sbin/dracut | excludes:process.parent.args |
process.parent.executable | in | /bin/dracut, /sbin/dracut, /usr/lib/needrestart/vmlinuz-get-version, /usr/sbin/dracut | excludes:process.parent.executable |
Kubernetes Exposed Service Created With Type NodePort
#This rule detects an attempt to create or modify a service as type NodePort. The NodePort service allows a user to externally expose a set of labeled pods to the internet. This creates an open port on every worker node in the cluster that has a pod for that service. When external traffic is received on that open port, it directs it to the specific pod through the service representing it. A malicious user can configure a service as type Nodeport in order to intercept traffic from other pods or nodes, bypassing firewalls and other network security measures configured for load balancers within a cluster. This creates a direct method of communication between the cluster and the outside world, which could be used for more malicious behavior and certainly widens the attack surface of your cluster.
Known False Positives
- Developers may have a legitimate use for NodePorts. For frontend parts of an application you may want to expose a Service onto an external IP address without using cloud specific Loadbalancers. NodePort can be used to expose the Service on each Node's IP at a static port (the NodePort). You'll be able to contact the NodePort Service from outside the cluster, by requesting <NodeIP>:<NodePort>. NodePort unlike Loadbalancers, allow the freedom to set up your own load balancing solution, configure environments that aren't fully supported by Kubernetes, or even to expose one or more node's IPs directly.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Initial Access | |
| Persistence |
Telemetry Coverage
Rules Detecting the Same Action
These rules filter on the same operation.
- GCP K8S Service Type NodePort Deployed (Panther)
- GKE Exposed Service Created With Type NodePort (Elastic)
- Kubernetes Node Port Creation (Splunk)
- Kubernetes NodePort Service Deployed (Panther)
- Kubernetes Service with Type Node Port Deployed (Panther)
- Kubernetes Service with Type Node Port Deployed (Panther)
Rule Body
[metadata]
creation_date = "2022/07/05"
integration = ["kubernetes"]
maturity = "production"
updated_date = "2026/04/10"
[rule]
author = ["Elastic"]
description = """
This rule detects an attempt to create or modify a service as type NodePort. The NodePort service allows a user to
externally expose a set of labeled pods to the internet. This creates an open port on every worker node in the cluster
that has a pod for that service. When external traffic is received on that open port, it directs it to the specific pod
through the service representing it. A malicious user can configure a service as type Nodeport in order to intercept
traffic from other pods or nodes, bypassing firewalls and other network security measures configured for load balancers
within a cluster. This creates a direct method of communication between the cluster and the outside world, which could
be used for more malicious behavior and certainly widens the attack surface of your cluster.
"""
false_positives = [
"""
Developers may have a legitimate use for NodePorts. For frontend parts of an application you may want to expose a
Service onto an external IP address without using cloud specific Loadbalancers. NodePort can be used to expose the
Service on each Node's IP at a static port (the NodePort). You'll be able to contact the NodePort Service from
outside the cluster, by requesting <NodeIP>:<NodePort>. NodePort unlike Loadbalancers, allow the freedom to set up
your own load balancing solution, configure environments that aren't fully supported by Kubernetes, or even to
expose one or more node's IPs directly.
""",
]
index = ["logs-kubernetes.audit_logs-*"]
language = "kuery"
license = "Elastic License v2"
name = "Kubernetes Exposed Service Created With Type NodePort"
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 Kubernetes Exposed Service Created With Type NodePort
Kubernetes NodePort services enable external access to cluster pods by opening a port on each worker node. This can be exploited by attackers to bypass network security, intercept traffic, or establish unauthorized communication channels. The detection rule identifies suspicious NodePort service creation or modification by monitoring Kubernetes audit logs for specific actions and authorization decisions, helping to mitigate potential security risks.
### Possible investigation steps
- Review the Kubernetes audit logs to identify the specific service that was created or modified with the type NodePort. Focus on entries where kubernetes.audit.objectRef.resource is "services" and kubernetes.audit.verb is "create", "update", or "patch".
- Check the kubernetes.audit.annotations.authorization_k8s_io/decision field to confirm that the action was allowed, ensuring that the service creation or modification was authorized.
- Identify the user or service account responsible for the action by examining the relevant fields in the audit logs, such as the user identity or service account name.
- Investigate the context of the NodePort service by reviewing the associated pods and their labels to understand what applications or services are being exposed externally.
- Assess the network security implications by determining if the NodePort service could potentially bypass existing firewalls or security controls, and evaluate the risk of unauthorized access or data interception.
- Verify if the NodePort service is necessary for legitimate business purposes or if it was created without proper justification, indicating potential malicious intent.
### False positive analysis
- Routine service updates or deployments may trigger the rule if NodePort services are part of standard operations. To manage this, create exceptions for specific namespaces or service accounts that are known to perform these actions regularly.
- Development or testing environments often use NodePort services for ease of access. Exclude these environments from the rule by filtering based on labels or annotations that identify non-production clusters.
- Automated deployment tools or scripts that configure services as NodePort for legitimate reasons can cause false positives. Identify these tools and add their service accounts to an exception list to prevent unnecessary alerts.
- Internal services that require external access for legitimate business needs might be flagged. Document these services and apply exceptions based on their specific labels or annotations to avoid false alarms.
- Temporary configurations during incident response or troubleshooting might involve NodePort services. Ensure that these activities are logged and approved, and consider temporary exceptions during the incident resolution period.
### Response and remediation
- Immediately isolate the affected NodePort service by removing or disabling it to prevent further unauthorized access or traffic interception.
- Review and revoke any unauthorized access or permissions granted to users or service accounts that created or modified the NodePort service.
- Conduct a thorough audit of network traffic logs to identify any suspicious or unauthorized external connections made through the NodePort service.
- Implement network segmentation and firewall rules to restrict external access to critical services and ensure that only necessary ports are exposed.
- Escalate the incident to the security operations team for further investigation and to assess potential impacts on the cluster's security posture.
- Apply security patches and updates to Kubernetes components and worker nodes to mitigate any known vulnerabilities that could be exploited.
- Enhance monitoring and alerting mechanisms to detect future unauthorized NodePort service creations or modifications promptly.
## Setup
The Kubernetes Fleet integration with Audit Logs enabled or similarly structured data is required to be compatible with this rule."""
references = [
"https://kubernetes.io/docs/concepts/services-networking/service/#publishing-services-service-types",
"https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport",
"https://www.tigera.io/blog/new-vulnerability-exposes-kubernetes-to-man-in-the-middle-attacks-heres-how-to-mitigate/",
]
risk_score = 47
rule_id = "65f9bccd-510b-40df-8263-334f03174fed"
severity = "medium"
tags = ["Data Source: Kubernetes", "Tactic: Execution", "Tactic: Persistence", "Resources: Investigation Guide"]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset : "kubernetes.audit_logs"
and kubernetes.audit.annotations.authorization_k8s_io/decision:"allow"
and kubernetes.audit.objectRef.resource:"services"
and kubernetes.audit.verb:("create" or "update" or "patch")
and kubernetes.audit.requestObject.spec.type:"NodePort"
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1133"
name = "External Remote Services"
reference = "https://attack.mitre.org/techniques/T1133/"
[rule.threat.tactic]
id = "TA0003"
name = "Persistence"
reference = "https://attack.mitre.org/tactics/TA0003/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1133"
name = "External Remote Services"
reference = "https://attack.mitre.org/techniques/T1133/"
[rule.threat.tactic]
id = "TA0001"
name = "Initial Access"
reference = "https://attack.mitre.org/tactics/TA0001/"
Stages and Predicates
Stage 1: query
data_stream.dataset : "kubernetes.audit_logs"
and kubernetes.audit.annotations.authorization_k8s_io/decision:"allow"
and kubernetes.audit.objectRef.resource:"services"
and kubernetes.audit.verb:("create" or "update" or "patch")
and kubernetes.audit.requestObject.spec.type:"NodePort"
Indicators
These rows show field, operator, and value matches.
Library Loaded From a Potentially Altered Call Stack
#Detects attempts to load a networking module from a potentially altered call stack in order to conceal the true source of the call.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Detects attempts to load a networking module from a potentially altered call stack in order to conceal the true source
of the call.
"""
id = "3ab93164-3d6a-4a84-a7db-cc4dbb2012f4"
license = "Elastic License v2"
name = "Library Loaded From a Potentially Altered Call Stack"
os_list = ["windows"]
reference = ["https://www.elastic.co/security-labs/doubling-down-etw-callstacks"]
version = "1.0.8"
query = '''
library where process.executable != null and
dll.name : ("vaultcli.dll", "wmiutils.dll", "taskschd.dll", "dnsapi.dll", "dsquery.dll",
"mstask.dll", "mstscax.dll", "sqlite3.dll", "ws2_32.dll", "wininet.dll", "amsi.dll",
"dnsapi.dll", "winhttp.dll", "psapi.dll", "bitsproxy.dll", "softokn3.dll",
"System.Management.Automation.dll", "Wldap32.dll", "wtsapi32.dll") and
process.thread.Ext.call_stack_summary like "ntdll.dll|*" and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info like "C:\\Windows\\Sys?????\\ntdll.dll!LdrLoadDll*") and
not stringcontains~(process.thread.Ext.call_stack_summary, process.name) and
not process.thread.Ext.call_stack_summary like ("*Unbacked*", "*Unknown*", "*hmpalert.dll*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll",
"ntdll.dll|wow64.dll|ntdll.dll", "*tmmon64.dll*",
"ntdll.dll|*wcp.dll|cbscore.dll|*",
"ntdll.dll|*$$deletemekernelbase.dll*",
"ntdll.dll|*$$deleteme.kernelbase.dll*",
"ntdll.dll|kernelbase.dll|combase.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|mscoreei.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|combase.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|clr.dll|*",
"ntdll.dll|*kernelbase.dll|clr.dll|*",
"ntdll.dll|ctiuser.dll|ntdll.dll|kernelbase.dll|ctiuser.dll|*",
"ntdll.dll|kernelbase.dll|wsmsvc.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|advapi32.dll|system.management.automation.ni.dll|clr.dll|*",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|dwminit.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|fastprox.dll|combase.dll|rpcrt4.dll|combase.dll|wbemprox.dll|*",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|seagull_v3_configdispatcher.dll|winspool.drv|printisolationproxy.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|netjoin.dll|wkssvc.dll|rpcrt4.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|doclient.dll|ucrtbase.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|msi.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|umppc2*.dll|ntdll.dll|kernelbase.dll|combase.dll|qmgr.dll|combase.dll|qmgr.dll|combase.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|devicesoftwareinstallationclient.dll|drvstore.dll|devicesoftwareinstallationclient.dll|drvstore.dll|*",
"ntdll.dll|kernelbase.dll|ucrtbase.dll|msvcp_win.dll|coremessaging.dll|dcomp.dll|windows.ui.xaml.dll|coremessaging.dll|user32.dll|ntdll.dll") and
not _arraysearch(process.thread.Ext.call_stack, $entry,
$entry.symbol_info : ("*KernelBase.dll!LoadLibrary*", "*KernelBase.dll+0x*","*ntdll.dll!TpCallbackIndependent*",
"*ntdll.dll!LdrAddLoadAsDataTable*", "*ntdll.dll!LdrUnloadDll*", "*ntdll.dll!LdrInitializeThunk*",
"*ntdll.dll!TpSimpleTryPost*", "*wcp.dll!?RtlRunPrimitiveOperationsInXmlAgainstExecutor*",
"*KernelBase.dll!FreeLibraryAndExitThread*", "?:\\Users\\*", "?:\\Program Files*", "?:\\ProgramData*",
"?:\\*\\Mount*", "\\Device\\Mup*", "D:\\*", "F:\\*", "F:\\*", "I:\\*", "?:\\Windows\\temp\\*",
"*ntdll.dll!LdrResolveDelayLoadedAPI*", "*KernelBase.dll!FindFirstFileExW*",
"*ntdll.dll!TpReleaseCleanupGroupMembers*", "*KernelBase.dll!VirtualUnlock*", "*KernelBase.dll!GetCPHashNode*",
"C:\\Windows\\System32\\KernelBase.dll!GetEnvironmentVariableW+*", "C:\\Windows\\System32\\KernelBase.dll!DeviceIoControl*",
"C:\\Windows\\System32\\KernelBase.dll!GetComputerName*", "C:\\Windows\\System32\\KernelBase.dll!CreateProcessInternal*",
"C:\\Windows\\System32\\KernelBase.dll!GetProcAddress*", "C:\\Windows\\Sys*\\ntdll.dll!LdrShutdownThread*"))
'''
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 = "T1036"
name = "Masquerading"
reference = "https://attack.mitre.org/techniques/T1036/"
[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: library
library where process.executable != null and
dll.name : ("vaultcli.dll", "wmiutils.dll", "taskschd.dll", "dnsapi.dll", "dsquery.dll",
"mstask.dll", "mstscax.dll", "sqlite3.dll", "ws2_32.dll", "wininet.dll", "amsi.dll",
"dnsapi.dll", "winhttp.dll", "psapi.dll", "bitsproxy.dll", "softokn3.dll",
"System.Management.Automation.dll", "Wldap32.dll", "wtsapi32.dll") and
process.thread.Ext.call_stack_summary like "ntdll.dll|*" and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info like "C:\\Windows\\Sys?????\\ntdll.dll!LdrLoadDll*") and
not stringcontains~(process.thread.Ext.call_stack_summary, process.name) and
not process.thread.Ext.call_stack_summary like ("*Unbacked*", "*Unknown*", "*hmpalert.dll*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll",
"ntdll.dll|wow64.dll|ntdll.dll", "*tmmon64.dll*",
"ntdll.dll|*wcp.dll|cbscore.dll|*",
"ntdll.dll|*$$deletemekernelbase.dll*",
"ntdll.dll|*$$deleteme.kernelbase.dll*",
"ntdll.dll|kernelbase.dll|combase.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|mscoreei.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|combase.dll|*",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|clr.dll|*",
"ntdll.dll|*kernelbase.dll|clr.dll|*",
"ntdll.dll|ctiuser.dll|ntdll.dll|kernelbase.dll|ctiuser.dll|*",
"ntdll.dll|kernelbase.dll|wsmsvc.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|advapi32.dll|system.management.automation.ni.dll|clr.dll|*",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|dwminit.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|fastprox.dll|combase.dll|rpcrt4.dll|combase.dll|wbemprox.dll|*",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|seagull_v3_configdispatcher.dll|winspool.drv|printisolationproxy.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|netjoin.dll|wkssvc.dll|rpcrt4.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|doclient.dll|ucrtbase.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernelbase.dll|msi.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|umppc2*.dll|ntdll.dll|kernelbase.dll|combase.dll|qmgr.dll|combase.dll|qmgr.dll|combase.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll",
"ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|devicesoftwareinstallationclient.dll|drvstore.dll|devicesoftwareinstallationclient.dll|drvstore.dll|*",
"ntdll.dll|kernelbase.dll|ucrtbase.dll|msvcp_win.dll|coremessaging.dll|dcomp.dll|windows.ui.xaml.dll|coremessaging.dll|user32.dll|ntdll.dll") and
not _arraysearch(process.thread.Ext.call_stack, $entry,
$entry.symbol_info : ("*KernelBase.dll!LoadLibrary*", "*KernelBase.dll+0x*","*ntdll.dll!TpCallbackIndependent*",
"*ntdll.dll!LdrAddLoadAsDataTable*", "*ntdll.dll!LdrUnloadDll*", "*ntdll.dll!LdrInitializeThunk*",
"*ntdll.dll!TpSimpleTryPost*", "*wcp.dll!?RtlRunPrimitiveOperationsInXmlAgainstExecutor*",
"*KernelBase.dll!FreeLibraryAndExitThread*", "?:\\Users\\*", "?:\\Program Files*", "?:\\ProgramData*",
"?:\\*\\Mount*", "\\Device\\Mup*", "D:\\*", "F:\\*", "F:\\*", "I:\\*", "?:\\Windows\\temp\\*",
"*ntdll.dll!LdrResolveDelayLoadedAPI*", "*KernelBase.dll!FindFirstFileExW*",
"*ntdll.dll!TpReleaseCleanupGroupMembers*", "*KernelBase.dll!VirtualUnlock*", "*KernelBase.dll!GetCPHashNode*",
"C:\\Windows\\System32\\KernelBase.dll!GetEnvironmentVariableW+*", "C:\\Windows\\System32\\KernelBase.dll!DeviceIoControl*",
"C:\\Windows\\System32\\KernelBase.dll!GetComputerName*", "C:\\Windows\\System32\\KernelBase.dll!CreateProcessInternal*",
"C:\\Windows\\System32\\KernelBase.dll!GetProcAddress*", "C:\\Windows\\Sys*\\ntdll.dll!LdrShutdownThread*"))
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
dll.name | wildcard |
| field:"dll.name" kind:wildcard |
process.executable | is_not_null | field:"Image" kind:is_not_null | |
process.thread.Ext.call_stack_summary | wildcard |
| field:"process.thread.Ext.call_stack_summary" kind:wildcard value:"ntdll.dll|*" |
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 | |
process.thread.Ext.call_stack_summary | contains | process.name | excludes:process.thread.Ext.call_stack_summary field:"process.thread.Ext.call_stack_summary" value:"process.name" |
process.thread.Ext.call_stack_summary | wildcard | *Unbacked*, *Unknown*, *hmpalert.dll*, ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll, ntdll.dll|wow64.dll|ntdll.dll, *tmmon64.dll*, ntdll.dll|*wcp.dll|cbscore.dll|*, ntdll.dll|*$$deletemekernelbase.dll*, ntdll.dll|*$$deleteme.kernelbase.dll*, ntdll.dll|kernelbase.dll|combase.dll|*, ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|mscoreei.dll|*, ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|combase.dll|*, ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|clr.dll|*, ntdll.dll|*kernelbase.dll|clr.dll|*, ntdll.dll|ctiuser.dll|ntdll.dll|kernelbase.dll|ctiuser.dll|*, ntdll.dll|kernelbase.dll|wsmsvc.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll, ntdll.dll|advapi32.dll|system.management.automation.ni.dll|clr.dll|*, ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|dwminit.dll|kernel32.dll|ntdll.dll, ntdll.dll|kernelbase.dll|fastprox.dll|combase.dll|rpcrt4.dll|combase.dll|wbemprox.dll|*, ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|seagull_v3_configdispatcher.dll|winspool.drv|printisolationproxy.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll, ntdll.dll|kernelbase.dll|netjoin.dll|wkssvc.dll|rpcrt4.dll|kernelbase.dll|ntdll.dll|kernel32.dll|ntdll.dll, ntdll.dll|kernelbase.dll|doclient.dll|ucrtbase.dll|kernel32.dll|ntdll.dll, ntdll.dll|kernelbase.dll|msi.dll|kernel32.dll|ntdll.dll, ntdll.dll|umppc2*.dll|ntdll.dll|kernelbase.dll|combase.dll|qmgr.dll|combase.dll|qmgr.dll|combase.dll|rpcrt4.dll|combase.dll|rpcrt4.dll|ntdll.dll|kernel32.dll|ntdll.dll, ntdll.dll|kernel32.dll|kernelbase.dll|kernel32.dll|devicesoftwareinstallationclient.dll|drvstore.dll|devicesoftwareinstallationclient.dll|drvstore.dll|*, ntdll.dll|kernelbase.dll|ucrtbase.dll|msvcp_win.dll|coremessaging.dll|dcomp.dll|windows.ui.xaml.dll|coremessaging.dll|user32.dll|ntdll.dll | excludes:process.thread.Ext.call_stack_summary |
M365 Exchange Mailbox High-Risk Permission Delegated
#Identifies the assignment of rights to access content from another mailbox. An adversary may use the compromised account to send messages to other accounts in the network of the target organization while creating inbox rules, so messages can evade spam/phishing detection mechanisms.
Known False Positives
- Assignment of rights to a service account.
- Delegation by first-party applications that require mailbox access.
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 = "2021/05/17"
integration = ["o365"]
maturity = "production"
updated_date = "2026/04/10"
[rule]
author = ["Elastic", "Austin Songer"]
description = """
Identifies the assignment of rights to access content from another mailbox. An adversary may use the compromised account
to send messages to other accounts in the network of the target organization while creating inbox rules, so messages can
evade spam/phishing detection mechanisms.
"""
false_positives = [
"Assignment of rights to a service account.",
"Delegation by first-party applications that require mailbox access."
]
index = ["filebeat-*", "logs-o365.audit-*"]
language = "kuery"
license = "Elastic License v2"
name = "M365 Exchange Mailbox High-Risk Permission Delegated"
note = """## Triage and Analysis
### Investigating M365 Exchange Mailbox High-Risk Permission Delegated
This rule detects the delegation of mailbox permissions in Microsoft 365 Exchange. This behavior may indicate that an adversary is attempting to gain access to another user's mailbox or send messages on behalf of that user.
### Possible Investigation Steps
- `user.id` and `o365.audit.Parameters.Identity`: Determine which account was delegated access and which account performed the delegation. Review both for unusual activity.
- `event.action`: Indicates the type of permission granted. Review which delegation action was taken.
- `o365.audit.Parameters.AccessRights` or `GrantSendOnBehalfTo`: Confirm the exact permission granted.
- `@timestamp` and `event.ingested`: Review the timing of the delegation and whether it aligns with user activity or known business events.
- `source.ip` and `source.geo`: Validate that the source IP and location are expected for the admin or account performing the action.
- `user_agent.original`: If present, review to identify any automation, script, or unexpected interface used to assign the permissions.
#### FullAccess (`Add-MailboxPermission`)
- `o365.audit.Parameters.Identity`: The mailbox being accessed.
- `o365.audit.Parameters.User`: The user granted FullAccess.
- Review for subsequent mailbox logins or message rules created by the grantee.
#### SendAs (`Add-RecipientPermission`)
- `o365.audit.Parameters.Identity`: The account the grantee is allowed to impersonate.
- `o365.audit.Parameters.Trustee`: The user who was granted the ability to send as the identity.
- Search for recent messages sent "as" the identity and validate whether the activity was legitimate.
#### SendOnBehalf (`Set-Mailbox`)
- `o365.audit.Parameters.GrantSendOnBehalfTo`: The user allowed to send on behalf of the mailbox owner.
- Check for outbound emails or meeting requests with "on behalf of" headers.
### False Positive Analysis
- Delegation to Assistants: Executive or admin assistants often receive FullAccess or SendOnBehalf permissions.
- Shared Mailboxes: Teams or departments may share access to mailboxes for operational efficiency.
- Automated Admin Actions: System or service accounts may perform these actions as part of onboarding or automation.
- Project-Based Access: Temporary access granted for short-term collaboration.
- Maintain an allowlist of known delegation relationships.
### Response and Remediation
If the delegation is determined to be unauthorized or suspicious:
- Revoke the delegated permissions immediately to prevent further access.
- Reset credentials for the impacted accounts if compromise is suspected.
- Review mailbox rules and sent items to detect abuse.
- Alert impacted users and advise on suspicious activity to watch for.
- Audit audit logs around the delegation for additional attacker actions (e.g., MFA disablement, mailbox rule creation, login from foreign IPs).
- Review conditional access, role-based access control, and app permissions to reduce the attack surface.
- Harden delegation policies by requiring approvals, limiting delegation to specific groups, or implementing Just-in-Time (JIT) access for mailboxes.
"""
references = [
"https://learn.microsoft.com/en-us/microsoft-365/admin/add-users/give-mailbox-permissions-to-another-user?view=o365-worldwide"
]
risk_score = 21
rule_id = "0ce6487d-8069-4888-9ddd-61b52490cebc"
severity = "low"
tags = [
"Domain: Cloud",
"Domain: SaaS",
"Data Source: Microsoft 365",
"Data Source: Microsoft Exchange",
"Data Source: Microsoft 365 Audit Logs",
"Use Case: Configuration Audit",
"Tactic: Persistence",
"Resources: Investigation Guide"
]
timestamp_override = "event.ingested"
type = "new_terms"
query = '''
data_stream.dataset: "o365.audit" and
event.provider: "Exchange" and
event.outcome: "success" and
not o365.audit.UserType : (3 or 4) and
(
(event.action: "Add-MailboxPermission" and o365.audit.Parameters.AccessRights: "FullAccess") or
(event.action: "Add-RecipientPermission" and o365.audit.Parameters.AccessRights: "SendAs") or
(event.action: "Set-Mailbox" and o365.audit.Parameters.GrantSendOnBehalfTo: *)
) and
not user.id:(
"NT AUTHORITY\SYSTEM (Microsoft.Exchange.ServiceHost)" or
"NT AUTHORITY\SYSTEM (Microsoft.Exchange.AdminApi.NetCore)" or
"NT AUTHORITY\SYSTEM (w3wp)"
)
'''
[rule.investigation_fields]
field_names = [
"@timestamp",
"o365.audit.ObjectId",
"o365.audit.Parameters.Identity",
"user.id",
"source.ip",
"user_agent.original",
"event.action",
]
[[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.002"
name = "Additional Email Delegate Permissions"
reference = "https://attack.mitre.org/techniques/T1098/002/"
[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.002"
name = "Additional Email Delegate Permissions"
reference = "https://attack.mitre.org/techniques/T1098/002/"
[rule.threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"
[rule.new_terms]
field = "new_terms_fields"
value = ["o365.audit.UserId"]
[[rule.new_terms.history_window_start]]
field = "history_window_start"
value = "now-14d"
Stages and Predicates
Stage 1: new_terms
data_stream.dataset: "o365.audit" and
event.provider: "Exchange" and
event.outcome: "success" and
not o365.audit.UserType : (3 or 4) and
(
(event.action: "Add-MailboxPermission" and o365.audit.Parameters.AccessRights: "FullAccess") or
(event.action: "Add-RecipientPermission" and o365.audit.Parameters.AccessRights: "SendAs") or
(event.action: "Set-Mailbox" and o365.audit.Parameters.GrantSendOnBehalfTo: *)
) and
not user.id:(
"NT AUTHORITY\SYSTEM (Microsoft.Exchange.ServiceHost)" or
"NT AUTHORITY\SYSTEM (Microsoft.Exchange.AdminApi.NetCore)" or
"NT AUTHORITY\SYSTEM (w3wp)"
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"o365.audit" |
event.action | eq |
| field:"EventType" kind:eq |
event.outcome | eq |
| field:"event.outcome" kind:eq value:"success" |
event.provider | eq |
| field:"Provider_Name" kind:eq value:"Exchange" |
o365.audit.Parameters.AccessRights | eq |
| field:"o365.audit.Parameters.AccessRights" kind:eq |
o365.audit.Parameters.GrantSendOnBehalfTo | is_not_null | field:"o365.audit.Parameters.GrantSendOnBehalfTo" kind:is_not_null |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
o365.audit.UserType | in | 3, 4 | excludes:o365.audit.UserType field:"o365.audit.UserType" value:"3" field:"o365.audit.UserType" value:"4" |
user.id | in | NT AUTHORITY\SYSTEM (Microsoft.Exchange.AdminApi.NetCore), NT AUTHORITY\SYSTEM (Microsoft.Exchange.ServiceHost), NT AUTHORITY\SYSTEM (w3wp) | excludes:user.id field:"user.id" value:"NT AUTHORITY\SYSTEM (Microsoft.Exchange.AdminApi.NetCore)" field:"user.id" value:"NT AUTHORITY\SYSTEM (Microsoft.Exchange.ServiceHost)" field:"user.id" value:"NT AUTHORITY\SYSTEM (w3wp)" |
Potential Database Dumping Activity
#This rule detects the use of database dumping utilities to exfiltrate data from a database. Attackers may attempt to dump the database to a file on the system and then exfiltrate the file to a remote server.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Collection | |
| Exfiltration |
Rule Body
[metadata]
creation_date = "2026/03/13"
integration = ["endpoint", "crowdstrike", "sentinel_one_cloud_funnel"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
description = """
This rule detects the use of database dumping utilities to exfiltrate data from a database. Attackers
may attempt to dump the database to a file on the system and then exfiltrate the file to a remote server.
"""
from = "now-9m"
index = [
"endgame-*",
"logs-crowdstrike.fdr*",
"logs-endpoint.events.process*",
"logs-sentinel_one_cloud_funnel.*",
]
language = "eql"
license = "Elastic License v2"
name = "Potential Database Dumping 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 Potential Database Dumping Activity
This alert flags a Linux process starting a common database export tool, which matters because these utilities can quickly copy entire datasets into portable files for theft. An attacker with shell access may run mysqldump, pg_dump, or mongodump to dump customer records or application data to disk and then transfer the archive off the host over a separate network channel.
### Possible investigation steps
- Review the full command line, parent and ancestor process chain, and execution user to determine whether the dump was launched by approved backup automation, an administrator shell, or an unexpected process such as a web server or scripting interpreter.
- Validate whether the account and host normally perform database backups by comparing the activity with change windows, cron or systemd timer jobs, deployment scripts, and historical executions on this and similar systems.
- Identify any dump artifacts created around the alert by looking for new large files, archive or compression activity, staging in temporary directories, or writes to mounted shares that could indicate preparation for transfer.
- Examine surrounding authentication and network activity for signs of compromise or exfiltration, including recent SSH or VPN access to the host, unusual database logins, and outbound connections or file transfers shortly after the dump began.
- If the activity is not authorized, isolate the host as appropriate and scope for related activity across the environment by searching for the same user, parent process, command pattern, and follow-on transfer utilities on other systems.
### False positive analysis
- Scheduled backup or maintenance scripts may legitimately run pg_dump, mysqldump, or mongodump on Linux database hosts; confirm the execution user, parent process, and timing match documented cron or systemd jobs and that the output is written to the expected backup location.
- A DBA or application administrator may manually export data for migration, troubleshooting, or upgrade validation; verify the user account, shell history or change records, and command-line options align with an approved maintenance task and that no unusual outbound transfer follows the dump.
### Response and remediation
- Quarantine the affected Linux host from the network except for approved management access, stop any active pg_dump, mysqldump, mariadb-dump, pg_dumpall, or mongodump activity and any follow-on compression or transfer processes, and block the account and destination used to stage the dump.
- Remove attacker persistence by deleting unauthorized cron jobs, systemd services or timers, startup scripts, SSH authorized_keys entries, web shells, and any scripts or binaries used to create, archive, or move the database export.
- Revoke and rotate the database credentials, local passwords, SSH keys, and API tokens exposed on the host, then review database users for newly granted backup, export, replication, or superuser privileges and disable anything not explicitly approved.
- Restore to a known-good state by rebuilding the host or reverting from a trusted image, validating the database against clean backups, and deleting dump files, archives, and copied datasets from temporary directories, mounted shares, and storage buckets.
- Escalate to incident response immediately if any dump file was transferred to an external server, cloud service, or user workstation, if similar dumping activity is found on other hosts, or if the attacker used a privileged administrator or database account.
- Harden the environment by limiting dump utilities to approved backup hosts and service accounts, enforcing MFA and least privilege for administrators, restricting outbound network paths from database servers, and alerting on new dump archives or unexpected database export tool execution.
"""
references = [
"https://cloud.google.com/blog/topics/threat-intelligence/disrupting-gridtide-global-espionage-campaign?hl=en"
]
risk_score = 21
rule_id = "47fdd8e9-2f53-4648-afbf-0c6dd52f3ce5"
setup = """## Setup
This rule requires data coming in from Elastic Defend.
### Elastic Defend Integration Setup
Elastic Defend is integrated into the Elastic Agent using Fleet. Upon configuration, the integration allows the Elastic Agent to monitor events on your host and send data to the Elastic Security app.
#### Prerequisite Requirements:
- Fleet is required for Elastic Defend.
- To configure Fleet Server refer to the [documentation](https://www.elastic.co/guide/en/fleet/current/fleet-server.html).
#### The following steps should be executed in order to add the Elastic Defend integration on a Linux System:
- Go to the Kibana home page and click "Add integrations".
- In the query bar, search for "Elastic Defend" and select the integration to see more details about it.
- Click "Add Elastic Defend".
- Configure the integration name and optionally add a description.
- Select the type of environment you want to protect, either "Traditional Endpoints" or "Cloud Workloads".
- Select a configuration preset. Each preset comes with different default settings for Elastic Agent, you can further customize these later by configuring the Elastic Defend integration policy. [Helper guide](https://www.elastic.co/guide/en/security/current/configure-endpoint-integration-policy.html).
- We suggest selecting "Complete EDR (Endpoint Detection and Response)" as a configuration setting, that provides "All events; all preventions"
- Enter a name for the agent policy in "New agent policy name". If other agent policies already exist, you can click the "Existing hosts" tab and select an existing policy instead.
For more details on Elastic Agent configuration settings, refer to the [helper guide](https://www.elastic.co/guide/en/fleet/8.10/agent-policy.html).
- Click "Save and Continue".
- To complete the integration, select "Add Elastic Agent to your hosts" and continue to the next section to install the Elastic Agent on your hosts.
For more details on Elastic Defend refer to the [helper guide](https://www.elastic.co/guide/en/security/current/install-endpoint.html).
"""
severity = "low"
tags = [
"Domain: Endpoint",
"OS: Linux",
"Use Case: Threat Detection",
"Tactic: Exfiltration",
"Data Source: Elastic Defend",
"Data Source: Crowdstrike",
"Data Source: SentinelOne",
"Data Source: Elastic Endgame",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "linux" and event.type == "start" and
event.action in ("exec", "exec_event", "start", "ProcessRollup2") and
process.name in ("pg_dump", "pg_dumpall", "mysqldump", "mariadb-dump", "mongodump")
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1048"
name = "Exfiltration Over Alternative Protocol"
reference = "https://attack.mitre.org/techniques/T1048/"
[rule.threat.tactic]
id = "TA0010"
name = "Exfiltration"
reference = "https://attack.mitre.org/tactics/TA0010/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1119"
name = "Automated Collection"
reference = "https://attack.mitre.org/techniques/T1119/"
[[rule.threat.technique]]
id = "T1213"
name = "Data from Information Repositories"
reference = "https://attack.mitre.org/techniques/T1213/"
[rule.threat.tactic]
id = "TA0009"
name = "Collection"
reference = "https://attack.mitre.org/tactics/TA0009/"
Stages and Predicates
Stage 1: process
process where host.os.type == "linux" and event.type == "start" and
event.action in ("exec", "exec_event", "start", "ProcessRollup2") and
process.name in ("pg_dump", "pg_dumpall", "mysqldump", "mariadb-dump", "mongodump")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | in |
| field:"EventType" kind:in |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.name | in |
| field:"process_basename" kind:in |
Potential Evasion via Inline Execute Assembly
#Identifies attempts to load the Microsoft Common Language Runtime from a suspicious memory followed by an egress network connection.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies attempts to load the Microsoft Common Language Runtime from a suspicious memory followed by an egress network
connection.
"""
id = "ad65d579-b904-48e0-9408-f4c4e8e685a0"
license = "Elastic License v2"
name = "Potential Evasion via Inline Execute Assembly"
os_list = ["windows"]
reference = ["https://github.com/anthemtotheego/InlineExecute-Assembly"]
version = "1.0.22"
query = '''
sequence by process.entity_id with maxspan=5s
[library where dll.name : "mscorwks.dll" and
process.thread.Ext.call_stack_summary :
("ntdll.dll|kernelbase.dll|mscoreei.dll|Unbacked",
"ntdll.dll|kernelbase.dll|mscoreei.dll|mscoree.dll|Unbacked",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|mscoreei.dll|Unbacked") and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "*mscoreei.dll!CreateInterface*") and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "Unbacked*" and $entry.callsite_trailing_bytes : "?*") and
not (process.executable : "?:\\Program Files\\Dell\\DTP\\DiagnosticsSubAgent\\Dell.TechHub.Diagnostics.SubAgent.exe" and
process.code_signature.trusted == true and process.code_signature.subject_name : "Dell Inc") and
not (process.code_signature.trusted == true and
process.code_signature.subject_name : ("Azul Systems, Inc.", "JetBrains s.r.o.", "Milsoft Utility Solutions, Inc.")) and
not (process.executable : "C:\\ManageEngine\\ADManager Plus\\jre\\bin\\java.exe" and
process.code_signature.subject_name : "Oracle America, Inc." and process.code_signature.trusted == true) and
not (process.executable : "?:\\Program Files*\\Amazon Corretto\\jdk*\\bin\\java.exe" and
process.code_signature.subject_name : "Amazon.com Services LLC" and process.code_signature.trusted == true) and
not process.executable : ("?:\\Program Files\\Hexagon\\Cipher *\\Cipher.exe",
"?:\\Windows\\Microsoft.NET\\Framework64\\*\\dfsvc.exe",
"?:\\Program Files (x86)\\XMPie\\Circle Agent\\Service\\XMCircleAgent.exe")
]
[network where network.direction == "egress" and network.transport == "tcp"]
'''
min_endpoint_version = "8.8.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "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.8.0"
Stages and Predicates
Ordered sequence: each step below must occur in order within 5s, correlated by process.entity_id.
Stage 1: library
[library where dll.name : "mscorwks.dll" and
process.thread.Ext.call_stack_summary :
("ntdll.dll|kernelbase.dll|mscoreei.dll|Unbacked",
"ntdll.dll|kernelbase.dll|mscoreei.dll|mscoree.dll|Unbacked",
"ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|mscoreei.dll|Unbacked") and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "*mscoreei.dll!CreateInterface*") and
_arraysearch(process.thread.Ext.call_stack, $entry, $entry.symbol_info : "Unbacked*" and $entry.callsite_trailing_bytes : "?*") and
not (process.executable : "?:\\Program Files\\Dell\\DTP\\DiagnosticsSubAgent\\Dell.TechHub.Diagnostics.SubAgent.exe" and
process.code_signature.trusted == true and process.code_signature.subject_name : "Dell Inc") and
not (process.code_signature.trusted == true and
process.code_signature.subject_name : ("Azul Systems, Inc.", "JetBrains s.r.o.", "Milsoft Utility Solutions, Inc.")) and
not (process.executable : "C:\\ManageEngine\\ADManager Plus\\jre\\bin\\java.exe" and
process.code_signature.subject_name : "Oracle America, Inc." and process.code_signature.trusted == true) and
not (process.executable : "?:\\Program Files*\\Amazon Corretto\\jdk*\\bin\\java.exe" and
process.code_signature.subject_name : "Amazon.com Services LLC" and process.code_signature.trusted == true) and
not process.executable : ("?:\\Program Files\\Hexagon\\Cipher *\\Cipher.exe",
"?:\\Windows\\Microsoft.NET\\Framework64\\*\\dfsvc.exe",
"?:\\Program Files (x86)\\XMPie\\Circle Agent\\Service\\XMCircleAgent.exe")
]
Stage 2: network
[network where network.direction == "egress" and network.transport == "tcp"]
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
dll.name | wildcard |
| field:"dll.name" kind:wildcard value:"mscorwks.dll" |
network.direction | eq |
| field:"Initiated" kind:eq value:"egress" |
network.transport | eq |
| field:"Protocol" kind:eq value:"tcp" |
process.thread.Ext.call_stack_summary | wildcard |
| field:"process.thread.Ext.call_stack_summary" kind:wildcard |
Exclusions
The rule actively suppresses these predicates.
Potential Fileless Execution via Memory File Descriptor by LoLBin
#This rule detects when a process executes a file descriptor in the proc (temporary) file system via a LoLBin. This activity indicates an active attempt to execute a fileless payload and should be considered highly abnormal or suspicious. This activity can occur when the memfd syscall is utilized to create a memory resident file, like a payload, and then uses it to execute a process via a command and control channel via a LoLBin, resulting in an exec event.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth |
Rule Body
[rule]
description = """
This rule detects when a process executes a file descriptor in the proc (temporary) file system via a LoLBin. This
activity indicates an active attempt to execute a fileless payload and should be considered highly abnormal or
suspicious. This activity can occur when the memfd syscall is utilized to create a memory resident file, like a payload,
and then uses it to execute a process via a command and control channel via a LoLBin, resulting in an exec event.
"""
id = "af4a2ea7-391f-4fc2-8ccf-946f412c023b"
license = "Elastic License v2"
name = "Potential Fileless Execution via Memory File Descriptor by LoLBin"
os_list = ["linux"]
reference = ["https://man7.org/linux/man-pages/man2/memfd_create.2.html"]
version = "1.0.3"
query = '''
process where event.type == "start" and event.action == "exec" and process.interactive == true and (
process.name in (
"bash", "dash", "sh", "tcsh", "tclsh", "wish", "csh", "zsh", "ksh", "fish", "mksh",
"busybox", "pwsh", "node", "nodejs", "deno", "bun", "base64", "rscript", "escript",
"r", "julia", "mono", "dotnet", "dotnet-ef", "groovy", "kotlin", "scala", "erlang",
"ocaml", "ocamlopt", "ld.so", "ld-linux-x86-64.so.2", "awk", "gawk", "mawk", "nawk",
"env", "timeout", "nice", "stdbuf", "setsid", "setarch", "unshare", "nsenter", "flock",
"nohup", "runuser", "sudo", "snap", "snap-confine", "snap-exec", "erlexec", "beam.smp",
"java", "javaw"
) or
process.name like ("python*", "perl*", "ruby*", "lua*", "php*", "qemu-*-static")
) and
process.args regex """/proc/(self|[0-9]{1,7})/fd/[0-9]{1,7}""" and
not (
process.command_line in ("ln -f -s /proc/1/fd/2 /docker.stderr", "ln -f -s /proc/1/fd/1 /docker.stdout") or
process.parent.command_line like "*/home/*/.claude/shell-snapshots/snapshot-*" or
process.parent.executable like (
"/opt/omni/bin/drim/linux-amd64/coolie", "/bin/k3s", "/sbin/upstart", "/opt/hrt/hrtpylon-*/bin/python3.*",
"/data/k3s/*/bin/k3s", "/var/lib/docker/overlay2/*/bin/k3s", "/var/lib/rancher/k3s/*/bin/k3s",
"/usr/libexec/apptainer/bin/starter"
) or
process.executable like "/home/*/core3/plz-out/bin/third_party/python3/cpython/usr/python3*/bin/python3.*" or
(
process.parent.executable == "/sbin/apk" and
process.parent.args in ("add", "del", "upgrade")
) or
(
process.parent.executable == "/sbin/init" and
process.name == "sh" and
process.args == "-e"
) or
(
process.name == "busybox" and
process.command_line == "tee -a /proc/1/fd/1"
) or
(
process.executable == "/bin/busybox" and
process.args == "sh" and
process.args in ("/usr/bin", "/usr/sbin")
)
)
'''
min_endpoint_version = "9.1.4"
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 = "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 = "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
Stage 1: process
process where event.type == "start" and event.action == "exec" and process.interactive == true and (
process.name in (
"bash", "dash", "sh", "tcsh", "tclsh", "wish", "csh", "zsh", "ksh", "fish", "mksh",
"busybox", "pwsh", "node", "nodejs", "deno", "bun", "base64", "rscript", "escript",
"r", "julia", "mono", "dotnet", "dotnet-ef", "groovy", "kotlin", "scala", "erlang",
"ocaml", "ocamlopt", "ld.so", "ld-linux-x86-64.so.2", "awk", "gawk", "mawk", "nawk",
"env", "timeout", "nice", "stdbuf", "setsid", "setarch", "unshare", "nsenter", "flock",
"nohup", "runuser", "sudo", "snap", "snap-confine", "snap-exec", "erlexec", "beam.smp",
"java", "javaw"
) or
process.name like ("python*", "perl*", "ruby*", "lua*", "php*", "qemu-*-static")
) and
process.args regex """/proc/(self|[0-9]{1,7})/fd/[0-9]{1,7}""" and
not (
process.command_line in ("ln -f -s /proc/1/fd/2 /docker.stderr", "ln -f -s /proc/1/fd/1 /docker.stdout") or
process.parent.command_line like "*/home/*/.claude/shell-snapshots/snapshot-*" or
process.parent.executable like (
"/opt/omni/bin/drim/linux-amd64/coolie", "/bin/k3s", "/sbin/upstart", "/opt/hrt/hrtpylon-*/bin/python3.*",
"/data/k3s/*/bin/k3s", "/var/lib/docker/overlay2/*/bin/k3s", "/var/lib/rancher/k3s/*/bin/k3s",
"/usr/libexec/apptainer/bin/starter"
) or
process.executable like "/home/*/core3/plz-out/bin/third_party/python3/cpython/usr/python3*/bin/python3.*" or
(
process.parent.executable == "/sbin/apk" and
process.parent.args in ("add", "del", "upgrade")
) or
(
process.parent.executable == "/sbin/init" and
process.name == "sh" and
process.args == "-e"
) or
(
process.name == "busybox" and
process.command_line == "tee -a /proc/1/fd/1"
) or
(
process.executable == "/bin/busybox" and
process.args == "sh" and
process.args in ("/usr/bin", "/usr/sbin")
)
)
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 | regex_match |
| field:"process.args" kind:regex_match value:"/proc/(self|[0-9]{1,7})/fd/[0-9]{1,7}" |
process.interactive | eq |
| field:"process.interactive" kind:eq value:"true" |
process.name | in |
| field:"process_basename" kind:in |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
Exclusions
The rule actively suppresses these predicates.
Potential Hardware Breakpoints Evasion
#Identifies attempt to abuse a thread debug registers along with malicious exception handlers to hijack the normal execution flow of a thread. This provides an adversary an advantage to inject commands to perform unexpected, unwanted, or malicious operations.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies attempt to abuse a thread debug registers along with malicious exception handlers to hijack the normal
execution flow of a thread. This provides an adversary an advantage to inject commands to perform unexpected, unwanted,
or malicious operations.
"""
id = "b5b5afc5-f322-42ba-94aa-7ffc66b29086"
license = "Elastic License v2"
name = "Potential Hardware Breakpoints Evasion"
os_list = ["windows"]
reference = ["https://github.com/rad9800/hwbp4mw"]
version = "1.0.3"
query = '''
registry where event.action == "modification" and process.executable != null and registry.value == "CachePrefix" and
process.thread.Ext.hardware_breakpoint_set == true and
not (process.code_signature.trusted == true and
process.code_signature.subject_name in ("Roblox Corporation", "Kofax, Inc.", "PACE Anti-Piracy, Inc.", "CUMMINS INC.", "Nuance Communications, Inc.")) and
not (process.executable : "C:\\Program Files (x86)\\Java\\jre*\\bin\\jp2launcher.exe" and
process.code_signature.subject_name == "Oracle America, Inc." and process.code_signature.trusted == true) and
not (process.executable : "C:\\Program Files (x86)\\iLok License Manager\\iLok License Manager.exe" and
process.thread.Ext.call_stack_summary == "ntdll.dll|kernelbase.dll|wininet.dll|ntdll.dll|kernelbase.dll|wininet.dll|ieframe.dll|windows.storage.dll|ieframe.dll|mshtml.dll|user32.dll|winsparkle.dll|kernel32.dll|ntdll.dll") and
not (process.executable : ("C:\\Program Files (x86)\\Microsoft Office\\Office16\\MSACCESS.EXE", "C:\\Program Files (x86)\\Microsoft Office\\Office16\\OUTLOOK.EXE") and
process.thread.Ext.call_stack_summary == "ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|wininet.dll|ntdll.dll|kernelbase.dll|wininet.dll|adal.dll|mso30win32client.dll|mso20win32client.dll|kernel32.dll|ntdll.dll")
'''
min_endpoint_version = "8.11.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.technique]]
id = "T1574"
name = "Hijack Execution Flow"
reference = "https://attack.mitre.org/techniques/T1574/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.11.0"
Stages and Predicates
Stage 1: registry
registry where event.action == "modification" and process.executable != null and registry.value == "CachePrefix" and
process.thread.Ext.hardware_breakpoint_set == true and
not (process.code_signature.trusted == true and
process.code_signature.subject_name in ("Roblox Corporation", "Kofax, Inc.", "PACE Anti-Piracy, Inc.", "CUMMINS INC.", "Nuance Communications, Inc.")) and
not (process.executable : "C:\\Program Files (x86)\\Java\\jre*\\bin\\jp2launcher.exe" and
process.code_signature.subject_name == "Oracle America, Inc." and process.code_signature.trusted == true) and
not (process.executable : "C:\\Program Files (x86)\\iLok License Manager\\iLok License Manager.exe" and
process.thread.Ext.call_stack_summary == "ntdll.dll|kernelbase.dll|wininet.dll|ntdll.dll|kernelbase.dll|wininet.dll|ieframe.dll|windows.storage.dll|ieframe.dll|mshtml.dll|user32.dll|winsparkle.dll|kernel32.dll|ntdll.dll") and
not (process.executable : ("C:\\Program Files (x86)\\Microsoft Office\\Office16\\MSACCESS.EXE", "C:\\Program Files (x86)\\Microsoft Office\\Office16\\OUTLOOK.EXE") and
process.thread.Ext.call_stack_summary == "ntdll.dll|wow64.dll|wow64cpu.dll|wow64.dll|ntdll.dll|kernelbase.dll|wininet.dll|ntdll.dll|kernelbase.dll|wininet.dll|adal.dll|mso30win32client.dll|mso20win32client.dll|kernel32.dll|ntdll.dll")
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
Potential Linux Tunneling and/or Port Forwarding
#This rule monitors for a set of Linux utilities that can be used for tunneling and port forwarding. Attackers can leverage tunneling and port forwarding techniques to bypass network defenses, establish hidden communication channels, and gain unauthorized access to internal resources, facilitating data exfiltration, lateral movement, and remote control.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Command & Control |
Rule Body
[metadata]
creation_date = "2023/08/23"
integration = ["endpoint", "crowdstrike", "sentinel_one_cloud_funnel", "auditd_manager"]
maturity = "production"
updated_date = "2026/03/24"
[transform]
[[transform.osquery]]
label = "Osquery - Retrieve Listening Ports"
query = "SELECT pid, address, port, socket, protocol, path FROM listening_ports"
[[transform.osquery]]
label = "Osquery - Retrieve Open Sockets"
query = "SELECT pid, family, remote_address, remote_port, socket, state FROM process_open_sockets"
[[transform.osquery]]
label = "Osquery - Retrieve Information for a Specific User"
query = "SELECT * FROM users WHERE username = {{user.name}}"
[[transform.osquery]]
label = "Osquery - Investigate the Account Authentication Status"
query = "SELECT * FROM logged_in_users WHERE user = {{user.name}}"
[[transform.osquery]]
label = "Osquery - Retrieve Running Processes by User"
query = "SELECT pid, username, name FROM processes p JOIN users u ON u.uid = p.uid ORDER BY username"
[[transform.osquery]]
label = "Osquery - Retrieve Process Info"
query = "SELECT name, cmdline, parent, path, uid FROM processes"
[rule]
author = ["Elastic"]
description = """
This rule monitors for a set of Linux utilities that can be used for tunneling and port forwarding. Attackers can
leverage tunneling and port forwarding techniques to bypass network defenses, establish hidden communication channels,
and gain unauthorized access to internal resources, facilitating data exfiltration, lateral movement, and remote
control.
"""
from = "now-9m"
index = [
"endgame-*",
"logs-crowdstrike.fdr*",
"logs-endpoint.events.process*",
"logs-sentinel_one_cloud_funnel.*",
"auditbeat-*",
"logs-auditd_manager.auditd-*",
]
language = "eql"
license = "Elastic License v2"
name = "Potential Linux Tunneling and/or Port Forwarding"
note = """## Triage and analysis
### Investigating Potential Linux Tunneling and/or Port Forwarding
Attackers can leverage many utilities to clandestinely tunnel network communications and evade security measures, potentially gaining unauthorized access to sensitive systems.
This rule looks for several utilities that are capable of setting up tunnel network communications by analyzing process names or command line arguments.
> **Note**:
> This investigation guide uses the [Osquery Markdown Plugin](https://www.elastic.co/guide/en/security/current/invest-guide-run-osquery.html) introduced in Elastic Stack version 8.5.0. Older Elastic Stack versions will display unrendered Markdown in this guide.
> This investigation guide uses [placeholder fields](https://www.elastic.co/guide/en/security/current/osquery-placeholder-fields.html) to dynamically pass alert data into Osquery queries. Placeholder fields were introduced in Elastic Stack version 8.7.0. If you're using Elastic Stack version 8.6.0 or earlier, you'll need to manually adjust this investigation guide's queries to ensure they properly run.
#### Possible investigation steps
- Identify any signs of suspicious network activity or anomalies that may indicate protocol tunneling. This could include unexpected traffic patterns or unusual network behavior.
- Investigate listening ports and open sockets to look for potential protocol tunneling, reverse shells, or data exfiltration.
- $osquery_0
- $osquery_1
- Identify the user account that performed the action, analyze it, and check whether it should perform this kind of action.
- $osquery_2
- Investigate whether the user is currently logged in and active.
- $osquery_3
- Investigate the script execution chain (parent process tree) for unknown processes. Examine their executable files for prevalence and whether they are located in expected locations.
- $osquery_4
- $osquery_5
- Investigate other alerts associated with the user/host during the past 48 hours.
- If scripts or executables were dropped, retrieve the files and determine if they 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.
- Check if the domain is newly registered or unexpected.
- Check the reputation of the domain or IP address.
- File access, modification, and creation activities.
### Related rules
- Potential Linux Tunneling and/or Port Forwarding via Command Line - 8c8df61f-ed2a-4832-87b8-ee30812606e0
- Potential Protocol Tunneling via Chisel Client - 3f12325a-4cc6-410b-8d4c-9fbbeb744cfd
- Potential Protocol Tunneling via Chisel Server - ac8805f6-1e08-406c-962e-3937057fa86f
- Potential Protocol Tunneling via EarthWorm - 9f1c4ca3-44b5-481d-ba42-32dc215a2769
- Suspicious Utility Launched via ProxyChains - 6ace94ba-f02c-4d55-9f53-87d99b6f9af4
- ProxyChains Activity - 4b868f1f-15ff-4ba3-8c11-d5a7a6356d37
### False positive analysis
- If this activity is related to new benign software installation activity, consider adding exceptions — preferably with a combination of user and command line conditions.
- If this activity is related to a system administrator or developer who uses port tunneling/forwarding for benign purposes, consider adding exceptions for specific user accounts or hosts.
- Try to understand the context of the execution by thinking about the user, machine, or business purpose. A small number of endpoints, such as servers with unique software, might appear unusual but satisfy a specific business need.
### 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.
- 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, such as reverse shells, reverse proxies, or droppers, that attackers could use to reinfect the system.
- Remove and block malicious artifacts identified during triage.
- 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.
- 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.
- Leverage the incident response data and logging to improve the mean time to detect (MTTD) and the mean time to respond (MTTR).
"""
references = [
"https://blog.bitsadmin.com/living-off-the-foreign-land-windows-as-offensive-platform",
"https://book.hacktricks.xyz/generic-methodologies-and-resources/tunneling-and-port-forwarding",
]
risk_score = 47
rule_id = "6ee947e9-de7e-4281-a55d-09289bdf947e"
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: Command and Control",
"Data Source: Elastic Defend",
"Data Source: Elastic Endgame",
"Data Source: Crowdstrike",
"Data Source: SentinelOne",
"Data Source: Auditd Manager",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "eql"
query = '''
process where host.os.type == "linux" and event.type == "start" and event.action in ("exec", "exec_event", "start", "ProcessRollup2", "executed", "process_started") and (
(
// gost & pivotnacci - spawned without process.parent.name
(process.name == "gost" and process.args : ("-L*", "-C*", "-R*")) or (process.name == "pivotnacci")) or (
// ssh
(process.name == "ssh" and (
(
/* exact tunnel argument matching */
process.args in ("-R", "-L", "-D", "-w") or
/* single-dash token, first letter is NOT o/O, contains one of R/L/D/w/W somewhere later */
process.args regex "-[A-NP-Za-np-z][A-Za-z]*[RLDwW][A-Za-z]*"
) and
process.args_count >= 4 and
not (
process.args == "chmod" or process.command_line like "*rungencmd*"
)
)) or
(process.name == "ssh" and process.args == "-J") or
// sshuttle
(process.name == "sshuttle" and process.args in ("-r", "--remote", "-l", "--listen") and process.args_count >= 4) or
// socat
(process.name == "socat" and process.args : ("TCP4-LISTEN:*", "SOCKS*") and process.args_count >= 3) or
// chisel
(process.name : "chisel*" and process.args in ("client", "server")) or
// iodine(d), dnscat, hans, ptunnel-ng, ssf, 3proxy & ngrok
(process.name in ("iodine", "iodined", "dnscat", "hans", "hans-ubuntu", "ptunnel-ng", "ssf", "3proxy", "ngrok", "wstunnel"))
) and process.parent.name in ("bash", "dash", "ash", "sh", "tcsh", "csh", "zsh", "ksh", "fish")
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1071"
name = "Application Layer Protocol"
reference = "https://attack.mitre.org/techniques/T1071/"
[[rule.threat.technique]]
id = "T1090"
name = "Proxy"
reference = "https://attack.mitre.org/techniques/T1090/"
[[rule.threat.technique]]
id = "T1572"
name = "Protocol Tunneling"
reference = "https://attack.mitre.org/techniques/T1572/"
[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 == "linux" and event.type == "start" and event.action in ("exec", "exec_event", "start", "ProcessRollup2", "executed", "process_started") and (
(
(process.name == "gost" and process.args : ("-L*", "-C*", "-R*")) or (process.name == "pivotnacci")) or (
(process.name == "ssh" and (
(
process.args in ("-R", "-L", "-D", "-w") or
process.args regex "-[A-NP-Za-np-z][A-Za-z]*[RLDwW][A-Za-z]*"
) and
process.args_count >= 4 and
not (
process.args == "chmod" or process.command_line like "*rungencmd*"
)
)) or
(process.name == "ssh" and process.args == "-J") or
(process.name == "sshuttle" and process.args in ("-r", "--remote", "-l", "--listen") and process.args_count >= 4) or
(process.name == "socat" and process.args : ("TCP4-LISTEN:*", "SOCKS*") and process.args_count >= 3) or
(process.name : "chisel*" and process.args in ("client", "server")) or
(process.name in ("iodine", "iodined", "dnscat", "hans", "hans-ubuntu", "ptunnel-ng", "ssf", "3proxy", "ngrok", "wstunnel"))
) and process.parent.name in ("bash", "dash", "ash", "sh", "tcsh", "csh", "zsh", "ksh", "fish")
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | in |
| field:"EventType" kind:in |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.args | eq |
| field:"process.args" kind:eq value:"-J" |
process.args | in |
| field:"process.args" kind:in |
process.args | regex_match |
| field:"process.args" kind:regex_match value:"-[A-NP-Za-np-z][A-Za-z]*[RLDwW][A-Za-z]*" |
process.args | wildcard |
| field:"process.args" kind:wildcard |
process.args_count | ge |
| field:"process.args_count" kind:ge |
process.name | eq |
| field:"process_basename" kind:eq |
process.name | in |
| field:"process_basename" kind:in |
process.name | wildcard |
| field:"process_basename" kind:wildcard value:"chisel*" |
process.parent.name | in |
| field:"parent_process_basename" kind:in |
Potential Local NTLM Relay via HTTP
#Identifies attempts to coerce local NTLM authentication over HTTP through WebDAV named-pipe paths such as Print Spooler or SRVSVC. Adversaries can combine this primitive with relay tooling to elevate privileges.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth | |
| Credential Access |
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 = "2022/04/30"
integration = ["endpoint", "windows", "system", "m365_defender", "sentinel_one_cloud_funnel", "crowdstrike"]
maturity = "production"
updated_date = "2026/04/27"
[rule]
author = ["Elastic"]
description = """
Identifies attempts to coerce local NTLM authentication over HTTP through WebDAV named-pipe paths such as
Print Spooler or SRVSVC. Adversaries can combine this primitive with relay tooling to elevate privileges.
"""
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 = "Potential Local NTLM Relay via HTTP"
references = [
"https://github.com/med0x2e/NTLMRelay2Self",
"https://github.com/topotam/PetitPotam",
"https://github.com/dirkjanm/krbrelayx/blob/master/printerbug.py",
]
risk_score = 73
rule_id = "4682fd2c-cfae-47ed-a543-9bed37657aa6"
severity = "high"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Credential Access",
"Tactic: Defense Evasion",
"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 : "rundll32.exe" and
/* Rundll32 WbeDav Client */
process.args : ("?:\\Windows\\System32\\davclnt.dll,DavSetCookie", "?:\\Windows\\SysWOW64\\davclnt.dll,DavSetCookie") and
/* Access to named pipe via http */
process.args : ("http*/print/pipe/*", "http*/pipe/spoolss", "http*/pipe/srvsvc")
'''
note = """## Triage and analysis
### Investigating Potential Local NTLM Relay via HTTP
#### Possible investigation steps
- Does the alert-local command line confirm WebDAV-to-named-pipe relay behavior?
- Focus: `process.command_line` and `process.executable`; confirm rundll32.exe loads davclnt.dll,DavSetCookie and targets HTTP pipe paths: /print/pipe/, /pipe/spoolss, or /pipe/srvsvc.
- Implication: escalate when one command combines DavSetCookie with HTTP named-pipe paths, matching NTLMRelay2Self and printerbug-style coercion; close only when exact `process.command_line`, `user.id`, and `host.id` tie to authorized relay testing or explicit WebDAV/print diagnostics intentionally exercising this path.
- Is the binary identity and launch chain consistent with the relay context?
- Focus: `process.executable`, `process.pe.original_file_name`, `process.code_signature.subject_name`, `process.parent.executable`, and `process.parent.command_line`.
- Implication: escalate when rundll32.exe is renamed, outside a Windows system path, launched by a script, document, remote-management, or user-writable parent, or signer-mismatched; lower suspicion only when identity and parent chain match the authorized test or diagnostic workflow. Identity alone does not clear relay behavior.
- Did the process contact the HTTP listener implied by the relay path?
- Focus: if endpoint network telemetry exists, recover process network events with `host.id` plus `process.entity_id`; fallback to `host.id` plus `process.pid` in a tight window. Read DNS via `dns.question.name`; connections via `destination.ip` and `destination.port`. $investigate_2
- Hint: compare destinations to the HTTP host in `process.command_line`; loopback, same-host aliases, private listeners, or unexpected external HTTP infrastructure are decisive.
- Implication: escalate when traffic reaches the listener named by the relay command or an unexplained HTTP endpoint. Missing endpoint network or DNS telemetry is unresolved, not benign.
- Did authentication events explain the local rundll32 session or relay follow-on?
- Why: the process alert proves relay intent; Windows Security events can explain the operator session, while relay proof may surface as inbound NTLM on this host, target-host authentication, or DC-side validation.
- Focus: for local session context, bridge `process.Ext.authentication_id` to same-host `winlog.event_data.TargetLogonId`; on 4624, read `winlog.event_data.AuthenticationPackageName` and `source.ip`. $investigate_3
- Hint: for relay proof, search same-host inbound NTLM without `user.id`, target-host 4624/4625, and DC-side 4776 using the listener, reconstructed targets, or source addresses from command/network evidence. Search 4648 on `winlog.event_data.SubjectLogonId` only for explicit credentials from the local session.
- Implication: escalate when the local session origin is unexplained, same-host inbound NTLM appears around the alert, or target/DC authentication shows coerced machine or service-account use tied to the listener or targets. Missing authentication telemetry is unresolved, not benign.
- Is there follow-on execution, tooling, or repeated coercion around the process?
- Focus: child processes where `process.parent.entity_id` matches `process.entity_id`, reading `process.Ext.token.integrity_level_name`; if endpoint file telemetry exists, recover files with `host.id` plus `process.entity_id`, or `host.id` plus `process.pid` in a tight window, then read `file.path`. $investigate_4
- Hint: look for command lines or artifacts naming PetitPotam, printerbug, NTLMRelay2Self, ntlmrelayx, shadow credentials, RBCD, or WebClient/Print Spooler preparation.
- Implication: escalate when the window shows dropped tools, secondary scripts, repeated rundll32.exe relay attempts, privileged child processes, or WebClient/Print Spooler preparation. Missing endpoint file telemetry limits corroboration, not the alert-local finding.
- If local evidence is suspicious or unresolved, do related alerts change scope?
- Focus: related alerts for `user.id` covering credential access, relay testing, privilege escalation, or lateral movement. $investigate_0
- Hint: compare related alerts for `host.id` for spooler abuse, WebClient activity, remote execution, NTLM relay, or coercion patterns. $investigate_1
- Implication: broaden when either pivot shows repeated relay/coercion or credential-access activity outside the authorized test or diagnostic; keep local when both stay confined to that activity.
- Escalate when relay-path arguments plus binary lineage, listener contact, NTLM/auth evidence, follow-on tooling, or related alerts indicate unauthorized relay; close only when alert-local evidence and supported recovery fit one authorized workflow; preserve and escalate if evidence is mixed or incomplete.
### False positive analysis
- Authorized red-team, purple-team, relay-lab validation, or explicit WebDAV/print diagnostics can trigger this rule. Confirm that `process.command_line`, `process.parent.executable`, `user.id`, `host.id`, destination evidence if available, and authentication evidence all align with that activity. Routine WebDAV or print troubleshooting is insufficient unless it explains the DavSetCookie-to-HTTP-pipe pattern.
- Without workflow records, require a telemetry-only match across prior alerts from this rule: same `process.parent.executable`, exact `process.command_line` pattern, `user.id`, `host.id`, and supported destination or authentication pattern. Build exceptions only from that full workflow; avoid exceptions on rundll32.exe, davclnt.dll, or the pipe path alone.
### Response and remediation
- If confirmed benign, release temporary containment and document the workflow anchors: `process.executable`, `process.parent.executable`, exact `process.command_line`, `user.id`, `host.id`, and the recovered destination or authentication evidence. Create an exception only when the same full workflow recurs across prior alerts from this rule.
- If suspicious but unconfirmed, preserve the alert details, `process.entity_id` or `process.pid`, `process.command_line`, `process.parent.command_line`, process tree, recovered network or DNS records, Windows Security records, and file artifacts before containment. Apply reversible containment first, such as temporary HTTP/WebDAV restrictions or heightened monitoring on the host; isolate only if repeated relay attempts, corroborating NTLM activity, follow-on execution, or exposure on a domain controller, print server, or jump host raises the risk and the asset can tolerate isolation.
- If confirmed malicious, preserve the command line, process tree, listener details, authentication records, and dropped artifacts first. Then isolate the host through endpoint response when the evidence establishes unauthorized relay, and kill or suspend the responsible process if it is still active. Block confirmed malicious listeners, path fragments, hashes, or follow-on tools before cleanup.
- If investigation shows successful relay or privileged machine/service-account use, review and rotate affected credentials or secrets according to privilege tier, and coordinate disruptive identity or infrastructure changes before acting on domain controllers, print servers, or jump hosts.
- Before eradication, scope the same command fragment, listener, `user.id`, `host.id`, authentication indicators, and adjacent tooling across other hosts and sessions so evidence is not destroyed before spread is understood. Then remove the relay tooling and harden the exposed path, including unnecessary WebClient or Print Spooler exposure, NTLM relay mitigations, and service-specific controls identified during the investigation.
- Post-incident hardening: retain process, endpoint network, endpoint file, and Windows Security telemetry needed for this correlation, and document adjacent PetitPotam, printerbug, NTLMRelay2Self, or alternate coercion evidence for future triage.
"""
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.id",
"host.name",
"user.id",
"user.name",
"process.entity_id",
"process.pid",
"process.executable",
"process.command_line",
"process.pe.original_file_name",
"process.parent.executable",
"process.parent.command_line",
"process.code_signature.subject_name",
"process.code_signature.trusted",
"process.Ext.authentication_id",
]
[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 = "Network events for the relay process"
description = ""
providers = [
[
{ 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" },
{ excluded = false, field = "event.category", queryType = "phrase", value = "network", valueType = "string" }
]
]
relativeFrom = "now-1h"
relativeTo = "now"
[[transform.investigate]]
label = "Windows Security events for the local process session"
description = ""
providers = [
[
{ excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
{ excluded = false, field = "winlog.event_data.TargetLogonId", queryType = "phrase", value = "{{process.Ext.authentication_id}}", valueType = "string" },
{ excluded = false, field = "event.code", queryType = "phrase", value = "4624", valueType = "string" }
],
[
{ excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
{ excluded = false, field = "winlog.event_data.SubjectLogonId", queryType = "phrase", value = "{{process.Ext.authentication_id}}", valueType = "string" },
{ excluded = false, field = "event.code", queryType = "phrase", value = "4648", valueType = "string" }
]
]
relativeFrom = "now-24h"
relativeTo = "now"
[[transform.investigate]]
label = "Child process events for the relay process"
description = ""
providers = [
[
{ excluded = false, field = "host.id", queryType = "phrase", value = "{{host.id}}", valueType = "string" },
{ excluded = false, field = "process.parent.entity_id", queryType = "phrase", value = "{{process.entity_id}}", valueType = "string" },
{ excluded = false, field = "event.category", queryType = "phrase", value = "process", valueType = "string" }
]
]
relativeFrom = "now-1h"
relativeTo = "now"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1187"
name = "Forced Authentication"
reference = "https://attack.mitre.org/techniques/T1187/"
[[rule.threat.technique]]
id = "T1212"
name = "Exploitation for Credential Access"
reference = "https://attack.mitre.org/techniques/T1212/"
[[rule.threat.technique]]
id = "T1557"
name = "Adversary-in-the-Middle"
reference = "https://attack.mitre.org/techniques/T1557/"
[rule.threat.tactic]
id = "TA0006"
name = "Credential Access"
reference = "https://attack.mitre.org/tactics/TA0006/"
[[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.011"
name = "Rundll32"
reference = "https://attack.mitre.org/techniques/T1218/011/"
[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.name : "rundll32.exe" and
process.args : ("?:\\Windows\\System32\\davclnt.dll,DavSetCookie", "?:\\Windows\\SysWOW64\\davclnt.dll,DavSetCookie") and
process.args : ("http*/print/pipe/*", "http*/pipe/spoolss", "http*/pipe/srvsvc")
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:"rundll32.exe" |
Potential Privilege Escalation via Missing DLL
#Identifies the loading of a non Microsoft signed DLL that is missing on a default Windows installation (phantom DLL) or one that can be loaded from a different location by a native Windows process. This may be abused to persist or elevate privileges via privileged file write vulnerabilities.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth |
Rule Body
[rule]
description = """
Identifies the loading of a non Microsoft signed DLL that is missing on a default Windows installation (phantom DLL) or
one that can be loaded from a different location by a native Windows process. This may be abused to persist or elevate
privileges via privileged file write vulnerabilities.
"""
id = "a2a3d803-5c25-43cc-84b9-a4ae2a4dab27"
license = "Elastic License v2"
name = "Potential Privilege Escalation via Missing DLL"
os_list = ["windows"]
reference = [
"http://remoteawesomethoughts.blogspot.com/2019/05/windows-10-task-schedulerservice.html",
"http://waleedassar.blogspot.com/2013/01/wow64logdll.html",
"https://github.com/rapid7/metasploit-framework/blob/5863ff7e357af1634f5b370e811d647a9c999158/modules/exploits/windows/local/cve_2020_17136.rb#L192",
"https://googleprojectzero.blogspot.com/2018/04/windows-exploitation-tricks-exploiting.html",
"https://itm4n.github.io/windows-dll-hijacking-clarified/",
"https://shellz.club/edgegdi-dll-for-persistence-and-lateral-movement/",
"https://windows-internals.com/faxing-your-way-to-system/",
"https://www.elastic.co/security-labs/Hunting-for-Suspicious-Windows-Libraries-for-Execution-and-Evasion",
"https://www.elastic.co/security-labs/invisible-miners-unveiling-ghostengine",
]
version = "1.0.41"
query = '''
library where
user.id : "S-1-5-18" and (dll.code_signature.trusted == false or dll.code_signature.exists == false) and
(dll.Ext.relative_file_creation_time <= 172800 or dll.Ext.relative_file_name_modify_time <= 172800) and
(
dll.name :
("wlbsctrl.dll",
"WptsExtensions.dll",
"Tsmsisrv.dll",
"TSVIPSrv.dll",
"Msfte.dll",
"wow64log.dll",
"WindowsCoreDeviceInfo.dll",
"phoneinfo.dll",
"EdgeGdi.dll",
"cdpsgshims.dll",
"diagtrack_win.dll",
"wlanhlp.dll",
"healthapi.dll",
"prntvpt.dll",
"SprintCSP.dll") or
dll.path : ("?:\\Windows\\System32\\Ualapi.dll",
"?:\\Windows\\SysWOW64\\Ualapi.dll",
"?:\\Windows\\System\\Ualapi.dll",
"?:\\Windows\\Ualapi.dll",
"?:\\Windows\\System32\\oci.dll",
"?:\\Windows\\System32\\spool\\drivers\\x64\\PrintConfig.dll",
"?:\\windows\\Ualapi.dll",
"?:\\windows\\wbemcomn.dll",
"?:\\Windows\\oci.dll",
"?:\\windows\\System32\\Wbem\\Ualapi.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\wbemcomn.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\Ualapi.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\oci.dll",
"?:\\Python??\\wbemcomn.dll",
"?:\\Python??\\Ualapi.dll",
"?:\\Python??\\oci.dll",
"?:\\windows\\System32\\OpenSSH\\wbemcomn.dll",
"?:\\windows\\System32\\OpenSSH\\oci.dll",
"?:\\windows\\System32\\OpenSSH\\Ualapi.dll",
"?:\\Windows\\System32\\wbem\\wbemcomn.dll",
"?:\\Windows\\SysWOW64\\wbem\\wbemcomn.dll")
) and
not dll.path :
("?:\\Windows\\System32\\prntvpt.dll",
"?:\\Windows\\System32\\wlanhlp.dll",
"?:\\Windows\\SysWOW64\\prntvpt.dll",
"?:\\Windows\\WinSxS\\*.dll") and
not (dll.pe.imphash : "a9ab204cf2b4a1903b3fba3c920bd357" and dll.name : "Ualapi.dll")
'''
min_endpoint_version = "8.4.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 = "T1574"
name = "Hijack Execution Flow"
reference = "https://attack.mitre.org/techniques/T1574/"
[[threat.technique.subtechnique]]
id = "T1574.001"
name = "DLL"
reference = "https://attack.mitre.org/techniques/T1574/001/"
[threat.tactic]
id = "TA0004"
name = "Privilege Escalation"
reference = "https://attack.mitre.org/tactics/TA0004/"
[internal]
min_endpoint_version = "8.4.0"
Stages and Predicates
Stage 1: library
library where
user.id : "S-1-5-18" and (dll.code_signature.trusted == false or dll.code_signature.exists == false) and
(dll.Ext.relative_file_creation_time <= 172800 or dll.Ext.relative_file_name_modify_time <= 172800) and
(
dll.name :
("wlbsctrl.dll",
"WptsExtensions.dll",
"Tsmsisrv.dll",
"TSVIPSrv.dll",
"Msfte.dll",
"wow64log.dll",
"WindowsCoreDeviceInfo.dll",
"phoneinfo.dll",
"EdgeGdi.dll",
"cdpsgshims.dll",
"diagtrack_win.dll",
"wlanhlp.dll",
"healthapi.dll",
"prntvpt.dll",
"SprintCSP.dll") or
dll.path : ("?:\\Windows\\System32\\Ualapi.dll",
"?:\\Windows\\SysWOW64\\Ualapi.dll",
"?:\\Windows\\System\\Ualapi.dll",
"?:\\Windows\\Ualapi.dll",
"?:\\Windows\\System32\\oci.dll",
"?:\\Windows\\System32\\spool\\drivers\\x64\\PrintConfig.dll",
"?:\\windows\\Ualapi.dll",
"?:\\windows\\wbemcomn.dll",
"?:\\Windows\\oci.dll",
"?:\\windows\\System32\\Wbem\\Ualapi.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\wbemcomn.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\Ualapi.dll",
"?:\\windows\\System32\\WindowsPowerShell\\v1.0\\oci.dll",
"?:\\Python??\\wbemcomn.dll",
"?:\\Python??\\Ualapi.dll",
"?:\\Python??\\oci.dll",
"?:\\windows\\System32\\OpenSSH\\wbemcomn.dll",
"?:\\windows\\System32\\OpenSSH\\oci.dll",
"?:\\windows\\System32\\OpenSSH\\Ualapi.dll",
"?:\\Windows\\System32\\wbem\\wbemcomn.dll",
"?:\\Windows\\SysWOW64\\wbem\\wbemcomn.dll")
) and
not dll.path :
("?:\\Windows\\System32\\prntvpt.dll",
"?:\\Windows\\System32\\wlanhlp.dll",
"?:\\Windows\\SysWOW64\\prntvpt.dll",
"?:\\Windows\\WinSxS\\*.dll") and
not (dll.pe.imphash : "a9ab204cf2b4a1903b3fba3c920bd357" and dll.name : "Ualapi.dll")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
dll.Ext.relative_file_creation_time | le |
| field:"dll.Ext.relative_file_creation_time" kind:le value:"172800" |
dll.Ext.relative_file_name_modify_time | le |
| field:"dll.Ext.relative_file_name_modify_time" kind:le value:"172800" |
dll.code_signature.exists | eq |
| field:"dll.code_signature.exists" kind:eq value:"false" |
dll.code_signature.trusted | eq |
| field:"dll.code_signature.trusted" kind:eq value:"false" |
dll.name | wildcard |
| field:"dll.name" kind:wildcard |
dll.path | wildcard |
| field:"ImageLoaded" kind:wildcard |
user.id | wildcard |
| field:"user.id" kind:wildcard value:"S-1-5-18" |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
dll.name | eq | Ualapi.dll | excludes:dll.name field:"dll.name" value:"Ualapi.dll" |
dll.pe.imphash | eq | a9ab204cf2b4a1903b3fba3c920bd357 | excludes:dll.pe.imphash field:"dll.pe.imphash" value:"a9ab204cf2b4a1903b3fba3c920bd357" |
dll.path | wildcard | ?:\Windows\System32\prntvpt.dll, ?:\Windows\System32\wlanhlp.dll, ?:\Windows\SysWOW64\prntvpt.dll, ?:\Windows\WinSxS\*.dll | excludes:dll.path |
Potential Proxy Execution via Sed
#This rule detects the execution of a command or binary through the Sed binary. Attackers may use this technique to execute commands while attempting to evade detection.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth |
Rule Body
[rule]
description = """
This rule detects the execution of a command or binary through the Sed binary. Attackers may use this technique to
execute commands while attempting to evade detection.
"""
id = "272cf3e7-fd3f-442b-a781-f9e864fb1d4c"
license = "Elastic License v2"
name = "Potential Proxy Execution via Sed"
os_list = ["linux"]
reference = ["https://gtfobins.github.io/gtfobins/sed/"]
version = "1.0.4"
query = '''
sequence with maxspan=3s
[process where event.type == "start" and event.action == "exec" and process.parent.name == "sed" and
process.parent.args == "-n" and not process.args like "s/*"] by process.entity_id
[process where event.type == "start" and event.action == "exec" and
process.parent.name in ("bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish") and
process.parent.args == "-c"] by process.parent.entity_id
'''
min_endpoint_version = "7.15.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 1
[[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/"
[[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
Ordered sequence: each step below must occur in order within 3s, correlated by process.entity_id, process.parent.entity_id.
Stage 1: process
[process where event.type == "start" and event.action == "exec" and process.parent.name == "sed" and
process.parent.args == "-n" and not process.args like "s/*"] by process.entity_id
Stage 2: process
[process where event.type == "start" and event.action == "exec" and
process.parent.name in ("bash", "dash", "sh", "tcsh", "csh", "zsh", "ksh", "fish") and
process.parent.args == "-c"] 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 value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.parent.args | eq |
| field:"process.parent.args" kind:eq |
process.parent.name | eq |
| field:"parent_process_basename" kind:eq value:"sed" |
process.parent.name | in |
| field:"parent_process_basename" kind:in |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.args | starts_with | s/ | excludes:process.args field:"process.args" value:"s/" |
Powershell Execution via Named Pipe
#Identifies the execution of a PowerShell script that allow remote command execution via named pipe.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Lateral Movement |
Rule Body
[rule]
description = "Identifies the execution of a PowerShell script that allow remote command execution via named pipe."
id = "c286b078-793f-4c51-a49a-27948e0ed741"
license = "Elastic License v2"
name = "Powershell Execution via Named Pipe"
os_list = ["windows"]
reference = ["https://github.com/threatexpress/invoke-pipeshell/tree/master"]
version = "1.0.3"
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 : ("*Pipes.NamedPipeClientStream*.Connect(*", "*Pipes.NamedPipeServerStream*WaitForConnection*") and
process.Ext.api.parameters.buffer : "*.StreamReader*" and process.Ext.api.parameters.buffer : "*.StreamWriter*" and
process.Ext.api.parameters.buffer : "*.ReadLine*" and process.Ext.api.parameters.buffer : "*.WriteLine*" and
process.Ext.api.parameters.buffer : ("*while(*", "*while (*") and
not (process.command_line : "*AZQBjAHQAIABTAHkAcwB0AGUAbQAuAEkATwAuAFAAaQBwAGUAcwAuAE4AYQBtAGUAZABQAGkAcABlAFMAZQByAHYAZQByAFMAdAByAGUAYQBtACgAJwBpAG4AcwBwA*" and
process.Ext.api.parameters.size == 3354) and
not (process.parent.executable : ("?:\\Windows\\System32\\msiexec.exe", "?:\\Windows\\SysWOW64\\msiexec.exe") and
process.Ext.api.parameters.content_name : "?:\\WINDOWS\\SystemTemp\\ps*.ps1" and user.id == "S-1-5-18")
'''
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 = "T1021"
name = "Remote Services"
reference = "https://attack.mitre.org/techniques/T1021/"
[[threat.technique.subtechnique]]
id = "T1021.002"
name = "SMB/Windows Admin Shares"
reference = "https://attack.mitre.org/techniques/T1021/002/"
[threat.tactic]
id = "TA0008"
name = "Lateral Movement"
reference = "https://attack.mitre.org/tactics/TA0008/"
[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 : ("*Pipes.NamedPipeClientStream*.Connect(*", "*Pipes.NamedPipeServerStream*WaitForConnection*") and
process.Ext.api.parameters.buffer : "*.StreamReader*" and process.Ext.api.parameters.buffer : "*.StreamWriter*" and
process.Ext.api.parameters.buffer : "*.ReadLine*" and process.Ext.api.parameters.buffer : "*.WriteLine*" and
process.Ext.api.parameters.buffer : ("*while(*", "*while (*") and
not (process.command_line : "*AZQBjAHQAIABTAHkAcwB0AGUAbQAuAEkATwAuAFAAaQBwAGUAcwAuAE4AYQBtAGUAZABQAGkAcABlAFMAZQByAHYAZQByAFMAdAByAGUAYQBtACgAJwBpAG4AcwBwA*" and
process.Ext.api.parameters.size == 3354) and
not (process.parent.executable : ("?:\\Windows\\System32\\msiexec.exe", "?:\\Windows\\SysWOW64\\msiexec.exe") and
process.Ext.api.parameters.content_name : "?:\\WINDOWS\\SystemTemp\\ps*.ps1" and user.id == "S-1-5-18")
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.
PowerShell Script with Veeam Credential Access Capabilities
#Identifies PowerShell script block content that queries Veeam credential tables or uses ProtectedStorage to decrypt stored secrets. Attackers abuse Veeam credentials to access backup infrastructure and enable ransomware operations.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Credential Access | |
| Collection |
Rule Body
[metadata]
creation_date = "2024/03/14"
integration = ["windows"]
maturity = "production"
updated_date = "2026/03/24"
[rule]
author = ["Elastic"]
description = """
Identifies PowerShell script block content that queries Veeam credential tables or uses ProtectedStorage to decrypt stored
secrets. Attackers abuse Veeam credentials to access backup infrastructure and enable ransomware operations.
"""
from = "now-9m"
index = ["winlogbeat-*", "logs-windows.powershell*"]
language = "kuery"
license = "Elastic License v2"
name = "PowerShell Script with Veeam Credential Access Capabilities"
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 PowerShell Script with Veeam Credential Access Capabilities
This alert indicates PowerShell script content consistent with accessing credential material used by Veeam, either by querying the Veeam configuration database credential table or by invoking ProtectedStorage decryption routines. Because backup credentials often provide privileged access to infrastructure and backup systems, treat this activity as high risk until verified as authorized.
#### Key alert fields to review
- `user.name`, `user.domain`, `user.id`: Account execution context for correlation, prioritization, and scoping.
- `host.name`, `host.id`: Host execution context for correlation, prioritization, and scoping.
- `powershell.file.script_block_text`: Script block content that matched the detection logic.
- `powershell.file.script_block_id`, `powershell.sequence`, `powershell.total`: Script block metadata to pivot to other fragments or reconstruct full script content when split across multiple events.
- `file.path`, `file.directory`, `file.name`: File-origin context when the script block is sourced from an on-disk file.
- `powershell.file.script_block_length`: Script block length (size) context.
#### Possible investigation steps
- Confirm execution context and prioritize:
- Review `host.name` and `host.id` to determine whether the activity occurred on a host expected to administer Veeam or access its configuration database.
- Review `user.name`, `user.domain`, and `user.id` to determine whether the initiating account is expected to perform backup administration, database querying, or credential recovery activities.
- Note the alert `@timestamp` and determine whether it aligns with an approved maintenance window or change activity.
- Analyze the script block content for intent:
- Review `powershell.file.script_block_text` to understand which capability is present:
- Credential table access patterns (for example, references to `[dbo].[Credentials]` with Veeam-related identifiers).
- ProtectedStorage decryption usage (for example, `ProtectedStorage]::GetLocalString`), which may indicate an attempt to decrypt stored secret material.
- Identify and record any embedded target details present in the script content (database server names, instances, connection parameters, or credential object identifiers) to drive scoping and correlation.
- Look for evidence of data handling that suggests extraction, such as formatting credential data, aggregating results, writing output to disk, or preparing data for transfer.
- Reconstruct the complete script when split across multiple events:
- Group related events by `powershell.file.script_block_id` and order them by `powershell.sequence` through `powershell.total` to rebuild the full script logic before assessing intent.
- If only one fragment triggered the alert, ensure you retrieve the remaining fragments for the same `powershell.file.script_block_id`, since supporting logic may be contained in non-matching fragments.
- Use `powershell.file.script_block_length` as context; unusually large script blocks can indicate imported tooling or staged functionality rather than routine administration.
- Determine script origin and assess whether it is expected:
- If `file.path`, `file.directory`, or `file.name` are present, identify the on-disk script source and evaluate whether the location and naming align with approved administrative scripts (versus unexpected user-writable locations).
- If file metadata is absent, consider inline or remote execution and prioritize correlation with other endpoint telemetry to identify how PowerShell was initiated.
- Scope within PowerShell telemetry:
- Search for additional PowerShell script block activity from the same `host.name` and `user.name` near the alert time to identify surrounding steps (database connectivity setup, credential parsing, decryption routines, or output handling).
- Pivot on `powershell.file.script_block_id` to determine whether the script was executed repeatedly on the same host, and whether the same script appears on other hosts or under different users.
- Search for other occurrences of the same key strings in `powershell.file.script_block_text` across hosts and users to identify broader use, reuse, or distribution.
- Correlate with adjacent telemetry to validate access and identify follow-on behavior:
- Process execution telemetry: determine whether PowerShell activity was interactive or triggered by another process, and whether the launch chain is expected for the user and host.
- Network telemetry: check for connections from the alerting host to database servers and to backup-related infrastructure around the alert time, and validate whether the destinations are expected.
- Authentication telemetry: look for new or unusual logons involving the initiating user or any accounts referenced in the script content, especially to backup servers, database servers, and other high-value systems.
- Database auditing (if available): review authentication and query activity against the Veeam configuration database around the alert time for evidence of credential table access, repeated extraction attempts, or unusual query volume.
- Assess potential impact:
- Determine whether the script indicates bulk credential extraction versus targeted credential retrieval.
- Review for subsequent activity that could indicate use of obtained credentials to access or modify backup infrastructure, including actions that reduce recovery options.
### False positive analysis
- Approved Veeam administration, troubleshooting, or support workflows may reference the Veeam configuration database schema and credential storage routines; validate authorization, operator identity, and business justification.
- Maintenance activities such as upgrades, migrations, or recoveries may require credential-related queries or decryption logic; confirm timing, scope, and the designated administrators and hosts involved.
- Internal security testing may intentionally validate credential exposure paths; confirm test authorization and ensure results are handled and stored securely.
- Custom automation or reporting that interfaces with the Veeam database can trigger this alert; validate script ownership, change control approval, and that outputs do not expose secrets.
### Response and remediation
- If activity is not authorized, treat it as a credential access incident:
- Contain the affected host to prevent additional credential access and potential follow-on actions against backup infrastructure.
- Restrict or disable the initiating account (`user.name` / `user.id`) as appropriate, and review recent activity for signs of compromise.
- Preserve evidence for incident response:
- Retain the full reconstructed script content using `powershell.file.script_block_id` with `powershell.sequence` and `powershell.total`, along with `host.name`, `host.id`, `user.name`, `user.domain`, and `user.id`.
- If `file.path` is present, preserve the referenced script file and any related artifacts in the same directory for forensic review.
- Assume Veeam-stored credentials may be compromised:
- Rotate credentials that could be accessed via the Veeam configuration database or decrypted via ProtectedStorage routines, and review where they are used across backup jobs and infrastructure integrations.
- Review privileged access to backup systems and database servers for unauthorized use after the alert time.
- Reduce future exposure:
- Limit access to the Veeam configuration database to approved administrative hosts and accounts, and review permissions related to credential storage.
- Review Veeam administrative role assignments and access paths to ensure least privilege.
- Validate recovery readiness:
- Review backup job, repository, and retention configurations for unauthorized changes.
- Confirm the availability of recent backups and perform integrity checks consistent with your recovery procedures.
- Continue monitoring and hunting:
- Monitor for recurrence of the identified script patterns across hosts and users, and investigate any additional related PowerShell activity discovered during scoping.
"""
references = [
"https://forums.veeam.com/veeam-backup-replication-f2/recover-esxi-password-in-veeam-t34630.html",
"https://www.crowdstrike.com/blog/anatomy-of-alpha-spider-ransomware/",
]
risk_score = 47
rule_id = "5c602cba-ae00-4488-845d-24de2b6d8055"
setup = """## Setup
PowerShell Script Block Logging must be enabled to generate the events used by this rule (e.g., 4104).
Setup instructions: https://ela.st/powershell-logging-setup
"""
severity = "medium"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Credential Access",
"Data Source: PowerShell Logs",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
event.category:process and host.os.type:windows and
powershell.file.script_block_text : (
(
"[dbo].[Credentials]" and
("Veeam" or "VeeamBackup")
) or
"ProtectedStorage]::GetLocalString"
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1003"
name = "OS Credential Dumping"
reference = "https://attack.mitre.org/techniques/T1003/"
[[rule.threat.technique]]
id = "T1555"
name = "Credentials from Password Stores"
reference = "https://attack.mitre.org/techniques/T1555/"
[rule.threat.tactic]
id = "TA0006"
name = "Credential Access"
reference = "https://attack.mitre.org/tactics/TA0006/"
[[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.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1213"
name = "Data from Information Repositories"
reference = "https://attack.mitre.org/techniques/T1213/"
[rule.threat.tactic]
id = "TA0009"
name = "Collection"
reference = "https://attack.mitre.org/tactics/TA0009/"
[rule.investigation_fields]
field_names = [
"@timestamp",
"user.name",
"user.id",
"user.domain",
"powershell.file.script_block_text",
"powershell.file.script_block_id",
"powershell.sequence",
"powershell.total",
"file.path",
"file.directory",
"file.name",
"process.pid",
"host.name",
"host.id",
"powershell.file.script_block_length"
]
Stages and Predicates
Stage 1: query
event.category:process and host.os.type:windows and
powershell.file.script_block_text : (
(
"[dbo].[Credentials]" and
("Veeam" or "VeeamBackup")
) or
"ProtectedStorage]::GetLocalString"
)
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.category | eq |
| field:"event.category" kind:eq value:"process" |
powershell.file.script_block_text | eq |
| field:"ScriptBlockText" kind:eq |
powershell.file.script_block_text | in |
| field:"ScriptBlockText" kind:in |
Privilege Escalation via Named Pipe Impersonation
#Identifies a privilege escalation attempt via named pipe impersonation. An adversary may abuse this technique by utilizing a framework such as Metasploit's meterpreter getsystem command.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation |
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/11/23"
integration = ["endpoint", "windows", "system", "m365_defender", "sentinel_one_cloud_funnel", "crowdstrike"]
maturity = "production"
updated_date = "2026/05/03"
[rule]
author = ["Elastic"]
description = """
Identifies a privilege escalation attempt via named pipe impersonation. An adversary may abuse this technique by
utilizing a framework such as Metasploit's meterpreter getsystem command.
"""
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 = "Privilege Escalation via Named Pipe Impersonation"
references = [
"https://www.ired.team/offensive-security/privilege-escalation/windows-namedpipes-privilege-escalation",
"https://www.cobaltstrike.com/blog/what-happens-when-i-type-getsystem/",
"https://redcanary.com/blog/getsystem-offsec/",
]
risk_score = 73
rule_id = "3ecbdc9e-e4f2-43fa-8cca-63802125e582"
severity = "high"
tags = [
"Domain: Endpoint",
"OS: Windows",
"Use Case: Threat Detection",
"Tactic: Privilege Escalation",
"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 : ("Cmd.Exe", "PowerShell.EXE") or ?process.pe.original_file_name in ("Cmd.Exe", "PowerShell.EXE")) and
process.args : "echo" and process.args : ">" and process.args : "\\\\.\\pipe\\*"
'''
note = """## Triage and analysis
### Investigating Privilege Escalation via Named Pipe Impersonation
#### Possible investigation steps
- Did the alert process act as a named-pipe client for a SYSTEM-token handoff?
- Why: GetSystem-style abuse pairs a service-context client with a named-pipe server so the server can impersonate the client token; the shell pipe-write is the client-side marker.
- Focus: `process.name`, `process.pe.original_file_name`, `process.command_line`, `host.id`, and `user.id`.
- Implication: escalate when cmd or PowerShell sends a short marker into a named pipe before token impersonation; lower suspicion only when the same pipe name, marker, host, and user match a stable validation pattern.
- Does the parent and token context fit a service-driven impersonation attempt?
- Focus: `process.parent.name`, `process.parent.command_line`, broader process lineage when needed, `process.Ext.token.integrity_level_name`, and `process.Ext.token.elevation_level`. $investigate_0
- Implication: escalate when services.exe, service-creation command lines, or an unexplained launcher starts the pipe write under high or SYSTEM context; absent or ambiguous token context cannot close the alert without matching identity and follow-on evidence.
- Is the launching binary the expected Windows shell or a masqueraded copy?
- Focus: `process.executable`, `process.hash.sha256`, `process.pe.original_file_name`, `process.code_signature.subject_name`, and `process.code_signature.trusted`.
- Implication: escalate when the shell runs from a user-writable or deceptive path, has an untrusted signer, or mismatches its original file name; signed System32 cmd or PowerShell confirms identity only and does not clear the pipe-write behavior.
- Did the pipe writer launch or enable follow-on SYSTEM activity?
- Focus: child process events from `process.entity_id`; review `process.name`, `process.command_line`, and `process.Ext.token.integrity_level_name`. $investigate_1
- Implication: escalate when a shell, tool, service helper, or credential-access process follows under high or SYSTEM integrity; absence of child process evidence lowers only follow-on confidence when pipe syntax or service parentage remains suspicious.
- Hint: if `process.entity_id` is unavailable, use `host.id` plus `process.pid` in a tight alert-time window and treat matches as weaker.
- Is this isolated, or part of repeated named-pipe impersonation behavior?
- Focus: process starts sharing `host.id` or `user.id`, marker behavior in `process.command_line`, and either `process.parent.name` or `process.hash.sha256`.
- $investigate_2
- $investigate_3
- Implication: escalate scope when repeats cross hosts, users, hashes, or parent chains; keep response local only when all repeats stay inside the same process-evidenced validation pattern.
- Range: start with the alert window; expand only if local evidence is suspicious or unresolved.
- Escalate on suspicious pipe-write syntax, parent/token context, binary identity, follow-on process activity, or host/user scope; close only when all evidence matches a stable validation pattern with no contradictions; preserve artifacts and escalate when evidence is mixed or incomplete.
### False positive analysis
- Routine administration should not require shell echo redirection into a named pipe for privilege escalation. Controlled security validation is the narrow benign path; process evidence must prove the exact pattern:
- **Identity**: `process.executable`, `process.hash.sha256`, signer, and `process.parent.command_line` match the validation toolchain.
- **Pipe syntax**: `process.command_line` shows the expected pipe name, echo value, and wrapper syntax for that test.
- **Scope**: `host.id` and `user.id` stay inside the known test target and operator scope.
- **Follow-on**: child process starts do not show unexpected high or SYSTEM activity outside the test plan.
- If telemetry cannot prove the test scope or toolchain, outside confirmation can corroborate the case but cannot override contradictory process evidence; otherwise preserve and escalate.
- Build exceptions only from the minimum confirmed validation pattern: stable `process.hash.sha256`, `process.executable`, `process.parent.command_line`, constrained `host.id` or `user.id`, and the specific pipe-write shape in `process.command_line`. Avoid exceptions on `process.name`, cmd or PowerShell alone, or a pipe name alone.
### Response and remediation
- If confirmed benign:
- Reverse any temporary containment and document the evidence that confirmed the validation workflow: pipe syntax, parent/token context, binary identity, `host.id`, `user.id`, and lack of unexpected follow-on SYSTEM activity.
- If suspicious but unconfirmed:
- Preserve the alert, process tree, command lines, parent and child process records, `process.entity_id`, `process.pid`, hashes, and the named-pipe string before termination, cleanup, or credential actions.
- Apply reversible containment tied to the findings, such as isolating the endpoint after weighing host criticality or restricting the affected account/session while investigation continues.
- Do not terminate cmd, PowerShell, or child processes until the process identifiers, command lines, and any volatile state needed by responders are captured.
- If confirmed malicious:
- Isolate the endpoint after preservation when parent/token, identity, or follow-on process evidence confirms unauthorized SYSTEM activity.
- Suspend or terminate the pipe writer and follow-on processes only after recording their entity IDs, PIDs, command lines, hashes, and parent relationships.
- Reset credentials or revoke sessions for affected users only when process/session evidence indicates account misuse or credential exposure.
- Eradicate only malicious tools, service definitions, binaries, scripts, and configuration changes confirmed during the investigation, then remediate the entry vector that allowed the named-pipe impersonation attempt.
- Post-incident hardening:
- Restrict local admin and service-creation rights that allow untrusted tooling to create SYSTEM service clients.
- Retain command-line, parent/child process, and token-integrity telemetry because those fields distinguish testing from GetSystem abuse.
- Document the confirmed benign validation pattern or malicious artifact set so future analysts can separate repeat testing from repeat abuse.
"""
setup = """## Setup
This rule is designed for data generated by [Elastic Defend](https://www.elastic.co/security/endpoint-security), which provides native endpoint detection and response, along with event enrichments designed to work with our detection rules.
Setup instructions: https://ela.st/install-elastic-defend
### Additional data sources
This rule also supports the following third-party data sources. For setup instructions, refer to the links below:
- [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.id",
"user.id",
"process.entity_id",
"process.pid",
"process.executable",
"process.command_line",
"process.args",
"process.pe.original_file_name",
"process.code_signature.subject_name",
"process.code_signature.trusted",
"process.hash.sha256",
"process.Ext.token.integrity_level_name",
"process.parent.executable",
"process.parent.command_line",
]
[transform]
[[transform.investigate]]
label = "Process starts on the host near the pipe write"
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" }
]
]
relativeFrom = "now-1h"
relativeTo = "now"
[[transform.investigate]]
label = "Child process starts from the pipe writer"
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" }
],
[
{ 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.pid", queryType = "phrase", value = "{{process.pid}}", valueType = "string" }
]
]
relativeFrom = "now-1h"
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 = "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"
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1134"
name = "Access Token Manipulation"
reference = "https://attack.mitre.org/techniques/T1134/"
[[rule.threat.technique.subtechnique]]
id = "T1134.001"
name = "Token Impersonation/Theft"
reference = "https://attack.mitre.org/techniques/T1134/001/"
[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 == "windows" and event.type == "start" and
(process.name : ("Cmd.Exe", "PowerShell.EXE") or ?process.pe.original_file_name in ("Cmd.Exe", "PowerShell.EXE")) and
process.args : "echo" and process.args : ">" and process.args : "\\\\.\\pipe\\*"
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 |
process.pe.original_file_name | in |
| field:"OriginalFileName" kind:in |
Process Termination Following Ptrace Manipulation
#This rule detects a process terminating shortly after its memory and register state were modified through ptrace. Immediate termination following ptrace manipulation can indicate an unsuccessful process-injection attempt, invalid shellcode, or execution-flow corruption.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
This rule detects a process terminating shortly after its memory and register state were modified through ptrace.
Immediate termination following ptrace manipulation can indicate an unsuccessful process-injection attempt, invalid
shellcode, or execution-flow corruption.
"""
id = "ee3e4e2b-6f2a-473f-b51c-60c7e29664ef"
license = "Elastic License v2"
name = "Process Termination Following Ptrace Manipulation"
os_list = ["linux"]
reference = [
"https://man7.org/linux/man-pages/man2/ptrace.2.html",
"https://www.akamai.com/blog/security-research/the-definitive-guide-to-linux-process-injection",
]
version = "1.0.3"
query = '''
sequence with maxspan=1s
[process where event.type == "start" and event.action == "ptrace" and
process.Ext.ptrace.request in (4, 5) and
process.Ext.ptrace.addr >= 4096 and process.executable != null and
not process.executable in (
"/opt/dynatrace/oneagent/agent/lib64/oneagenthelper", "/usr/libexec/gdb"
)] by process.Ext.ptrace.child_pid
[process where event.type == "start" and event.action == "ptrace" and
process.Ext.ptrace.request in (6, 13, 16901)] by process.Ext.ptrace.child_pid
[process where event.type == "end" and event.action == "end"] by process.pid
'''
min_endpoint_version = "9.1.4"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 1
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 0
[[actions]]
action = "kill_process"
field = "process.parent.entity_id"
state = 1
[[threat]]
framework = "MITRE ATT&CK"
[[threat.technique]]
id = "T1055"
name = "Process Injection"
reference = "https://attack.mitre.org/techniques/T1055/"
[[threat.technique.subtechnique]]
id = "T1055.008"
name = "Ptrace System Calls"
reference = "https://attack.mitre.org/techniques/T1055/008/"
[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 1s, correlated by process.Ext.ptrace.child_pid, process.pid.
Stage 1: process
[process where event.type == "start" and event.action == "ptrace" and
process.Ext.ptrace.request in (4, 5) and
process.Ext.ptrace.addr >= 4096 and process.executable != null and
not process.executable in (
"/opt/dynatrace/oneagent/agent/lib64/oneagenthelper", "/usr/libexec/gdb"
)] by process.Ext.ptrace.child_pid
Stage 2: process
[process where event.type == "start" and event.action == "ptrace" and
process.Ext.ptrace.request in (6, 13, 16901)] by process.Ext.ptrace.child_pid
Stage 3: process
[process where event.type == "end" and event.action == "end"] by process.pid
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 |
process.Ext.ptrace.addr | ge |
| field:"process.Ext.ptrace.addr" kind:ge value:"4096" |
process.Ext.ptrace.request | in |
| field:"process.Ext.ptrace.request" kind:in |
process.executable | is_not_null | field:"Image" kind:is_not_null |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.executable | in | /opt/dynatrace/oneagent/agent/lib64/oneagenthelper, /usr/libexec/gdb | excludes:process.executable field:"process.executable" value:"/opt/dynatrace/oneagent/agent/lib64/oneagenthelper" field:"process.executable" value:"/usr/libexec/gdb" |
Remote Process Injection via Python
#Identifies attempt to perform remote process code injection from a python program.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = "Identifies attempt to perform remote process code injection from a python program."
id = "634dcd98-0656-48a8-bd41-5fa025b6c812"
license = "Elastic License v2"
name = "Remote Process Injection via Python"
os_list = ["windows"]
version = "1.0.8"
query = '''
api where process.Ext.api.behaviors == "cross-process" and process.Ext.api.metadata.target_address_name like "?*" and
process.thread.Ext.call_stack_final_user_module.name : ("libffi*.dll", "python*.dll") and
not process.Ext.api.metadata.target_address_name in ("PEB", "PEB32", "ProcessStartupInfo") and
not process.Ext.api.summary like ("* PEB*", "* PEB32*", "*ProcessStartupInfo*", "*Data*", "*python??.dll*", "NtQueueApcThread( cmd.exe, Unbacked, NULL, NULL, NULL )") and
not process.executable : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*.exe") and
not (process.Ext.api.name == "WriteProcessMemory" and process.Ext.api.parameters.size == 4) and
not process.thread.Ext.call_stack_final_user_module.path like
("c:\\program files\\*.dll",
"c:\\program files (x86)\\*.dll",
"c:\\programdata\\anaconda3\\python??.dll",
"c:\\windows\\systemtemp\\chrome_unpacker_*\\python*.dll")
'''
min_endpoint_version = "8.10.0"
[[actions]]
action = "kill_process"
field = "Target.process.entity_id"
state = 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 = "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.behaviors == "cross-process" and process.Ext.api.metadata.target_address_name like "?*" and
process.thread.Ext.call_stack_final_user_module.name : ("libffi*.dll", "python*.dll") and
not process.Ext.api.metadata.target_address_name in ("PEB", "PEB32", "ProcessStartupInfo") and
not process.Ext.api.summary like ("* PEB*", "* PEB32*", "*ProcessStartupInfo*", "*Data*", "*python??.dll*", "NtQueueApcThread( cmd.exe, Unbacked, NULL, NULL, NULL )") and
not process.executable : ("?:\\Program Files\\*", "?:\\Program Files (x86)\\*.exe") and
not (process.Ext.api.name == "WriteProcessMemory" and process.Ext.api.parameters.size == 4) and
not process.thread.Ext.call_stack_final_user_module.path like
("c:\\program files\\*.dll",
"c:\\program files (x86)\\*.dll",
"c:\\programdata\\anaconda3\\python??.dll",
"c:\\windows\\systemtemp\\chrome_unpacker_*\\python*.dll")
Indicators
These rows show field, operator, and value matches.
Exclusions
The rule actively suppresses these predicates.
Suspicious Binary Execution via SSH
#Detects SSH sessions executing suspicious binaries followed by outbound network connections. This pattern indicates potential post-exploitation activity via compromised SSH access.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution |
Telemetry Coverage
Rule Body
[rule]
description = """
Detects SSH sessions executing suspicious binaries followed by outbound network connections. This pattern indicates
potential post-exploitation activity via compromised SSH access.
"""
id = "050a7053-a119-43fc-ad14-9a0c4944a9b8"
license = "Elastic License v2"
name = "Suspicious Binary Execution via SSH"
os_list = ["macos"]
version = "1.0.9"
query = '''
sequence by process.entity_id with maxspan=15s
[process where event.type == "start" and event.action == "exec" and process.parent.name in ("ssh", "sshd", "sshd-session") and
(process.name like~ ("osascript", "curl", "nscurl", "wget", "perl", "node") or (process.code_signature.exists == false or
process.code_signature.trusted == false)) and
not process.executable like~ ("/opt/homebrew/Cellar/*", "/usr/local/Cellar/*", "/Users/*/homebrew/Cellar/*", "/usr/local/libexec/ssh-sk-helper") and
not process.Ext.effective_parent.executable in ("/Applications/Codex.app/Contents/MacOS/Codex", "/Applications/Cursor.app/Contents/MacOS/Cursor") and
process.hash.sha256 not in ("cc2b7231c9f1696e24c0c05cbc93ec88172ba6fa102b0fbbdc8ed95ee564b4d6",
"aefccb7d3427093e6e4681c335066606d40191e12d734cc73ad457e223b0c948")
]
[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
[[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.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.parent.name in ("ssh", "sshd", "sshd-session") and
(process.name like~ ("osascript", "curl", "nscurl", "wget", "perl", "node") or (process.code_signature.exists == false or
process.code_signature.trusted == false)) and
not process.executable like~ ("/opt/homebrew/Cellar/*", "/usr/local/Cellar/*", "/Users/*/homebrew/Cellar/*", "/usr/local/libexec/ssh-sk-helper") and
not process.Ext.effective_parent.executable in ("/Applications/Codex.app/Contents/MacOS/Codex", "/Applications/Cursor.app/Contents/MacOS/Cursor") and
process.hash.sha256 not in ("cc2b7231c9f1696e24c0c05cbc93ec88172ba6fa102b0fbbdc8ed95ee564b4d6",
"aefccb7d3427093e6e4681c335066606d40191e12d734cc73ad457e223b0c948")
]
Stage 2: 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 value:"exec" |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.code_signature.exists | eq |
| field:"process.code_signature.exists" kind:eq value:"false" |
process.code_signature.trusted | eq |
| field:"process.code_signature.trusted" kind:eq value:"false" |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
process.parent.name | in |
| field:"parent_process_basename" kind:in |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.Ext.effective_parent.executable | in | /Applications/Codex.app/Contents/MacOS/Codex, /Applications/Cursor.app/Contents/MacOS/Cursor | excludes:process.Ext.effective_parent.executable field:"process.Ext.effective_parent.executable" value:"/Applications/Codex.app/Contents/MacOS/Codex" field:"process.Ext.effective_parent.executable" value:"/Applications/Cursor.app/Contents/MacOS/Cursor" |
process.executable | wildcard | /opt/homebrew/Cellar/*, /usr/local/Cellar/*, /Users/*/homebrew/Cellar/*, /usr/local/libexec/ssh-sk-helper | excludes:process.executable |
process.hash.sha256 | in | aefccb7d3427093e6e4681c335066606d40191e12d734cc73ad457e223b0c948, cc2b7231c9f1696e24c0c05cbc93ec88172ba6fa102b0fbbdc8ed95ee564b4d6 | excludes:process.hash.sha256 field:"process.hash.sha256" value:"aefccb7d3427093e6e4681c335066606d40191e12d734cc73ad457e223b0c948" field:"process.hash.sha256" value:"cc2b7231c9f1696e24c0c05cbc93ec88172ba6fa102b0fbbdc8ed95ee564b4d6" |
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 Process Creation via Reflection
#Identifies the creation of process clone via the Windows API RtlCreateProcessReflection. This may indicate an attempt to create a process as a target for process injection.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Stealth |
Rule Body
[rule]
description = """
Identifies the creation of process clone via the Windows API RtlCreateProcessReflection. This may indicate an attempt to
create a process as a target for process injection.
"""
id = "8d222b62-4ca5-41aa-85e1-4e6c0a21f2aa"
license = "Elastic License v2"
name = "Suspicious Process Creation via Reflection"
os_list = ["windows"]
reference = ["https://www.deepinstinct.com/blog/dirty-vanity-a-new-approach-to-code-injection-edr-bypass"]
version = "1.0.10"
query = '''
process where event.action == "start" and process.parent.executable != null and
descendant of [process where event.action == "start" and
_arraysearch(process.parent.thread.Ext.call_stack, $entry, $entry.symbol_info: ("*ntdll.dll!RtlCreateProcessReflection*", "*ntdll.dll!RtlCloneUserProcess*"))] and
not (process.executable : ("?:\\WINDOWS\\SysWOW64\\WerFault.exe", "?:\\WINDOWS\\system32\\WerFault.exe") and
process.parent.thread.Ext.call_stack_summary : "*faultrep.dll|wersvc.dl*") and
not (process.executable : "?:\\WINDOWS\\system32\\conhost.exe" and
_arraysearch(process.parent.thread.Ext.call_stack, $entry, $entry.symbol_info: "*ntdll.dll!*DeviceIoControlFile*")) and
not (process.code_signature.trusted == true and
process.code_signature.subject_name : ("Tencent Technology(Shenzhen) Company Limited", "Logitech Inc")) and
not (process.parent.executable : ("?:\\WINDOWS\\SysWOW64\\WerFault.exe", "?:\\WINDOWS\\system32\\WerFault.exe") and
process.parent.thread.Ext.call_stack_summary : "*faultrep.dll*") and
not (process.executable : "C:\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe" and process.parent.executable : "C:\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe") and
not (process.executable : "\\Device\\HarddiskVolume?\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe" and
process.parent.executable : "\\Device\\HarddiskVolume?\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe")
'''
min_endpoint_version = "8.7.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.7.0"
Stages and Predicates
Stage 1: process
process where event.action == "start" and process.parent.executable != null and
descendant of [process where event.action == "start" and
_arraysearch(process.parent.thread.Ext.call_stack, $entry, $entry.symbol_info: ("*ntdll.dll!RtlCreateProcessReflection*", "*ntdll.dll!RtlCloneUserProcess*"))] and
not (process.executable : ("?:\\WINDOWS\\SysWOW64\\WerFault.exe", "?:\\WINDOWS\\system32\\WerFault.exe") and
process.parent.thread.Ext.call_stack_summary : "*faultrep.dll|wersvc.dl*") and
not (process.executable : "?:\\WINDOWS\\system32\\conhost.exe" and
_arraysearch(process.parent.thread.Ext.call_stack, $entry, $entry.symbol_info: "*ntdll.dll!*DeviceIoControlFile*")) and
not (process.code_signature.trusted == true and
process.code_signature.subject_name : ("Tencent Technology(Shenzhen) Company Limited", "Logitech Inc")) and
not (process.parent.executable : ("?:\\WINDOWS\\SysWOW64\\WerFault.exe", "?:\\WINDOWS\\system32\\WerFault.exe") and
process.parent.thread.Ext.call_stack_summary : "*faultrep.dll*") and
not (process.executable : "C:\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe" and process.parent.executable : "C:\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe") and
not (process.executable : "\\Device\\HarddiskVolume?\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe" and
process.parent.executable : "\\Device\\HarddiskVolume?\\Program Files\\TxGameAssistant\\ui\\aow_exe.exe")
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | eq |
| field:"EventType" kind:eq value:"start" |
process.parent.executable | is_not_null | field:"ParentImage" kind:is_not_null |
Exclusions
The rule actively suppresses these predicates.
Suspicious Python One-Liner with Encoded Payload Execution
#Identifies Python interpreters started with -c (inline code) where the command line suggests decoding obfuscated content (e.g. base64, binascii, codecs) and then executing it via exec, eval, compile, or dynamic import. Also identifies child processes spawned by a parent Python process whose command line matches the same suspicious python -c decode-and-exec pattern, when parent telemetry is present.
MITRE ATT&CK Coverage
| Tactic | Techniques |
|---|---|
| Execution | |
| Stealth |
Telemetry Coverage
Rule Body
[rule]
description = """
Identifies Python interpreters started with -c (inline code) where the command line suggests decoding obfuscated content
(e.g. base64, binascii, codecs) and then executing it via exec, eval, compile, or dynamic import. Also identifies child
processes spawned by a parent Python process whose command line matches the same suspicious python -c decode-and-exec
pattern, when parent telemetry is present.
"""
id = "a4c9e1b2-8d3f-4a5e-9c7b-2f6e8d0a1b3c"
license = "Elastic License v2"
name = "Suspicious Python One-Liner with Encoded Payload Execution"
os_list = ["macos", "windows"]
reference = ["https://attack.mitre.org/techniques/T1059/006/", "https://attack.mitre.org/techniques/T1027/"]
version = "1.0.3"
query = '''
process where event.type == "start" and event.action in ("start", "exec") and
(
/* Inline malicious python -c one-liner on this process */
(
process.name : ("python*", "py.exe", "py", "pypy*") and
process.args : "-c" and
process.command_line : (
"*b64decode*",
"*b32decode*",
"*b85decode*",
"*a85decode*",
"*.read().decode(*",
"*binascii*",
"*codecs.decode*",
"*fromhex*",
"*zlib.decompress*",
"*marshal.loads*"
) and
process.command_line : (
"*exec(*",
"*eval(*",
"*__import__*",
"*compile(*",
"*types.FunctionType*",
"*runpy*",
"*importlib.util*",
"*importlib.import_module*"
)
)
or
/* Child of a parent Python process running the same suspicious -c pattern (parent fields populated) */
(
process.parent.name : ("python*", "py.exe", "py", "pypy*") and
process.parent.command_line != null and
process.parent.args : "-c" and
process.parent.command_line : (
"*b64decode*",
"*b32decode*",
"*b85decode*",
"*a85decode*",
"*.read().decode(*",
"*binascii*",
"*codecs.decode*",
"*fromhex*",
"*zlib.decompress*",
"*marshal.loads*"
) and
process.parent.command_line : (
"*exec(*",
"*eval(*",
"*__import__*",
"*compile(*",
"*types.FunctionType*",
"*runpy*",
"*importlib.util*",
"*importlib.import_module*"
)
and not process.executable : "?:\\Windows\\System32\\conhost.exe"
)
) and
not process.parent.executable like~ (
"*/opencode-ai/*/opencode*",
"*/opencode-darwin-arm64/bin/opencode",
"*/opencode-linux-*/bin/opencode"
) and
not process.parent.executable like~ "/Applications/Alfred*.app/*" and
not (process.command_line : (
"*runpy.run_module(\"pip\"*",
"*runpy.run_module('pip'*",
"*ensurepip*"
) and
process.executable like~ (
"*/Python.framework/Versions/*/bin/python*",
"*/Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"*/Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"/opt/homebrew/Cellar/python*/*/bin/python*",
"/usr/local/Cellar/python*/*/bin/python*",
"/usr/bin/python*"
)) and
not (process.parent.command_line : (
"*runpy.run_module(\"pip\"*",
"*runpy.run_module('pip'*",
"*ensurepip*"
) and
process.parent.executable like~ (
"*/Python.framework/Versions/*/bin/python*",
"*/Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"*/Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"/opt/homebrew/Cellar/python*/*/bin/python*",
"/usr/local/Cellar/python*/*/bin/python*",
"/usr/bin/python*"
)) and
not process.Ext.effective_parent.executable like~ (
"/Applications/Cursor.app/*",
"/Users/*/Applications/Cursor.app/*",
"/Applications/Codex.app/*",
"/Users/*/Applications/Codex.app/*",
"/Users/*/Library/Application Support/Claude/claude-code/*/claude.app/*",
"/Applications/Visual Studio Code.app/Contents/MacOS/Code"
) and
not process.parent.command_line like "*/Users/*/shell-snapshots/snapshot-*" and
not process.hash.sha256 == "7c72112b685250b1aec69081696d8fc04040ccefc34505ca56ac48ace7da8d5b"
'''
min_endpoint_version = "8.5.0"
optional_actions = []
[[actions]]
action = "kill_process"
field = "process.entity_id"
state = 0
tree = true
[[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 = "T1027"
name = "Obfuscated Files or Information"
reference = "https://attack.mitre.org/techniques/T1027/"
[threat.tactic]
id = "TA0005"
name = "Defense Evasion"
reference = "https://attack.mitre.org/tactics/TA0005/"
[internal]
min_endpoint_version = "8.5.0"
Stages and Predicates
Stage 1: process
process where event.type == "start" and event.action in ("start", "exec") and
(
(
process.name : ("python*", "py.exe", "py", "pypy*") and
process.args : "-c" and
process.command_line : (
"*b64decode*",
"*b32decode*",
"*b85decode*",
"*a85decode*",
"*.read().decode(*",
"*binascii*",
"*codecs.decode*",
"*fromhex*",
"*zlib.decompress*",
"*marshal.loads*"
) and
process.command_line : (
"*exec(*",
"*eval(*",
"*__import__*",
"*compile(*",
"*types.FunctionType*",
"*runpy*",
"*importlib.util*",
"*importlib.import_module*"
)
)
or
(
process.parent.name : ("python*", "py.exe", "py", "pypy*") and
process.parent.command_line != null and
process.parent.args : "-c" and
process.parent.command_line : (
"*b64decode*",
"*b32decode*",
"*b85decode*",
"*a85decode*",
"*.read().decode(*",
"*binascii*",
"*codecs.decode*",
"*fromhex*",
"*zlib.decompress*",
"*marshal.loads*"
) and
process.parent.command_line : (
"*exec(*",
"*eval(*",
"*__import__*",
"*compile(*",
"*types.FunctionType*",
"*runpy*",
"*importlib.util*",
"*importlib.import_module*"
)
and not process.executable : "?:\\Windows\\System32\\conhost.exe"
)
) and
not process.parent.executable like~ (
"*/opencode-ai/*/opencode*",
"*/opencode-darwin-arm64/bin/opencode",
"*/opencode-linux-*/bin/opencode"
) and
not process.parent.executable like~ "/Applications/Alfred*.app/*" and
not (process.command_line : (
"*runpy.run_module(\"pip\"*",
"*runpy.run_module('pip'*",
"*ensurepip*"
) and
process.executable like~ (
"*/Python.framework/Versions/*/bin/python*",
"*/Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"*/Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"/opt/homebrew/Cellar/python*/*/bin/python*",
"/usr/local/Cellar/python*/*/bin/python*",
"/usr/bin/python*"
)) and
not (process.parent.command_line : (
"*runpy.run_module(\"pip\"*",
"*runpy.run_module('pip'*",
"*ensurepip*"
) and
process.parent.executable like~ (
"*/Python.framework/Versions/*/bin/python*",
"*/Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"*/Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python",
"/opt/homebrew/Cellar/python*/*/bin/python*",
"/usr/local/Cellar/python*/*/bin/python*",
"/usr/bin/python*"
)) and
not process.Ext.effective_parent.executable like~ (
"/Applications/Cursor.app/*",
"/Users/*/Applications/Cursor.app/*",
"/Applications/Codex.app/*",
"/Users/*/Applications/Codex.app/*",
"/Users/*/Library/Application Support/Claude/claude-code/*/claude.app/*",
"/Applications/Visual Studio Code.app/Contents/MacOS/Code"
) and
not process.parent.command_line like "*/Users/*/shell-snapshots/snapshot-*" and
not process.hash.sha256 == "7c72112b685250b1aec69081696d8fc04040ccefc34505ca56ac48ace7da8d5b"
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
event.action | in |
| field:"EventType" kind:in |
event.type | eq |
| field:"event.type" kind:eq value:"start" |
process.args | wildcard |
| field:"process.args" kind:wildcard value:"-c" |
process.command_line | wildcard |
| field:"CommandLine" kind:wildcard |
process.name | wildcard |
| field:"process_basename" kind:wildcard |
process.parent.args | wildcard |
| field:"process.parent.args" kind:wildcard value:"-c" |
process.parent.command_line | is_not_null | field:"ParentCommandLine" kind:is_not_null | |
process.parent.command_line | wildcard |
| field:"ParentCommandLine" kind:wildcard |
process.parent.name | wildcard |
| field:"parent_process_basename" kind:wildcard |
Exclusions
The rule actively suppresses these predicates.
| Field | Kind | Excluded values | Search |
|---|---|---|---|
process.command_line | match | runpy.run_module("pip", runpy.run_module('pip', ensurepip | excludes:process.command_line |
process.executable | wildcard | */Python.framework/Versions/*/bin/python*, */Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python, */Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python, /opt/homebrew/Cellar/python*/*/bin/python*, /usr/local/Cellar/python*/*/bin/python*, /usr/bin/python* | excludes:process.executable |
process.parent.command_line | match | runpy.run_module("pip", runpy.run_module('pip', ensurepip | excludes:process.parent.command_line |
process.parent.executable | wildcard | */Python.framework/Versions/*/bin/python*, */Python.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python, */Python3.framework/Versions/*/Resources/Python.app/Contents/MacOS/Python, /opt/homebrew/Cellar/python*/*/bin/python*, /usr/local/Cellar/python*/*/bin/python*, /usr/bin/python* | excludes:process.parent.executable |
process.Ext.effective_parent.executable | wildcard | /Applications/Cursor.app/*, /Users/*/Applications/Cursor.app/*, /Applications/Codex.app/*, /Users/*/Applications/Codex.app/*, /Users/*/Library/Application Support/Claude/claude-code/*/claude.app/*, /Applications/Visual Studio Code.app/Contents/MacOS/Code | excludes:process.Ext.effective_parent.executable |
process.hash.sha256 | eq | 7c72112b685250b1aec69081696d8fc04040ccefc34505ca56ac48ace7da8d5b | excludes:process.hash.sha256 field:"process.hash.sha256" value:"7c72112b685250b1aec69081696d8fc04040ccefc34505ca56ac48ace7da8d5b" |
process.parent.command_line | wildcard | */Users/*/shell-snapshots/snapshot-* | excludes:process.parent.command_line field:"process.parent.command_line" value:"*/Users/*/shell-snapshots/snapshot-*" |
process.parent.executable | wildcard | */opencode-ai/*/opencode*, */opencode-darwin-arm64/bin/opencode, */opencode-linux-*/bin/opencode | excludes:process.parent.executable field:"process.parent.executable" value:"*/opencode-ai/*/opencode*" field:"process.parent.executable" value:"*/opencode-darwin-arm64/bin/opencode" field:"process.parent.executable" value:"*/opencode-linux-*/bin/opencode" |
process.parent.executable | wildcard | /Applications/Alfred*.app/* | excludes:process.parent.executable field:"process.parent.executable" value:"/Applications/Alfred*.app/*" |