
Cloud Vulnerability DB
A community-led vulnerabilities database
NOTE Also covers GHSA-5w7f-g655-933c (PAR
request_uri), consolidated here: same root cause, same reporter, same fix. Concurrent requests can redeem one authorization code, or complete authorization with one pushedrequest_uri, more than once.Severity reconciled to Medium. Every variant needs the attacker to already hold the single-use artifact: PKCE is required for all clients except
client_secret_basic, so a code is redeemable only with its verifier or the client secret, and a pushedrequest_uriis completed only through the victim's authenticated session. What the race adds is a second redemption that evades single-use and replay detection.
A Time-of-Check to Time-of-Use (TOCTOU) race condition in Logto's OIDC database adapter allows an attacker to bypass the single-use restriction of OAuth 2.0 Authorization Codes. By sending concurrent token exchange requests, an attacker can redeem a single intercepted authorization code multiple times, resulting in the issuance of multiple distinct access and refresh tokens bound to the victim's identity. This violates RFC 6749 §4.1.2.
The vulnerability stems from a non-atomic check-then-consume pattern in the OIDC provider's grant handler and Logto's Postgres adapter.
authorization_code.js), the code checks if code.consumed is true (based on a prior SELECT query). If false, it calls code.consume().packages/core/src/queries/oidc-model-instance.ts:167-174), consumeInstanceById executes an UPDATE statement without a Compare-And-Swap (CAS) guard:const consumeInstanceById = async (modelName: string, id: string) => {
await pool.query(sql`
update ${table}
set ${fields.consumedAt}=${convertToTimestamp()}
where ${fields.modelName}=${modelName}
and ${fields.id}=${id}
// MISSING: AND ${fields.consumedAt} IS NULL
`);
};Under high concurrency, multiple threads can pass the JS-level check before any UPDATE commits. Because the UPDATE is idempotent and lacks a row-level lock or CAS condition, all concurrent requests succeed, minting distinct tokens for the same code.
POST /oidc/token requests using the same code and PKCE verifier, synchronized via a threading barrier.access_token, refresh_token, and id_token values. All minted tokens carry the victim's sub claim.Any attacker who can intercept an authorization code can multiply their access by racing the token exchange. This defeats the single-use guarantee, allowing the attacker to establish multiple concurrent sessions as the victim, bypassing downstream rate-limiting or single-session enforcement mechanisms.
Source: NVD
Free Vulnerability Assessment
Evaluate your cloud security practices across 9 security domains to benchmark your risk level and identify gaps in your defenses.
Get a personalized demo
"Best User Experience I have ever seen, provides full visibility to cloud workloads."
"Wiz provides a single pane of glass to see what is going on in our cloud environments."
"We know that if Wiz identifies something as critical, it actually is."