# convert {start_ip, end_ip} into prefix notation # # Tatsuya Mori def inet_aton ip ip.split(/\./).map{|c| c.to_i}.pack("C*").unpack("N").first end def inet_ntoa n [n].pack("N").unpack("C4").join(".") end def get_forward_prefixes(s,e) prefixes = [] while s <= e len = 32 - ((Math.log(e - s + 1) / Math.log(2)).to_i).floor prefixes << "#{inet_ntoa(s)}/#{len}" s = s + 2 ** (32 - len) end return prefixes end def get_backward_prefixes(s,e) prefixes = [] while s <= e len = 32 - ((Math.log(e - s + 1) / Math.log(2)).to_i).floor prefix = inet_ntoa(e - 2 ** (32 - len) + 1) prefixes << "#{prefix}/#{len}" e = e - 2 ** (32 - len) end return prefixes.reverse end def get_prefixes(s, e) return [] if e < s prefixes = [] if (s & 0x000000ff == 0) prefixes = get_forward_prefixes(s,e) else if (e & 0xffffff00) > (s & 0xffffff00) prefixes = get_backward_prefixes(s, (e & 0xffffff00) - 1) + get_forward_prefixes(e & 0xffffff00, e) else l = e - s + 1 base = s & 0xffffff00 width = 2 ** ((Math.log(l) / Math.log(2)).to_i.floor - 1) i = 0 while i < (s & 0x000000ff) i += width end prefixes = get_backward_prefixes(s, base + i - 1) + get_forward_prefixes(base + i, e) end end return prefixes end start_ip = (ARGV[0] || "192.168.5.0") end_ip = (ARGV[1] || "192.168.5.254") puts "#{start_ip} - #{end_ip}" puts "---" puts get_prefixes(inet_aton(start_ip),inet_aton(end_ip)).join("\n")