Detect Compromise Infrastructure in Microsoft Sentinel
This detection identifies indicators that adversaries may be leveraging compromised third-party infrastructure — including domains, servers, DNS services, or web services — to conduct operations against the organization. Because T1584 is a PRE-ATT&CK technique focused on adversary preparation, direct detection is not possible at the moment of compromise; instead, this detection identifies downstream indicators: network connections to infrastructure with characteristics consistent with hijacked or recently compromised assets (domains with mismatched registrar history, IPs flagged in threat intelligence, DNS resolutions to newly re-pointed hostnames, and C2 beaconing patterns associated with known compromised-infrastructure campaigns). Alerts from this detection warrant investigation into whether the communicating endpoint has been targeted via phishing, drive-by compromise, or C2 channels routed through legitimate third-party infrastructure.
MITRE ATT&CK
- Tactic
- Resource Development
- Technique
- T1584 Compromise Infrastructure
- Canonical reference
- https://attack.mitre.org/techniques/T1584/
KQL Detection Query
let SuspiciousASNs = dynamic(["AS14061", "AS16276", "AS24940", "AS20473", "AS9009"]);
let LookbackPeriod = 7d;
let BeaconingThreshold = 20;
// Part 1: Detect beaconing to infrastructure with suspicious characteristics
let BeaconingAlerts = DeviceNetworkEvents
| where Timestamp > ago(LookbackPeriod)
| where ActionType in ("ConnectionSuccess", "ConnectionAttempt")
| where RemotePort in (80, 443, 8080, 8443, 4443, 4444, 1080, 3128)
| where not(ipv4_is_private(RemoteIP))
| summarize
ConnectionCount = count(),
UniqueRemotePorts = dcount(RemotePort),
BytesSent = sum(SentBytes),
BytesReceived = sum(ReceivedBytes),
FirstSeen = min(Timestamp),
LastSeen = max(Timestamp),
SampleProcesses = make_set(InitiatingProcessFileName, 5)
by DeviceId, DeviceName, RemoteIP, RemoteUrl
| where ConnectionCount >= BeaconingThreshold
| where BytesSent > 1000
// Flag where beacon interval is highly regular (potential C2)
| extend DurationHours = datetime_diff('hour', LastSeen, FirstSeen)
| where DurationHours > 1
| extend BeaconRate = toreal(ConnectionCount) / toreal(DurationHours)
| where BeaconRate between (0.5 .. 200.0)
| extend AlertType = "PotentialBeaconing";
// Part 2: Detect DNS resolutions to IPs with poor reputation characteristics
let DNSSuspicious = DeviceNetworkEvents
| where Timestamp > ago(LookbackPeriod)
| where ActionType == "ConnectionSuccess"
| where isnotempty(RemoteUrl)
// Flag domains using dynamic DNS providers commonly abused for compromised infra
| where RemoteUrl matches regex @"(?i)(duckdns\.org|no-ip\.com|hopto\.org|ddns\.net|servebeer\.com|myftp\.biz|redirectme\.net|serveftp\.com|zapto\.org|sytes\.net|myddns\.me|dynalias\.com)"
| summarize
ConnectionCount = count(),
UniqueDevices = dcount(DeviceId),
SampleProcesses = make_set(InitiatingProcessFileName, 5),
SampleIPs = make_set(RemoteIP, 5)
by RemoteUrl
| where ConnectionCount > 0
| extend AlertType = "SuspiciousDynamicDNS";
// Part 3: Detect connections from non-browser processes to domains with short TTLs (fast-flux)
let FastFlux = DeviceNetworkEvents
| where Timestamp > ago(LookbackPeriod)
| where ActionType == "ConnectionSuccess"
| where not(ipv4_is_private(RemoteIP))
| where InitiatingProcessFileName !in~ ("chrome.exe", "firefox.exe", "msedge.exe", "iexplore.exe", "safari", "opera.exe", "brave.exe")
| where InitiatingProcessFileName !in~ ("svchost.exe", "MsMpEng.exe", "SenseIR.exe", "MsSense.exe", "SenseCncProxy.exe")
| summarize
UniqueIPs = dcount(RemoteIP),
ConnectionCount = count(),
DomainList = make_set(RemoteUrl, 10),
ProcessList = make_set(InitiatingProcessFileName, 5)
by DeviceId, DeviceName, bin(Timestamp, 1h)
| where UniqueIPs >= 5 and ConnectionCount >= 10
| extend AlertType = "PotentialFastFluxActivity";
// Union all alert types
BeaconingAlerts
| project Timestamp = LastSeen, DeviceName, RemoteIP, RemoteUrl, AlertType, ConnectionCount, BytesSent, BytesReceived, SampleProcesses
| union (
DNSSuspicious
| project Timestamp = now(), DeviceName = "Multiple", RemoteIP = tostring(SampleIPs[0]), RemoteUrl, AlertType, ConnectionCount, BytesSent = long(0), BytesReceived = long(0), SampleProcesses
)
| union (
FastFlux
| project Timestamp, DeviceName, RemoteIP = "", RemoteUrl = tostring(DomainList[0]), AlertType, ConnectionCount, BytesSent = long(0), BytesReceived = long(0), SampleProcesses = ProcessList
)
| sort by Timestamp desc Detects three patterns consistent with adversary use of compromised infrastructure: (1) beaconing behavior from endpoints to external IPs at regular intervals with data transfer, indicative of C2 over hijacked servers; (2) DNS resolutions to known dynamic DNS providers commonly abused to proxy through compromised hosts; and (3) fast-flux-like behavior where non-browser processes rapidly connect to many distinct IPs, suggestive of botnet or compromised proxy network use.
Data Sources
Required Tables
False Positives & Tuning
- Legitimate software update services or telemetry agents making frequent connections to cloud infrastructure on shared hosting providers
- VPN or proxy clients using dynamic DNS hostnames for legitimate enterprise connectivity
- IT monitoring and RMM tools (e.g., ConnectWise, Kaseya) that beacon regularly to SaaS infrastructure hosted on major cloud ASNs
- CDN-backed services with high IP rotation that may appear as fast-flux to endpoint telemetry
- Developers running local tunneling tools (ngrok, localtunnel) that resolve to dynamic DNS entries
Other platforms for T1584
Testing Methodology
Validate this detection against 3 adversary techniques from Atomic Red Team. Each test below lists the behaviour to exercise and the telemetry you should expect to see. Executable commands and cleanup steps are available with Pro.
- Test 1Simulate C2 Beaconing to Compromised VPS Infrastructure
Expected signal: Sysmon Event ID 3 (Network Connection) from powershell.exe to TARGET_IP on port 8080, firing at regular 30-second intervals. DeviceNetworkEvents in Defender for Endpoint will show repeated ConnectionSuccess events from PowerShell to the destination IP.
- Test 2DNS Resolution to Dynamic DNS Provider Domain
Expected signal: Sysmon Event ID 22 (DNS Query) entries for each domain in the $suspiciousDomains list. The Image field will show powershell.exe or the parent process. QueryName will contain the duckdns.org / ddns.net / hopto.org domains.
- Test 3Simulate Fast-Flux Connection Pattern from Non-Browser Process
Expected signal: Sysmon Event ID 3 (Network Connection) events from powershell.exe to 10+ distinct destination IPs on port 80, all occurring within a short time window. DeviceNetworkEvents will show ConnectionAttempt or ConnectionSuccess entries for each target IP.
References (8)
- https://attack.mitre.org/techniques/T1584/
- https://www.mandiant.com/resources/apt1-exposing-one-of-chinas-cyber-espionage-units
- https://www.icann.org/en/blogs/details/the-domain-name-hijacking-threat-to-global-internet-security-21-1-2021-en
- https://blog.talosintelligence.com/dnspionage-campaign-targets-middle-east/
- https://www.fireeye.com/blog/threat-research/2019/01/global-dns-hijacking-campaign-dns-record-manipulation-at-scale.html
- https://www.volexity.com/blog/2025/01/17/volttzite-targets-nato-member-using-nearest-neighbor-attack-via-compromised-infrastructure/
- https://www.cisa.gov/news-events/cybersecurity-advisories/aa20-258a
- https://sysdig.com/blog/proxyjacking-attackers-hijack-bandwidth/
Unlock Pro Content
Get the full detection package for T1584 including response playbook, investigation guide, and atomic red team tests.