Opened 8 years ago

Last modified 8 years ago

#1025 new enhancement

No country detected for requests with X-Forwarded-For 127.0.0.1 or any reserved IP address

Reported by: romamo@… Owned by:
Priority: minor Milestone:
Component: nginx-module Version: 1.10.x
Keywords: ngx_http_geoip_module, geoip Cc:
uname -a: FreeBSD test 9.3-RELEASE FreeBSD 9.3-RELEASE #0: Tue Nov 3 13:52:37 UTC 2015 /usr/obj/usr/src/sys/EX4RVM91 amd64
nginx -V: nginx version: nginx/1.10.1
configure arguments: --prefix=/usr/local/etc/nginx --with-cc-opt='-I /usr/local/include' --with-ld-opt='-L /usr/local/lib' --conf-path=/usr/local/etc/nginx/nginx.conf --sbin-path=/usr/local/sbin/nginx --pid-path=/var/run/nginx.pid --error-log-path=/var/log/nginx-error.log --user=www --group=www --modules-path=/usr/local/libexec/nginx --with-file-aio --http-client-body-temp-path=/var/tmp/nginx/client_body_temp --http-fastcgi-temp-path=/var/tmp/nginx/fastcgi_temp --http-proxy-temp-path=/var/tmp/nginx/proxy_temp --http-scgi-temp-path=/var/tmp/nginx/scgi_temp --http-uwsgi-temp-path=/var/tmp/nginx/uwsgi_temp --http-log-path=/var/log/nginx-access.log --with-http_geoip_module=dynamic --with-http_gzip_static_module --with-http_image_filter_module=dynamic --add-module=/usr/ports/www/nginx/work/ngx_http_substitutions_filter_module-0.6.4 --with-http_stub_status_module --with-pcre

Description

I use ngx_http_geoip_module to detect origin country of every request including requests behind public proxy servers.

geoip_country /usr/local/etc/nginx/geobase/GeoIP-106_20160712.dat;
geoip_proxy_recursive on; # Use X-Forwarded-For
geoip_proxy 0.0.0.0/0;

if X-Forwarded-For header contains IP address from reserved range https://en.wikipedia.org/wiki/Reserved_IP_addresses

$geoip_country_code is empty ""

For example: X-Forwarded-For: 127.0.0.1

GeoIP database has empty values for these IP ranges.
GeoIP2 database has no values.

I think nginx_geoip module must query geoip database again using REMOTE_ADDR if no country value received using X-Forwarded-For value.

How to repeat
test.php

<?
var_dump($_SERVER['HTTP_X_FORWARDED_FOR']);
var_dump($_SERVER['GEOIP_COUNTRY']);
?>
curl --header "X-Forwarded-For: 127.0.0.1" http://localhost/test.php

Alternative solution may be put all valid IP ranges into geoip_proxy like
geoip_proxy 1.0.0.0/8;
geoip_proxy 2.0.0.0/7;
4.0.0.0/6
8.0.0.0/7
11.0.0.0/8
12.0.0.0/6
16.0.0.0/4
32.0.0.0/3
64.0.0.0/3
96.0.0.0/6
100.0.0.0/10
100.128.0.0/9
101.0.0.0/8
102.0.0.0/7
104.0.0.0/5
112.0.0.0/5
120.0.0.0/6
124.0.0.0/7
126.0.0.0/8
128.0.0.0/1
but it may lower performance.

Change History (2)

comment:1 by romamo@…, 8 years ago

Sorry Alternative solution is not correct and does not solve the problem.

comment:2 by Maxim Dounin, 8 years ago

Type: defectenhancement

It looks like you are asking for something similar to GeoIPUseFirstNonPrivateXForwardedForIP in MaxMind's mod_geoip2.

This is not something nginx can do now. Currently, general concept is to only trust explicitly configured proxies, and if a proxy returns an address - provide information for this address whether we know something about the address or not. This approach is much more secure as it doesn't allow users to provide arbitrary addresses nginx will blindly trust, but this may be too strict for just geoinformation.

Changing this to "enhancement" as current behaviour is intended and certainly not a bug, though we may want to introduce different behaviour to simplify providing "best case" geoinformation.

Note: See TracTickets for help on using tickets.