Skip to content

Commit 2a3cab8

Browse files
[New Rule] Entra ID Mismatched Device Code Auth Attempts for Single User
Fixes #5395
1 parent 02979fe commit 2a3cab8

File tree

1 file changed

+97
-0
lines changed

1 file changed

+97
-0
lines changed
Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,97 @@
1+
[metadata]
2+
creation_date = "2025/12/02"
3+
integration = ["azure"]
4+
maturity = "production"
5+
updated_date = "2025/12/02"
6+
7+
[rule]
8+
author = ["Elastic"]
9+
description = """
10+
Identifies Entra ID authentication using device code sign-in from atypical locations. Adversaries may leverage OAuth 2.0
11+
device code flow phishing techniques to gain unauthorized access to Azure resources from unusual geographic locations.
12+
This rule detects successful sign-ins using device code authentication originating from locations that deviate from the
13+
user's typical sign-in patterns, indicating potential malicious activity.
14+
"""
15+
from = "now-9m"
16+
interval = "8m"
17+
language = "esql"
18+
license = "Elastic License v2"
19+
name = "Entra ID Device Code Auth from Atypical Location"
20+
references = ["https://www.wiz.io/blog/recent-oauth-attacks-detection-strategies"]
21+
risk_score = 47
22+
rule_id = "53df1dfc-cf9b-11f0-8892-f661ea17fbcc"
23+
severity = "medium"
24+
tags = [
25+
"Domain: Cloud",
26+
"Domain: Identity",
27+
"Data Source: Azure",
28+
"Data Source: Entra ID",
29+
"Data Source: Entra ID Sign-In Logs",
30+
"Use Case: Identity and Access Audit",
31+
"Tactic: Initial Access",
32+
"Resources: Investigation Guide",
33+
]
34+
timestamp_override = "event.ingested"
35+
type = "esql"
36+
37+
query = '''
38+
from logs-azure.signinlogs-*
39+
| where
40+
event.category == "authentication" and
41+
azure.signinlogs.properties.original_transfer_method == "deviceCodeFlow"
42+
| eval
43+
Esql.interactive_logon = CASE(azure.signinlogs.category == "SignInLogs", source.ip, null),
44+
Esql.non_interactive_logon = CASE(azure.signinlogs.category == "NonInteractiveUserSignInLogs", source.ip, null)
45+
| stats
46+
Esql.count.logon = count(*),
47+
Esql.dc.source_ip = count_distinct(source.ip),
48+
Esql.is_interactive = count(Esql.interactive_logon),
49+
Esql.is_non_interactive = count(Esql.non_interactive_logon),
50+
Esql.user_agent = VALUES(user_agent.original),
51+
Esql.dc.user_agents = COUNT_DISTINCT(user_agent.original)
52+
by azure.signinlogs.properties.session_id
53+
| where
54+
Esql.is_interactive >= 2 and
55+
Esql.is_non_interactive >= 1 and
56+
(
57+
Esql.dc.user_agents >= 2 or
58+
Esql.dc.source_ip >= 2
59+
)
60+
| keep
61+
Esql.*,
62+
Esql_priv.*,
63+
azure.signinlogs.*,
64+
source.ip,
65+
user_agent.original,
66+
event.*
67+
'''
68+
69+
70+
[[rule.threat]]
71+
framework = "MITRE ATT&CK"
72+
[[rule.threat.technique]]
73+
id = "T1078"
74+
name = "Valid Accounts"
75+
reference = "https://attack.mitre.org/techniques/T1078/"
76+
[[rule.threat.technique.subtechnique]]
77+
id = "T1078.004"
78+
name = "Cloud Accounts"
79+
reference = "https://attack.mitre.org/techniques/T1078/004/"
80+
81+
82+
[[rule.threat.technique]]
83+
id = "T1566"
84+
name = "Phishing"
85+
reference = "https://attack.mitre.org/techniques/T1566/"
86+
[[rule.threat.technique.subtechnique]]
87+
id = "T1566.002"
88+
name = "Spearphishing Link"
89+
reference = "https://attack.mitre.org/techniques/T1566/002/"
90+
91+
92+
93+
[rule.threat.tactic]
94+
id = "TA0001"
95+
name = "Initial Access"
96+
reference = "https://attack.mitre.org/tactics/TA0001/"
97+

0 commit comments

Comments
 (0)