Kusto Query Language (KQL) queries for Advanced Hunting (Microsoft Defender for Endpoint)
Here is the KQL query list to check the Defender client details with specific areas.
Virus Definition status
Product AV Version Details
Firewall
DeviceNetworkEvents
| where ActionType == “ConnectionBlocked”
| project Timestamp, DeviceName, LocalIP, RemoteIP, RemotePort, Protocol, InitiatingProcessFileName
| sort by Timestamp desc
DeviceNetworkEvents
| where ActionType == “InboundConnectionBlocked”
| summarize BlockCount = count() by RemoteIP, DeviceName, bin(Timestamp, 1h)
| sort by BlockCount desc
DeviceNetworkEvents
| where ActionType == “ConnectionBlocked”
| where InitiatingProcessFileName !in~ (“chrome.exe”,”msedge.exe”,”firefox.exe”)
| project Timestamp, DeviceName, RemoteIP, RemotePort, InitiatingProcessFileName
DeviceEvents
| where Timestamp > (30d)
| where ActionType in (“FirewallOutBoundConnectionBlocked”, “FirewallInBoundConnectionBlocked”,”FirewallOutBoundConnectionToAppBlocked”)
| project DeviceName, Timestamp, InitiatingProcessFileName, InitiatingProcessParentFileName, RemoteIP, RemotePort, LocalIP, LocalPort,ActionType
//| where DeviceName contains “”
DeviceNetworkEvents
| where Timestamp > (7d)
| project Timestamp, DeviceName, ActionType, RemoteIP, RemotePort, RemoteUrl, LocalIP, LocalPort,Protocol, LocalIPType, InitiatingProcessFileName
//| where ActionType == “ConnectionFailed”
| where RemotePort == “3389”
| where DeviceName contains “desktop-3jtb9c6”
| order by Timestamp
DeviceEvents
| where ActionType in (“FirewallRuleAdded”, “FirewallRuleModified”, “FirewallRuleDeleted”)
| project Timestamp, DeviceName, ActionType, InitiatingProcessAccountName
| sort by Timestamp desc
KQL for ASR and EDR
DeviceEvents
| where ActionType startswith 'ASR'
| project DeviceName, ActionType
| evaluate pivot(ActionType)
DeviceEvents
| where ingestion_time() > ago(30d)
| where ActionType in ('AsrRansomwareBlocked', 'AsrRansomwareAudited')
| summarize arg_max(Timestamp, *), TotalEvents = count(), TriggeredFiles = make_set(FileName), FileHashes = make_set(SHA1), IntiatingProcesses = make_set(InitiatingProcessCommandLine) by DeviceName, AccountName
| project Timestamp, DeviceName, AccountDomain, AccountName, TotalEvents, TriggeredFiles, FileHashes, IntiatingProcesses
KQL Query for USB Device Control Policy
DeviceEvents | where ActionType == "PnpDeviceConnected" | extend PNPInfo = parse_json(AdditionalFields) | extend ClassName = tostring(PNPInfo.ClassName), DeviceDescription = tostring(PNPInfo.DeviceDescription), VendorIds = tostring(PNPInfo.VendorIds), DeviceId = tostring(PNPInfo.DeviceId) | extend PnPType = tostring(split(DeviceId, @"\", 0)[0]) | where PnPType == "USB" | project-reorder ClassName, PnPType, DeviceDescription, VendorIds, DeviceId | summarize TotalEvents = count() by DeviceDescription | sort by TotalEvents
General KQL Query
let ProcessBased = DeviceProcessEvents | where ProcessCommandLine has "Get-MpPreference" | extend Table = "DeviceProcessEvents" | project-reorder Table, Timestamp, DeviceName, ProcessCommandLine, InitiatingProcessFileName; let EventBased = DeviceEvents | extend Command = parse_json(AdditionalFields).Command | where Command == "Get-MpPreference" | extend ScriptLocation = extract(@"literalPath '(.*?)'", 0, InitiatingProcessCommandLine) | extend Table = "DeviceEvents" | project-reorder Table, Timestamp, DeviceName, InitiatingProcessCommandLine, InitiatingProcessParentFileName, ScriptLocation; union ProcessBased, EventBased
let ExclusionOptions = dynamic(['ExclusionPath', 'ExclusionExtension', 'ExclusionProcess', 'ExclusionIpAddress']); let Modules = dynamic(['Add-MpPreference','Set-MpPreference']); let CommandLineExecutions = DeviceProcessEvents | where ProcessCommandLine has_any (Modules) and ProcessCommandLine has_any (ExclusionOptions); let PowerShellExecutions = DeviceEvents | where ActionType == 'PowerShellCommand' | where AdditionalFields has_any (Modules) and AdditionalFields has_any (ExclusionOptions); union PowerShellExecutions, CommandLineExecutions
DeviceEvents | where Timestamp > ago(30d) | where ActionType startswith "SmartScreen" | extend SmartScreenTrigger = iff(ActionType == "SmartScreenUrlWarning", RemoteUrl, FileName) | extend ReasonForTrigger = parse_json(AdditionalFields).Experience | project Timestamp, DeviceName, ActionType, SmartScreenTrigger, ReasonForTrigger, InitiatingProcessCommandLine
// Author: Alex Teixeira (alex@opstune.com) DeviceProcessEvents | where Timestamp > ago(60d) // Speed up the query by filtering most frequent processes | where FolderPath matches regex @'(?i)^[a-z]:\\\S+\.exe' and not ((FolderPath contains "c:\\windows" and FolderPath matches regex @'(?i)microsoft\.net|softwaredistribution|system32|syswow64|ccm|servicing|winsxs') or FolderPath matches regex @'(?i)^(d:\\apps|c:\\_datas\\)') // Normalize to frequent (known) RATs | extend RAT=case( FolderPath contains "teamviewer", "TeamViewer", FolderPath contains "anydesk", "AnyDesk", FolderPath contains "rustdesk", "RustDesk", FolderPath contains "vnc", "VNC", FolderPath contains "manageengine", "ManageEngine", FolderPath contains "fastclient", "FastClient", FolderPath contains "logmein", "LogMeIn", FolderPath contains "bomgar", "Bomgar", FolderPath contains "netviewer", "NetViewer", FolderPath contains "ultraviewer", "UltraViewer", FolderPath contains "dwrcs", "Dameware", FolderPath contains "splashtop", "Splashtop", FolderPath contains "zerotier", "ZeroTier", FolderPath contains "supremo", "Supremo", "Other" ) | summarize count(), count_distinct(DeviceName), make_set(DeviceName), max(Timestamp) by RAT, FolderPath | extend r_1=@'(?i)[\\]+(NetWire|rport)[\\]+|Rsocx|BeAnywhere|DWservice|Fleetdeck|Itarian Endpoint Manager|Splashtop|Level\.io|ManageEngine|ScreenConnect|TrendMicro BaseCamp|Sorillus|ZeroTier|JollyFastVNC|AB Tutor|Barracuda Workplace|SolarWinds RMM|Naverisk' | extend r_2=@'(?i)(NetSupport|TeamViewer|Anydesk|UltraViewer|realvnc|TightVNC|LogMeIn|fastclient|ultraVNC|bomgar.+scc|accessserver|aeroadmin|alitask|alpemix|ammyy|ateraagent|basupsrvc|basupsrvcupdate|basuptshelper|beamyourscreen|beanywhere|cagservice|chrome remote desktop|clientmrinit|connectwise|connectwisecontrol|crossloopservice|ctiserv|dameware|datto|domotz|dwrcs|dwservice|eratool|ericomconnnectconfigurationtool|ezhelpclient|fixmeit|fixmeitclient|fleetdeck|goverrmc|guacd|instanthousecall|intelliadmin|iperiusremote|islalwaysonmonitor|isllightservice|itarian|jumpclient|jumpdesktop|jumpservice|kaseya|landeskagentbootstrap|laplink|laplinkeverywhere|ldsensors|llrcservice|lmiignition|ltsvcmon|mgntsvc|mikogo|mionet|myivomanager|nateon|neturo|netviewer|nhostsvc|ntrntservice|orcus|pcaquickconnect|pcstarter|pcvisit|pocketcontroller|ptdskclient|pulseway|rcengmgru|rcmgrsvc|rdpwrap|remobo|remote utilities|remoteconsole|remotepass|remotepc|remotepcservice|remotesupportplayeru|remoteview|rfusclient|romfusclient|romserver|romviewer|rpaccess|rpcgrab|rpcsetup|rpcsuite|rpwhostscr|rustdesk|rutserv|rutview|rxstartsupport|screenconnect|seetrolclient|seetrolremote|serverproxyservice|showmypc|simplehelpcustomer|simpleservice|sorillus|sragent|supremo|supremohelper|syncro|tacticalrmm|take\s*control|tdp2tcp|tigervnc|trend.+basecamp|turbomeeting|ultraviewer|vncconnect|webex remote|webrdp|weezo|weezohttpd|windows admin centre|wmcsvc|zerotier|zoho assist).*\.exe$' | extend r_3=@'(?i)\\(baseclient|BASupApp|DWAgent|ITSMAgent|level|Atera|radmin|srserver|rvagent|intouch)\.exe$' | where (FolderPath matches regex r_1 or FolderPath matches regex r_2 or FolderPath matches regex r_3) | extend set_DeviceName=iff(count_distinct_DeviceName>5, strcat("Too many (", count_distinct_DeviceName, ")"), set_DeviceName) | summarize TotalEvents=sum(count_), DeviceCount=count_distinct(set_DeviceName), Devices=make_set(set_DeviceName), Processes=make_set(FolderPath), LastSeen=max(max_Timestamp) by RAT | sort by DeviceCount desc, TotalEvents desc
DeviceNetworkEvents | where RemotePort == 445 | where ActionType == "ConnectionSuccess" // Collect the last event that a device has connected via SMB to a unique remote IP | summarize arg_max(Timestamp, *) by DeviceId, RemoteIP | summarize RemoteSMBUrls = make_set_if(RemoteUrl, isnotempty(RemoteUrl)), make_set_if(RemoteIP, isempty(RemoteUrl)), TotalConnections = dcount(RemoteIP) by DeviceName | sort by TotalConnections