Query Details

All Encoded Powershell Commands

Power Shell Encoded Commands Executed

Query

let EncodedList = dynamic(['-encodedcommand', '-enc']); 
// For more results use line below en filter one above. This will also return more FPs.
// let EncodedList = dynamic(['-encodedcommand', '-enc', '-e']);
let TimeFrame = 48h; //Customizable h = hours, d = days
DeviceProcessEvents
| where Timestamp > ago(TimeFrame)
| where ProcessCommandLine contains "powershell" or InitiatingProcessCommandLine contains "powershell"
| where ProcessCommandLine has_any (EncodedList) or InitiatingProcessCommandLine has_any (EncodedList)
| extend base64String = extract(@'\s+([A-Za-z0-9+/]{20}\S+$)', 1, ProcessCommandLine)
| extend DecodedCommandLine = base64_decode_tostring(base64String)
| extend DecodedCommandLineReplaceEmptyPlaces = replace_string(DecodedCommandLine, '\u0000', '')
| where isnotempty(base64String) and isnotempty(DecodedCommandLineReplaceEmptyPlaces)
| summarize UniqueExecutionsList = make_set(DecodedCommandLineReplaceEmptyPlaces) by DeviceName
| extend TotalUniqueEncodedCommandsExecuted = array_length(UniqueExecutionsList)
| project DeviceName, TotalUniqueEncodedCommandsExecuted, UniqueExecutionsList
| sort by TotalUniqueEncodedCommandsExecuted

About this query

Explanation

This query is designed to identify and analyze encoded PowerShell commands executed on devices within a specified timeframe (48 hours by default). Here's a simplified breakdown of what the query does:

  1. Define Encoded Commands: It sets up a list of indicators (-encodedcommand, -enc) that are commonly used in PowerShell to denote that a command is encoded.

  2. Set Timeframe: The query looks at events from the past 48 hours, but this can be adjusted as needed.

  3. Filter Events: It filters the device process events to find those where the command line or initiating process command line contains "powershell" and includes any of the encoded command indicators.

  4. Extract and Decode: For each matching event, it extracts a base64-encoded string from the command line, decodes it, and removes any null characters.

  5. Filter Non-Empty Results: It ensures that only events with a non-empty base64 string and decoded command line are considered.

  6. Summarize Results: For each device, it compiles a list of unique decoded commands executed and counts how many unique encoded commands were executed.

  7. Output: The final output is a list of devices, the total number of unique encoded commands executed on each device, and the list of those unique commands, sorted by the total number of unique commands executed.

This query helps in identifying potentially suspicious or obfuscated PowerShell activity, which is a common technique used by attackers to hide malicious actions.

Details

Bert-Jan Pals profile picture

Bert-Jan Pals

Released: December 1, 2024

Tables

DeviceProcessEvents

Keywords

Device

Operators

letdynamicagocontainshas_anyextractbase64_decode_tostringreplace_stringisnotemptysummarizemake_setbyextendarray_lengthprojectsort

MITRE Techniques

Actions

GitHub