Listen to this Post
How the CVE works: The vulnerability exists in rwsdk server actions which enforce HTTP method restrictions but lack origin validation. When a browser makes a request from an origin that the browser considers same-site (e.g., sibling subdomain under the same registrable domain, or localhost:different port), the victim’s session cookie is automatically attached due to SameSite=Lax behavior. An attacker controlling such an origin can craft a POST request to `/server-action` endpoint using mode: "no-cors". The browser sends the request with the victim’s cookie, and rwsdk processes it without checking the `Origin` header against the request’s host. The action executes on the server, performing writes or state changes. The attacker cannot read responses due to opaque responses, but side effects occur. For apps on custom domains like app.example.com, any sibling subdomain under `example.com` becomes a threat vector. Subdomain takeover, XSS on sibling apps, or user-content subdomains can be exploited. On public suffix domains (.workers.dev, .pages.dev), sibling subdomains are cross-site, so not exposed. Local development on `localhost` with any port is treated same-site, so a separate local process can trigger actions. Cross-site requests from entirely different domains (e.g., `evil.com` to app.com) are not affected because `SameSite=Lax` cookies are not sent. Only non-GET action requests via `serverAction()` or RSC protocol are vulnerable; `serverQuery()` uses GET and is idempotent, thus unaffected. The patch adds Origin/Host match enforcement for non-GET requests, rejecting mismatched origins with HTTP 403 unless explicitly allowed via `allowedOrigins` config.
dailycve form:
Platform: rwsdk
Version: before patch
Vulnerability: missing origin validation
Severity: critical
date: 2024-12-01
Prediction: patch already released
What Undercode Say:
Analytics
Check if server action endpoint is vulnerable
curl -X POST https://app.example.com/server-action \
-H "Origin: https://attacker.example.com" \
-H "Cookie: session= victim_cookie" \
-d '{"action":"deleteUser","id":123}' \
--no-cors -v
Extract registrable domain for sibling subdomain testing
python3 -c "import tldextract; print(tldextract.extract('app.example.com').registered_domain)"
Test localhost cross-port attack
curl -X POST http://localhost:3000/server-action \
-H "Origin: http://localhost:8080" \
--cookie "session=dev_cookie" \
-d '{"action":"createAdmin"}'
Exploit:
Attacker registers expired subdomain (e.g., `cdn.example.com` pointing to attacker’s server). Victim visits attacker’s site where JavaScript fetches `https://cdn.example.com/exploit.html` (same-site). From there, fetch POST to `https://app.example.com/server-action` with `credentials: ‘include’` and mode: 'no-cors'. Victim’s session cookie attaches, action executes.
Protection from this CVE
Upgrade rwsdk to patched version enabling Origin/Host check. If cannot upgrade, set `allowedOrigins: []` (empty) in `defineApp` to block all cross-origin actions. Validate `Origin` header manually nginx: if ($http_origin !~ "^https?://(app\.example\.com)$") { return 403; }. Use CSRF tokens for sensitive actions. Deploy on public suffix domains (.workers.dev) to avoid sibling subdomain risks.
Impact
Authenticated victim’s session used to invoke arbitrary server actions, leading to unauthorized data writes, account modifications, privilege escalation, or any state-changing operation exposed by the app. No response read, so blind SSRF or internal state corruption. In development, local attackers can pivot to production-like actions.
🎯Let’s Practice Exploiting & Learn Patching For Free:
Sources:
Reported By: github.com
Extra Source Hub:
Undercode

