Since you cannot convert IPv6 addresses to integer, you should operate bits, like this:
$ip='21DA:00D3:0000:2F3B:02AC:00FF:FE28:9C5A';
$cidrnet='21DA:00D3:0000:2F3B::/64';
// converts inet_pton output to string with bits
function inet_to_bits($inet)
{
$splitted = str_split($inet);
$binaryip = '';
foreach ($splitted as $char) {
$binaryip .= str_pad(decbin(ord($char)), 8, '0', STR_PAD_LEFT);
}
return $binaryip;
}
$ip = inet_pton($ip);
$binaryip=inet_to_bits($ip);
list($net,$maskbits)=explode('/',$cidrnet);
$net=inet_pton($net);
$binarynet=inet_to_bits($net);
$ip_net_bits=substr($binaryip,0,$maskbits);
$net_bits =substr($binarynet,0,$maskbits);
if($ip_net_bits!==$net_bits) echo 'Not in subnet';
else echo 'In subnet';
Also, if you use some database to store IPs, it may already have all the functions to compare them. For example, Postgres has an inet type and can determine, whether IP is contained within subnet like this:
SELECT
'21DA:00D3:0000:2F3B:02AC:00FF:FE28:9C5A'::inet <<
'21DA:00D3:0000:2F3B::/64'::inet;
9.11. Network Address Functions and Operators in PostgreSQL
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…