GHSA-qfgr-crr9-7r49
Rack: Forwarded Header semicolon injection enables Host and Scheme spoofing
Quick fix
GHSA-qfgr-crr9-7r49 — rack: upgrade to the fixed version with the command below.
bundle update rackDetails
## Summary
`Rack::Utils.forwarded_values` parses the RFC 7239 `Forwarded` header by splitting on semicolons before handling quoted-string values. Because quoted values may legally contain semicolons, a header such as:
```http Forwarded: for="127.0.0.1;host=evil.com;proto=https" ```
can be interpreted by Rack as multiple `Forwarded` directives rather than as a single quoted `for` value.
In deployments where an upstream proxy, WAF, or intermediary validates or preserves quoted `Forwarded` values differently, this discrepancy can allow an attacker to smuggle `host`, `proto`, `for`, or `by` parameters through a single header value.
## Details
`Rack::Utils.forwarded_values` processes the header using logic equivalent to:
```ruby forwarded_header.split(';').each_with_object({}) do |field, values| field.split(',').each do |pair| pair = pair.split('=').map(&:strip).join('=') return nil unless pair =~ /\A(by|for|host|proto)="?([^"]+)"?\Z/i (values[$1.downcase.to_sym] ||= []) << $2 end end ```
The method splits on `;` before it parses individual `name=value` pairs. This is inconsistent with RFC 7239, which permits quoted-string values, and quoted strings may contain semicolons as literal content.
As a result, a header value such as:
```http Forwarded: for="127.0.0.1;host=evil.com;proto=https" ```
is not treated as a single `for` value. Instead, Rack may interpret it as if the client had supplied separate `for`, `host`, and `proto` directives.
This creates an interpretation conflict when another component in front of Rack treats the quoted value as valid literal content, while Rack reparses it as multiple forwarding parameters.
## Impact
Applications that rely on `Forwarded` to derive request metadata may observe attacker-controlled values for `host`, `proto`, `for`, or related URL components.
In affected deployments, this can lead to host or scheme spoofing in derived values such as `req.host`, `req.scheme`, `req.base_url`, or `req.url`. Applications that use those values for password reset links, redirects, absolute URL generation, logging, IP-based decisions, or backend requests may be vulnerable to downstream security impact.
The practical security impact depends on deployment architecture. If clients can already supply arbitrary trusted `Forwarded` parameters directly, this bug may not add meaningful attacker capability. The issue is most relevant where an upstream component and Rack interpret the same `Forwarded` header differently.
## Mitigation
* Update to a patched version of Rack that parses `Forwarded` quoted-string values before splitting on parameter delimiters. * Avoid trusting client-supplied `Forwarded` headers unless they are normalized or regenerated by a trusted reverse proxy. * Prefer stripping inbound `Forwarded` headers at the edge and reconstructing them from trusted proxy metadata. * Avoid using `req.host`, `req.scheme`, `req.base_url`, or `req.url` for security-sensitive operations unless the forwarding chain is explicitly trusted and validated.
Are you affected?
Enter the version of the package you're using.