true_atlantis has asked for the wisdom of the Perl Monks concerning the following question:

When running this command line for Net::IP, I get an error

perl -e 'use Net::IP; my $x=new Net::IP("172.24.43.226/27") or die(Net::IP::Error()); '
Invalid prefix 10101100000110000010101111100010/28 at -e line 1.

Why does this occur. If another module is suggested, I'm using Net::IP to detrmine if an IP address intersects/includes/overlaps (whatever terminology you want to use) an cidr/range/or ip
thanks

Replies are listed 'Best First'.
Re: Net::IP Invalid Prefix?
by ikegami (Patriarch) on Oct 31, 2007 at 01:26 UTC
    Like the message says, 172.24.43.226 is not a /27 prefix.
    172.24.43.226 -> 10101100.00011000.00101011.11100010
    /27           -> 11111111.11111111.11111111.11100000
                                                   00010   <-- Error!
    
Re: Net::IP Invalid Prefix?
by apl (Monsignor) on Oct 31, 2007 at 10:04 UTC
    IP addresses are composed of four decimal numbers separated by periods. If I had to guess, someone was asking you to look at either 172.24.43.226 or 172.24.43.227 .

      "172.24.43.226/27" means "the subnet starting at 172.24.43.226 with a mask of 27 bits (255.255.255.224)". It doesn't mean "172.24.43.226 or 172.24.43.227". There error means that given a mask of 27 bits, 172.24.43.226 is not the start of a subnet.

Re: Net::IP Invalid Prefix?
by shmem (Chancellor) on Oct 31, 2007 at 10:08 UTC
    qwurx [shmem] ~ > perl - 172.24.43.226/27 $m=pack B32,pop=~'/'x$';printf"$` net %vd bc %vd mask %vd\n",($z=eval$ +`)&$m,$z|~$m,$m __END__ 172.24.43.226 net 172.24.43.224 bc 172.24.43.255 mask 255.255.255.224

    "valid prefix" is indeed the network address - 172.24.43.224.

    <update>

    Skimming Net::IP I didn't find a function which returns network and broadcast addresses given an arbitrary IP address in CIDR notation. I'd do the following for IP v4 addresses

    sub get_boundaries { my ($ip, $bits) = split /\//, $_[0]; my $b_ip = pack "C4", split /\./, $ip; my $b_mask = pack "B32", 1 x $bits; my $b_net = $b_ip & $b_mask; my $b_bcast = $b_ip | ~ $b_mask; unpack("N", $b_net), unpack("N", $b_bcast); }

    which returns the network and broadcast addresses as 32 bit integers, being the lower and upper limit of a range to test other IP addresses against (after having converted them to integers, of course).

    sub in_range { my ($cidr, $ip) = @_; my ($low, $high) = get_boundaries($cidr); my $i_ip = unpack "N", pack "C4", split /\./, $ip; $i_ip > $low && $i_ip < $high; } print "yup\n" if in_range("172.24.43.226/27", "172.24.43.236");

    </update>

    --shmem

    _($_=" "x(1<<5)."?\n".q·/)Oo.  G°\        /
                                  /\_¯/(q    /
    ----------------------------  \__(m.====·.(_("always off the crowd"))."·
    ");sub _{s./.($e="'Itrs `mnsgdq Gdbj O`qkdq")=~y/"-y/#-z/;$e.e && print}