From 7b076048688ddd20fc698d19e1921155de8c48e5 Mon Sep 17 00:00:00 2001 From: Christian A. Weber Date: Mon, 1 Feb 2016 15:42:04 +0100 Subject: add support for arrays of cidrs in cidr_match() --- it.class | 25 ++++++++++++++++--------- tests/it.t | 1 + 2 files changed, 17 insertions(+), 9 deletions(-) diff --git a/it.class b/it.class index cfad675..b533c3f 100644 --- a/it.class +++ b/it.class @@ -317,18 +317,25 @@ static function toascii($text) /** * Check whether an IP adress lies within a given range. Supports IPv4 and IPv6 * @param $ip IP address (192.168.42.123) - * @param $cidr IP range in CIDR notation (192.168.42.64/26) + * @param $cidrs IP range in CIDR notation (192.168.42.64/26) or array of ranges * @return true if $ip is within $cidr */ -function cidr_match($ip, $cidr) +function cidr_match($ip, $cidrs) { - list($subnet, $mask) = explode('/', $cidr); - $ip_bin = inet_pton($ip); - $subnet_bin = inet_pton($subnet); - $valid_bytes = $mask ? $mask >> 3 : 42; - $bitmask = 256 - (1 << (8 - ($mask & 7))); - $lastbyte_matched = $bitmask ? (ord($ip_bin{$valid_bytes}) & $bitmask) == (ord($subnet_bin{$valid_bytes}) & $bitmask) : true; - return substr($ip_bin, 0, $valid_bytes) == substr($subnet_bin, 0, $valid_bytes) && $lastbyte_matched; + foreach ((array)$cidrs as $cidr) + { + list($subnet, $mask) = explode('/', $cidr); + $ip_bin = inet_pton($ip); + $subnet_bin = inet_pton($subnet); + $valid_bytes = $mask ? $mask >> 3 : 42; + $bitmask = 256 - (1 << (8 - ($mask & 7))); + $lastbyte_matched = $bitmask ? (ord($ip_bin{$valid_bytes}) & $bitmask) == (ord($subnet_bin{$valid_bytes}) & $bitmask) : true; + + if (substr($ip_bin, 0, $valid_bytes) == substr($subnet_bin, 0, $valid_bytes) && $lastbyte_matched) + return true; + } + + return false; } diff --git a/tests/it.t b/tests/it.t index 74ac57a..4fd848b 100755 --- a/tests/it.t +++ b/tests/it.t @@ -327,6 +327,7 @@ is(it::cidr_match('192.168.42.42', '192.168.42.64/26'), false, "cidr_match o is(it::cidr_match('192.168.42.42', '192.168.42.32/27'), true, "cidr_match offset"); is(it::cidr_match('2001:918:ff83:101:798e:77c0:b722:fe56', '2001:918:ff83:101::/64'), true, "cidr_match ipv6"); is(it::cidr_match('2001:918:ff83:102:798e:77c0:b722:fe56', '2001:918:ff83:101::/64'), false, "cidr_match ipv6 no match" ); +is(it::cidr_match('10.11.12.13', array('10.0.0.0/8', '192.168.0.0./16')), true, "cidr_match array"); # it::filter_keys tests -- cgit v1.2.3