php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #61700 FILTER_FLAG_IPV6, FILTER_FLAG_NO_PRIV_RANGE, FILTER_FLAG_NO_RES_RANGE failing
Submitted: 2012-04-12 13:14 UTC Modified: 2018-10-11 20:51 UTC
Votes:12
Avg. Score:4.6 ± 0.9
Reproduced:11 of 11 (100.0%)
Same Version:4 (36.4%)
Same OS:1 (9.1%)
From: nanocaiordo at gmail dot com Assigned:
Status: Verified Package: Filter related
PHP Version: 7.2.11 OS:
Private report: No CVE-ID: None
Have you experienced this issue?
Rate the importance of this bug to you:

 [2012-04-12 13:14 UTC] nanocaiordo at gmail dot com
Description:
------------
FILTER_FLAG_NO_PRIV_RANGE and FILTER_FLAG_NO_RES_RANGE failing in some circumstances

Test script:
---------------
var_dump(filter_var('::ffff:192.168.1.1', FILTER_VALIDATE_IP, FILTER_FLAG_IPV4));
var_dump(filter_var('::ffff:192.168.1.1', FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE));
var_dump(filter_var('0:0:0:0:0:0:0:1', FILTER_VALIDATE_IP, FILTER_FLAG_NO_RES_RANGE));



Expected result:
----------------
bool(true) ?
bool(false)
bool(false) as ::1 does?

Actual result:
--------------
bool(false)
string(18) "::ffff:192.168.1.1"
string(15) "0:0:0:0:0:0:0:1"

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2012-05-18 10:25 UTC] bramklg at gmail dot com
The FILTER_FLAG_NO_RES_RANGE flag only works in a couple of cases (verified 
against ext\filter\logical_filters.c from the php 5.3 snapshot of 2012-05-18).

Its missing almost all of the ranges described in 
http://en.wikipedia.org/wiki/Reserved_IP_addresses and 
http://tools.ietf.org/html/rfc5156.

This is also discussed in the following bugreport: https://bugs.php.net/bug.php?
id=47435 but nothing is done with it?
 [2013-03-11 18:25 UTC] bugreport at zippymail dot info
Hellon

The problem is still present, even on newer version.

Can you fix please ?

Thanks.
 [2014-04-12 12:41 UTC] klunejko at gmail dot com
FILTER_FLAG_NO_RES_RANGE also has some false positives, it sees 128.0.96.0/21 as a reserved, when it's not. This is happening in PHP 5.5
 [2018-10-11 19:16 UTC] eric at ericstern dot com
Any chance we can look into this further? It's been open and verified for over six years (I encountered it on 7.2.8), and has the potential to lead to security issues if code is relying on the accuracy of this filter to e.g. prevent malicious redirects to localhost. There are a _lot_ of ways to write an IPv6 address that equates to ::1, and this filter only appears to catch one of them.
 [2018-10-11 20:51 UTC] requinix@php.net
-Status: Open +Status: Verified -PHP Version: 5.3.10 +PHP Version: 7.2.11
 [2018-10-11 20:51 UTC] requinix@php.net
Given how many notations and short-hands there are, the only real way to validate IPv6 is to inet_pton it (which requires IPv6 support) and check the octets.

PHP doesn't do that. It looks at the input string directly. The checks are self-explanatory.
https://github.com/php/php-src/blob/PHP-7.2.11/ext/filter/logical_filters.c#L811

Note that the address must be mostly normalized beforehand (so no 0:0:0:0:0:0:0:1) yet some of the leading zeroes are required (2001:0010:: is excluded but 2001:10:: is not).

https://3v4l.org/MHERV

Regarding the original report, the first example should return false as the input was not a valid IPv4 address - the dotted notation has no technical significance and is only a convenience for humans to read. It's an IPv6 address that happens to map onto the IPv4 space.

The second example is debatable, considering that the address is IPv6 and not in the IPv6 private range, but I think it's very reasonable to say it should fail because the address explicitly corresponds to an IPv4 address which *is* private.

(Why should the first not be valid IPv4 but the second be treated as such? The IPV4/IPV6 flags test syntax and general usability, and a system that does not support IPv6 is not going to know to support a mapped address. I'm skeptical this format is used much in the wild anyways.)

Third example, of course, should not pass.
 
PHP Copyright © 2001-2019 The PHP Group
All rights reserved.
Last updated: Mon Aug 19 12:01:26 2019 UTC