HTTP request smuggling

Maxim Dounin mdounin at mdounin.ru
Wed Jun 30 16:13:32 UTC 2021


Hello!

On Wed, Jun 30, 2021 at 05:01:11PM +0200, Hans Middelhoek wrote:

> Recently I got a report from a security researcher who said I'm 
> vulnerable for HTTP request smuggling attacks and included a 
> demonstration. I couldn't imagine he was right because I'm using 
> HTTP/1.0 connections between Nginx (reverse proxy) and Apache. It should 
> only be possible when Nginx and Apache are reusing their connections, in 
> real life that means they're using keepalive but that's not possible 
> with HTTP/1.0 and therefore my setup shouldn't be vulnerable to this attack.
> 
> I tested his demonstration and am able to get the same result. Strange 
> thing is that I also get this outcome with Nginx as standalone 
> webserver, tested with different versions from 1.13.3 to 1.19.6 with 
> default configuration on Debian Stretch.
> 
> I used the Request Editor of OWASP ZAP (zaproxy) to test the following 
> request:
> ------------------------------
> POST / HTTP/1.1
> Transfer-Encoding: chunked
> Content-Length: 32
> Foo: bar
> Host: vulnerable-domain.com
> 
> 0
> 
> GET /admin7 HTTP/1.1
> X-Foo: k
> ------------------------------
> 
> Processing the request twice results in a 405 (not allowed) the first 
> time and 404 (not found) the second time. The Nginx logs show the 
> /admin7 GET request the second time.
> 
> When I set keepalive_timeout 0; this doesn't work anymore. The same 
> request doesn't work on Apache 2.4 with keepalive enabled. It seems like 
> Nginx is vulnerable to this type of attack, what am I missing?

The provided listing contains two separate requests, the "POST /" 
request with an empty body using chunked transfer encoding, and 
the "GET /admin7" request.

Note that "Transfer-Encoding: chunked" takes precedence over the 
"Content-Length: 32", see RFC 7230, section 3.3.3 "Message Body 
Length" for details 
(https://datatracker.ietf.org/doc/html/rfc7230#section-3.3.3):

       If a message is received with both a Transfer-Encoding and a
       Content-Length header field, the Transfer-Encoding overrides the
       Content-Length.

Unfortunately, many "security researchers" out there do not know 
how HTTP works, and generate many false reports.

Hope this helps.

-- 
Maxim Dounin
http://mdounin.ru/


More information about the nginx mailing list