GitHub Security Advisory: GHSA-qv7j-4883-hwh7
Package: rack (RUBYGEMS)
Severity: MODERATE (CVSS 5.9)
CWE: CWE-625: Permissive Regular Expression
Vulnerable versions: >= 3.0.0.beta1, < 3.1.21
Patched in: 3.1.21

Summary: Rack::Sendfile header-based X-Accel-Mapping regex injection enables unauthorized X-Accel-Redirect

Details:
## Summary

`Rack::Sendfile#map_accel_path` interpolates the value of the `X-Accel-Mapping` request header directly into a regular expression when rewriting file paths for `X-Accel-Redirect`. Because the header value is not escaped, an attacker who can supply `X-Accel-Mapping` to the backend can inject regex metacharacters and control the generated `X-Accel-Redirect` response header.

In deployments using `Rack::Sendfile` with `x-accel-redirect`, this can allow an attacker to cause nginx to serve unintended files from configured internal locations.

## Details

`Rack::Sendfile#map_accel_path` processes header-supplied mappings using logic equivalent to:

```ruby
mapping.split(',').map(&:strip).each do |m|
  internal, external = m.split('=', 2).map(&:strip)
  new_path = path.sub(/\A#{internal}/i, external)
  return new_path unless path == new_path
end
```

Here, `internal` comes from the `HTTP_X_ACCEL_MAPPING` request header and is inserted directly into a regular expression without escaping. This gives the header value regex semantics rather than treating it as a literal prefix.

As a result, an attacker can supply metacharacters such as `.*` or capture groups to alter how the path substitution is performed. For example, a mapping such as:

```http
X-Accel-Mapping: .*=/protected/secret.txt
```

causes the entire source path to match and rewrites the redirect target to a clean attacker-chosen internal path.

This differs from the documented behavior of the header-based mapping path, which is described as a simple substitution. While application-supplied mappings may intentionally support regular expressions, header-supplied mappings should be treated as literal path prefixes.

The issue is only exploitable when untrusted `X-Accel-Mapping` headers can reach Rack. One realistic case is a reverse proxy configuration that intends to set `X-Accel-Mapping` itself, but fails to do so on some routes, allowing a client-supplied header to pass through unchanged.

## Impact

Applications using `Rack::Sendfile` with `x-accel-redirect` may be affected if the backend accepts attacker-controlled `X-Accel-Mapping` headers.

In affected deployments, an attacker may be able to control the `X-Accel-Redirect` response header and cause nginx to serve files from internal locations that were not intended to be reachable through the application. This can lead to unauthorized file disclosure.

The practical impact depends on deployment architecture. If the proxy always strips or overwrites `X-Accel-Mapping`, or if the application uses explicit configured mappings instead of the request header, exploitability may be eliminated.

## Mitigation

* Update to a patched version of Rack that treats header-supplied `X-Accel-Mapping` values as literal strings rather than regular expressions.
* Strip or overwrite inbound `X-Accel-Mapping` headers at the reverse proxy so client-supplied values never reach Rack.
* Prefer explicit application-configured sendfile mappings instead of re