Max-Forwards
Tracing the path a request takes through proxies and gateways is achieved through the Max-Forwards request header, which limits how many intermediaries forward an HTTP TRACE or OPTIONS request.
Usage
The Max-Forwards header provides a mechanism for tracing the path a request takes through proxies and gateways. Each intermediary in the chain decrements the value by one before forwarding the request. When the count reaches zero, the intermediary stops forwarding and responds directly.
This behavior is useful for diagnosing routing issues. Setting the value to zero targets the first proxy in the chain. Incrementing the value by one for each subsequent request maps out each intermediary along the path. The Via header in the response identifies which intermediary handled the request at each hop.
The header applies exclusively to TRACE and OPTIONS methods. Intermediaries receiving Max-Forwards on other request methods ignore the header and forward the request normally.
When an intermediary receives a Max-Forwards value of zero on a TRACE request, the intermediary responds with a 200 status and echoes the received request as the response body. For an OPTIONS request with a zero value, the intermediary responds with the communication options available at the intermediary itself.
Directives
integer-value
A non-negative integer indicating the maximum number of remaining hops. Each intermediary decrements the value before forwarding.
Max-Forwards: <integer>
Example
A diagnostic TRACE request targets the second intermediary in the chain by setting Max-Forwards to
- The first proxy decrements the value and forwards the request. The second proxy receives zero and responds as the final recipient.
TRACE / HTTP/1.1
Host: origin.example.re
Max-Forwards: 1
The first proxy forwards the request with a decremented value.
TRACE / HTTP/1.1
Host: origin.example.re
Max-Forwards: 0
Via: 1.1 proxy-a.example.re
The second proxy receives a zero value, stops forwarding, and returns the request as received in the response body.
HTTP/1.1 200 OK
Content-Type: message/http
TRACE / HTTP/1.1
Host: origin.example.re
Max-Forwards: 0
Via: 1.1 proxy-a.example.re
A debugging tool the modern edge ignores
Max-Forwards is defined for TRACE and OPTIONS alone, and every hop is required to decrement before forwarding, answering as the final recipient at zero. A proxy is also permitted to clamp the value down to its own maximum, so a large starting value never guarantees reaching the origin.
Implementation coverage decides the header's real usefulness. Apache implements the full behavior and goes further, answering an unparseable value with 400, and a zero on any method other than TRACE or OPTIONS with a 400 carrying the message "Max-Forwards has reached zero
- proxy loop?". nginx implements nothing, neither reading nor decrementing the field, and refuses TRACE outright with 405, which removes the tracing half of the mechanism from any nginx-fronted stack.
CDN edges complete the picture: live probes show requests with a zero Max-Forwards passing straight through Varnish-based tiers to the origin, so the hop-by-hop diagnostic no longer survives contact with a modern edge.
TRACE itself is less dead than reputation suggests.
Apache ships TraceEnable on as the default and
answers with the reflected request, and the disabling
is policy from hardening guides rather than a vendor
default. What ended the cross-site tracing attack was
the browser side: script has been unable to issue
TRACE for years, and the Fetch standard forbids the
method outright.