Add --open-redirect mutator (CWE-601 unvalidated redirect)#32
Merged
Conversation
Targets the CWE-601 / ASVS V5.1.5 unvalidated-redirect family at the request-parameter layer. Where --ssrf-probe attacks what server-side network resource the application fetches on the caller's behalf, --open-redirect attacks what destination the application bounces the caller's browser to: a redirect-destination value (next, redirect_uri, returnTo, callback, ...) is reflected into a Location: header reaching an attacker-controlled external site, turning the trusted host into a phishing-redirect surface or leaking OAuth authorization codes via the redirect_uri. Four surfaces (query, urlencoded body, top-level JSON string, Referer header when present) cross-producted with seven disjoint payload techniques: backslash-host, cross-origin, data-uri, javascript-uri, protocol-relative, userinfo-confusion, whitespace-prefix. The Referer surface emits only the header-safe subset (net/http rejects/trims the other two). Eligibility by name substring match against a redirect-destination token list, or by value shape (absolute http(s) URL). Every variant keeps the caller's own credentials (Identity == nil); requests with no redirect-destination parameter and no Referer emit zero variants. Findings are class open-redirect, severity MEDIUM. Off by default (payloads point browsers at attacker URLs and embed XSS-via-redirect shapes). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds the
--open-redirectmutator targeting CWE-601 / ASVS V5.1.5 unvalidated redirects at the request-parameter layer.Where
--ssrf-probe(shipped R34) attacks what server-side network resource the application fetches (URL value consumed by outbound HTTP client reaching internal IPs / cloud metadata),--open-redirectattacks what destination the application bounces the caller's browser to (URL value reflected into aLocation:header reaching an attacker-controlled external site). The two are disjoint by design — different vuln classes, different fixes, different finding classes.The bug being tested: a
next/redirect_uri/returnTo/callbackvalue is echoed into aLocation:header (or meta-refresh /window.location.assign) without validating that the destination is in-scope. An attacker who substitutes that value with an attacker-controlled URL turns the trusted host into a phishing-redirect surface or leaks OAuth authorization codes to attacker.example via the URL fragment.Surfaces & techniques
Four surfaces (query, urlencoded body, top-level JSON string,
Refererheader when present) cross-producted with seven disjoint payload techniques (sorted, deterministic):backslash-hosthttps://attacker.example\@target.example/cross-originhttps://attacker.example/data-uridata:text/html,<script>alert(1)</script>javascript-urijavascript:alert(1)protocol-relative//attacker.example/userinfo-confusionhttps://target.example@attacker.example/whitespace-prefixhttps://attacker.example/The
Referersurface emits only the header-safe subset (excludesbackslash-hostandwhitespace-prefix, whichnet/httpwould reject or silently trim from a header value).Eligibility & invariants
back,callback,continue,dest,destination,goto,next,redir,redirect,return,returnto,success,target,url. Coversredirect_uri,redirect_url,returnTo,next_page,callback_url, etc.http(s)URL value, regardless of parameter name.Referersurface fires whenever aRefererheader is present.Refereremit zero variants.Identity == nil) — same-caller destination-rewrite probe, not an identity swap.Findings are class
open-redirect, severity MEDIUM (impact is phishing / OAuth-token leakage, not direct privilege bypass).Disjoint from
--ssrf-probe— server-side fetch (internal targets) vs. client-side redirect (external attacker site)--origin-spoof— spoofsOrigin/Refererto bypass origin-validation CSRF, not to coerce a redirect destination--csrf-header— forges anti-CSRF tokens, not redirect destinationsTest plan
go build ./...cleango vet ./...cleaninternal/mutate/open_redirect_test.goall passRefererpresent, only header-safe shapesreturnUrl,RedirectURI, etc.) + correct negativesgo test ./...green (all existing tests still pass;buildregistry_forbidden_test.goupdated for the newbuildRegistryarg)--open-redirectflag visible inscan --help🤖 Generated with Claude Code