Opened 4 years ago
Last modified 4 years ago
#2010 new defect
Proxy protocol headers from stream module reported as broken by http module
Reported by: | Owned by: | ||
---|---|---|---|
Priority: | minor | Milestone: | |
Component: | nginx-core | Version: | 1.19.x |
Keywords: | Cc: | ||
uname -a: | Linux nameredacted 4.15.0-108-generic #109-Ubuntu SMP Fri Jun 19 11:33:10 UTC 2020 x86_64 x86_64 x86_64 GNU/Linux | ||
nginx -V: |
nginx version: nginx/1.19.0
built by gcc 7.5.0 (Ubuntu 7.5.0-3ubuntu1~18.04) built with OpenSSL 1.1.1 11 Sep 2018 TLS SNI support enabled configure arguments: --http-client-body-temp-path=cache/client_temp --http-proxy-temp-path=cache/proxy_temp --http-fastcgi-temp-path=cache/fastcgi_temp --http-uwsgi-temp-path=cache/uwsgi_temp --http-scgi-temp-path=cache/scgi_temp --user=albert.aribaud --group=albert.aribaud --with-compat --with-file-aio --with-threads --with-http_addition_module --with-http_auth_request_module --with-http_dav_module --with-http_flv_module --with-http_gunzip_module --with-http_gzip_static_module --with-http_mp4_module --with-http_random_index_module --with-http_realip_module --with-http_secure_link_module --with-http_slice_module --with-http_ssl_module --with-http_stub_status_module --with-http_sub_module --with-http_v2_module --with-mail --with-mail_ssl_module --with-stream --with-stream_realip_module --with-stream_ssl_module --with-stream_ssl_preread_module --with-cc-opt='-g -O2 -fstack-protector-strong -Wformat -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2 -fPIC' --with-ld-opt='-Wl,-z,relro -Wl,-z,now -Wl,--as-needed -pie' |
Description
Using a NGINX configuration where:
- a stream server listens on 127.0.0.1:8080, enables proxy protocol, and proxies to socket temp.sock;
- a stream server listens on socket temp.sock with proxy protocol enabled, keeps proxy protocol enabled and proxies to 127.0.0.2:8080;
- a http server listens on port 127.0.0.2:8080 with proxy protocol enabled, serving a static website with a single index.html file at the root;
Attempts to fetch "http://127.0.0.1:8080/" result in the connection getting closed without any response, and the error log indicating the following:
2020/06/30 16:40:50 [error] 5688#5688: *15 broken header: "PROXY TCP4 127.0.0.1 unix:/path/redacted/temp.sock 52726 0
GET / HTTP/1.1
Host: 127.0.0.1:8080
User-Agent: HTTPie/0.9.8
Accept-Encoding: gzip, deflate
Accept: */*
Connection: keep-alive
" while reading PROXY protocol, client: 127.0.0.1, server: 127.0.0.2:8080
Tested with the NGINX git tree, commits be932e81 (works as expected) and 20389850 (breaks as above) as well as tags release-1.16.1 (works), release-1.80.0 (breaks) and release-1.19.0 (breaks).
Change History (2)
comment:1 by , 4 years ago
comment:2 by , 4 years ago
Thank you!
That's exactly this. I do indeed use realip, and switching from sockets to TCP ports did solve the issue.
I assume you also have the realip module enabled in your second server to pass the original client address. It's an IPv4 address. The PROXY protocol header created by this server contains this IPv4 address as source and UNIX address as destination. Addresses of different families are not supported by the PROXY protocol. This PROXY protocol header is technically incorrect and triggers parse error in the third server.
Prior to version 1.17.6, nginx only parsed the client address from the PROXY protocol header and ignored the server address. This is why incorrect values passed as the server address previously produced no error.
The realip module substitutes client address. Currently there's no way to do that for the server address too, which would solve the issue.
The easiest solution now is to switch from unix domain listen to a TCP listen.