ANT-2026-XJKJSANG · supabase/auth
other low
Severity Claude low · Security research firm - · Maintainer -
Discovered by Claude Mythos Preview
Anthropic's analysis of this finding, sealed at approval.
ANT-2026-XJKJSANG: Azure issuer check uses always-true boolean expression
In the Azure external auth provider (azure.go:72), the guard if !IsAzureIssuer(x) || !IsAzureCIAMIssuer(x) is always true because no issuer string can be both a v2 Azure issuer and a CIAM issuer simultaneously. As a result, expectedIssuer is unconditionally cleared and the strict per-tenant issuer comparison never fires. An attacker presenting an otherwise well-formed id_token from a different Azure tenant is not rejected early by the tenant pin; the token instead proceeds to the generic multi-tenant Azure common-key verification path. Operators who configured a specific tenant issuer and rely on this check for tenant isolation get weaker filtering than intended.
Target
Project: supabase/auth
Location: internal/api/provider/azure.go:72
Discovery: static analysis — not yet dynamically reproduced
Technical Details
The boolean uses OR of two negations where AND was intended: since IsAzureIssuer(x) and IsAzureCIAMIssuer(x) are mutually exclusive, at least one negation is always true, making the whole expression a tautology. This unconditionally sets expectedIssuer = "", neutering the subsequent equality check against the configured tenant issuer.
Reproduction
- Operator configures Azure provider with a specific tenant issuer URL
- Attacker obtains a valid, well-formed id_token from a different Azure tenant
- Attacker submits the token to the auth endpoint
- Tautological guard clears expectedIssuer so the strict tenant-issuer equality check is skipped
- Token proceeds to downstream common-key verification instead of being rejected early
[No reproducer or sanitizer output attached — request from security-cvd@anthropic.com if needed.]
Suggested Fix
Change the condition so expectedIssuer is cleared only when the configured URL is neither an Azure v2 issuer nor a CIAM issuer — i.e., use logical AND of the negations (!IsAzureIssuer(x) && !IsAzureCIAMIssuer(x)) — restoring per-tenant issuer pinning.
Acknowledgement
This vulnerability was discovered by Claude, Anthropic's AI assistant, and triaged by the Anthropic security team in collaboration with Anthropic Research. Please direct questions to security-cvd@anthropic.com and reference ANT-2026-XJKJSANG.
Reference: ANT-2026-XJKJSANG
Anthropic CVD Policy: https://www.anthropic.com/coordinated-vulnerability-disclosure
Dates from discovery through public reveal.
- 2026-05-14 Reported to tracker
- 2026-05-14 Maintainer acknowledged
- 2026-05-15 Sent to maintainer
- 2026-06-02 Patch released
- 2026-08-18 Publicly revealed
SHA-3-512 hash:
33feceffbe4abf6811dd3cab5c315a6e1fa1d9e3e4aaf937f4a69d8aed2512c787f3341c4055fa55907cc735e0ea4eb61a9f91cb60e9647dd4c1ae7551d3654d
Committed 2026-05-17 17:59 PT
Revealed 2026-08-18 07:12 PT
Verify (download preimage.json)
Show preimage JSON
{
"ant_id": "ANT-2026-XJKJSANG",
"bug_class": "other",
"claude_severity": "low",
"commit_sha": null,
"created_at": "2026-05-14T22:01:37+00:00",
"description": "In the Azure external auth provider (azure.go:72), the guard `if !IsAzureIssuer(x) || !IsAzureCIAMIssuer(x)` is always true because no issuer string can be both a v2 Azure issuer and a CIAM issuer simultaneously. As a result, expectedIssuer is unconditionally cleared and the strict per-tenant issuer comparison never fires. An attacker presenting an otherwise well-formed id_token from a different Azure tenant is not rejected early by the tenant pin; the token instead proceeds to the generic multi-tenant Azure common-key verification path. Operators who configured a specific tenant issuer and rely on this check for tenant isolation get weaker filtering than intended.",
"discovered_at": "2026-05-10T00:00:00+00:00",
"location": "internal/api/provider/azure.go:72",
"poc_sha256": null,
"preimage_version": 1,
"project": "supabase/auth",
"reproduction": [
"Operator configures Azure provider with a specific tenant issuer URL",
"Attacker obtains a valid, well-formed id_token from a different Azure tenant",
"Attacker submits the token to the auth endpoint",
"Tautological guard clears expectedIssuer so the strict tenant-issuer equality check is skipped",
"Token proceeds to downstream common-key verification instead of being rejected early"
],
"technical_details": "The boolean uses OR of two negations where AND was intended: since IsAzureIssuer(x) and IsAzureCIAMIssuer(x) are mutually exclusive, at least one negation is always true, making the whole expression a tautology. This unconditionally sets expectedIssuer = \"\", neutering the subsequent equality check against the configured tenant issuer.",
"title": "Azure issuer check uses always-true boolean expression",
"vendor_severity": null
}