IP アドレス範囲 (CIDR 表記) があり、任意の IP アドレスがその範囲内にあるかどうかを知る必要がある場合 (両方とも文字列として表示)、C# でこれを行う最も簡単な方法は何ですか?
例:
- IPv4 範囲:
192.168.168.100/24
、確認する IP:192.168.168.200
- IPv6 範囲:
fe80::202:b3ff:fe1e:8329/24
、確認する IP:2001:db8::
簡単なクラスを次に示します。
public class IPSubnet
{
private readonly byte[] _address;
private readonly int _prefixLength;
public IPSubnet(string value)
{
if (value == null)
throw new ArgumentNullException("value");
string[] parts = value.Split('/');
if (parts.Length != 2)
throw new ArgumentException("Invalid CIDR notation.", "value");
_address = IPAddress.Parse(parts[0]).GetAddressBytes();
_prefixLength = Convert.ToInt32(parts[1], 10);
}
public bool Contains(string address)
{
return this.Contains(IPAddress.Parse(address).GetAddressBytes());
}
public bool Contains(byte[] address)
{
if (address == null)
throw new ArgumentNullException("address");
if (address.Length != _address.Length)
return false; // IPv4/IPv6 mismatch
int index = 0;
int bits = _prefixLength;
for (; bits >= 8; bits -= 8)
{
if (address[index] != _address[index])
return false;
++index;
}
if (bits > 0)
{
int mask = (byte)~(255 >> bits);
if ((address[index] & mask) != (_address[index] & mask))
return false;
}
return true;
}
}
使用例:
Console.WriteLine(new IPSubnet("192.168.168.100/24").Contains("192.168.168.200")); // True
Console.WriteLine(new IPSubnet("fe80::202:b3ff:fe1e:8329/24").Contains("2001:db8::")); // False
このクラスは、すべての IPv4 アドレスをすべての IPv6 アドレスとは異なるものとして扱い、IPv4 と IPv6 の間で変換を試みません。
私はあなたのためにコードを書くつもりはありませんが:
あなたが始めるのに十分なはずです。
幸運を