Detect Web Cookies in Splunk
Adversaries may forge web cookies to gain unauthorized access to web applications or internet services. Unlike cookie theft (T1539), forged cookies are newly crafted by the adversary using stolen cryptographic material such as HMAC signing keys, private keys, or application secrets. Common targets include JWT bearer tokens, Flask session cookies (signed with itsdangerous using SECRET_KEY), Django session tokens, and platform-specific SaaS session identifiers. Because forged cookies appear as valid, trusted session credentials, they can bypass multi-factor authentication — the application trusts the cookie without re-challenging the user. The SolarWinds (SUNBURST) attack demonstrated this technique at scale when UNC2452/Dark Halo forged SAML assertion cookies after stealing ADFS signing certificates, enabling persistent access to cloud tenants that bypassed MFA entirely. Detection focuses on authentication anomalies in identity provider logs (sessions appearing from new locations without prior interactive authentication), endpoint activity where signing key material is accessed prior to token generation, and web server log patterns indicating session anomalies such as the same session ID appearing from multiple IPs.
MITRE ATT&CK
- Tactic
- Credential Access
- Technique
- T1606 Forge Web Credentials
- Sub-technique
- T1606.001 Web Cookies
- Canonical reference
- https://attack.mitre.org/techniques/T1606/001/
SPL Detection Query
( index=azure sourcetype="azure:aad:signin" ) OR ( index=azure sourcetype="azure:aad:signinlogs" )
| eval riskDetail=coalesce(riskDetail, "none")
| eval riskLevelDuringSignIn=coalesce(riskLevelDuringSignIn, "none")
| eval networkLocationDetails=coalesce(networkLocationDetails, "")
| eval authenticationRequirement=coalesce(authenticationRequirement, "multiFactorAuthentication")
| eval statusCode=coalesce('status.errorCode', 0)
// Score each sign-in against forgery indicators
| eval IsAnomalousToken=if(riskDetail="anomalousToken" OR riskDetail="unfamiliarFeatures", 1, 0)
| eval IsHighRisk=if(riskLevelDuringSignIn="high" OR riskLevelDuringSignIn="medium", 1, 0)
| eval IsAnonymousNetwork=if(match(lower(networkLocationDetails), "anonymizedipaddress|tor|anonymizer"), 1, 0)
| eval IsMFABypassedSession=if(authenticationRequirement="singleFactorAuthentication" AND statusCode=0, 1, 0)
| eval SuspicionScore=IsAnomalousToken + IsHighRisk + IsAnonymousNetwork + IsMFABypassedSession
| where SuspicionScore >= 1
// Aggregate by user and session correlation ID to identify multi-IP usage
| stats
max(SuspicionScore) as MaxSuspicion,
count as SignInCount,
dc(ipAddress) as UniqueIPCount,
values(ipAddress) as IPAddresses,
values(appDisplayName) as Applications,
values(riskDetail) as RiskDetails,
sum(IsAnomalousToken) as AnomalousTokenHits,
sum(IsHighRisk) as HighRiskHits,
sum(IsAnonymousNetwork) as AnonymousNetworkHits,
sum(IsMFABypassedSession) as MFABypassHits,
earliest(_time) as FirstSeen,
latest(_time) as LastSeen
by userPrincipalName, correlationId
// Flag sessions with multiple IPs regardless of base suspicion score
| eval SuspicionScore=if(UniqueIPCount > 1, MaxSuspicion + 1, MaxSuspicion)
| eval DetectionReasons=mvappend(
if(AnomalousTokenHits > 0, "AnomalousToken", null()),
if(HighRiskHits > 0, "HighRiskSignIn", null()),
if(AnonymousNetworkHits > 0, "AnonymousNetwork", null()),
if(MFABypassHits > 0, "MFABypassedViaSession", null()),
if(UniqueIPCount > 1, "MultiIPSession", null())
)
| where SuspicionScore >= 1
| sort - SuspicionScore, - SignInCount
| table userPrincipalName, correlationId, SignInCount, UniqueIPCount,
IPAddresses, Applications, DetectionReasons, SuspicionScore,
FirstSeen, LastSeen Detects potential forged web cookie usage in Azure AD sign-in telemetry ingested via the Microsoft Azure Add-on for Splunk. Evaluates each sign-in event against four forgery indicators: anomalous token risk (Microsoft Identity Protection flagging unusual JWT characteristics), high/medium risk level signals, anonymous network origin (Tor or anonymized IP), and successful single-factor authentication without MFA (suggesting a forged cookie bypassed step-up auth). Results are aggregated by user and session correlation ID to surface multi-IP session reuse — a strong indicator that a forged cookie is being used simultaneously from multiple attacker hosts. The suspicion scoring approach allows analysts to prioritize high-confidence events while retaining lower-confidence signals for hunting.
Data Sources
Required Sourcetypes
False Positives & Tuning
- Corporate VPN or ZTNA users appearing to authenticate from anonymized IPs — add known VPN egress ranges to a lookup table and use NOT lookup to suppress
- Mobile app token refresh flows triggering multiple non-interactive sign-ins across IP changes as users roam between networks
- Service accounts running scheduled automation from cloud infrastructure IPs that look anomalous to Identity Protection models
- Legitimate users who share devices or sessions (e.g., hospital shared terminals) where session IDs may be reused across different user IPs
- Azure AD Identity Protection model retraining periods where the baseline shifts and previously-normal tokens are flagged as anomalous
Other platforms for T1606.001
Testing Methodology
Validate this detection against 5 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 1Flask Session Cookie Forgery with Known Secret Key
Expected signal: On Linux: process creation for python3 with command line containing 'itsdangerous', 'URLSafeTimedSerializer', 'forged'. Sysmon for Linux / auditd will capture the process execution. On Windows: DeviceProcessEvents would show python.exe or python3.exe with the script content in the command line arguments if run via -c flag. No network events are generated (offline forgery) — the forged cookie must be injected into a subsequent HTTP request to trigger authentication events in web server logs.
- Test 2JWT Forgery via Weak HMAC Secret Brute Force and Re-Signing
Expected signal: Process creation for python3 with PyJWT library import visible in command line or process arguments. On Windows with Sysmon: DeviceProcessEvents with python.exe or python3.exe. No network telemetry is generated during the offline forgery stage. When the forged JWT is subsequently used in HTTP Authorization headers against the target application, web server access logs will record the authentication attempt.
- Test 3Browser Cookie Injection for Session Hijacking via Curl
Expected signal: Sysmon Event ID 3 (Network Connection): curl process making TCP connection to TARGET_URL. Web server access logs (IIS W3CIISLog or Apache access log via syslog sourcetype) will record the request with the Cookie header value, source IP, and User-Agent string. Web proxy logs (stream:http sourcetype if Splunk stream is deployed) will capture the full HTTP request including cookie headers. Azure AD or application auth logs will record the attempted authentication if the web application validates the cookie against an identity provider.
- Test 4JWT Algorithm Confusion Attack (None Algorithm)
Expected signal: Process creation for python3 with base64 and json module usage. The output is the forged JWT token string. On endpoints with Sysmon: DeviceProcessEvents with python command line content. When the 'alg: none' token is submitted to a vulnerable application, the web server logs will show successful authentication. Modern applications and Azure AD reject 'alg: none' tokens, but vulnerable on-premise applications may not.
- Test 5Simulate Cookie Forgery Detection — Azure AD Risk Event Trigger
Expected signal: Azure AD SigninLogs entry for the test account with IPAddress showing Tor exit node, NetworkLocationDetails containing 'anonymizedIPAddress', and RiskLevelDuringSignIn set to 'medium' or 'high' by Identity Protection. The sign-in will appear in Entra ID > Sign-in logs and should be ingested into Microsoft Sentinel's SigninLogs table within 5–15 minutes.
References (10)
- https://attack.mitre.org/techniques/T1606/001/
- https://www.volexity.com/blog/2020/12/14/dark-halo-leverages-solarwinds-compromise-to-breach-organizations/
- https://wunderwuzzi23.github.io/blog/passthecookie.html
- https://unit42.paloaltonetworks.com/mac-malware-steals-cryptocurrency-exchanges-cookies/
- https://learn.microsoft.com/en-us/entra/id-protection/concept-identity-protection-risks
- https://learn.microsoft.com/en-us/azure/sentinel/connect-azure-active-directory
- https://portswigger.net/web-security/jwt/algorithm-confusion
- https://github.com/ticarpi/jwt_tool
- https://owasp.org/www-community/attacks/Session_hijacking_attack
- https://flask.palletsprojects.com/en/3.0.x/security/#set-cookie-options
Unlock Pro Content
Get the full detection package for T1606.001 including response playbook, investigation guide, and atomic red team tests.