1 借助System.Net.NetworkInformation.NetworkInterface 作为切入点获取所有的网卡接口
2 通过NetworkInterface.OperationalStatus 状态判断是否可以传送包
3 通过NetworkInterface.NetworkInterfaceType 判断网卡类型
4 通过UnicastIPAddressInformation.Address 和 UnicastIPAddressInformation.IPv4Mask 计算局域网的所有IP
具体代码如下:
using System.Collections.Generic;
using System.Net;
using System.Net.NetworkInformation;
using System.Net.Sockets;
namespace Utils
{
/// <summary>
/// 子网IP范围查询
/// </summary>
public static class SubNetIps
{
/// <summary>
/// 获取所有IP网段
/// </summary>
/// <returns></returns>
public static List<IpRange> GetIpRanges()
{
var ranges = new List<IpRange>();
foreach (NetworkInterface netInterface in NetworkInterface.GetAllNetworkInterfaces())
{
var ipProps = GetIpInterfaceProperties(netInterface);
if (ipProps == null) continue;
foreach (var addressInfo in ipProps.UnicastAddresses)
{
//忽略非IP4的地址
if (addressInfo.Address.AddressFamily != AddressFamily.InterNetwork) continue;
var lowestAddress = GetLowestIp(addressInfo.Address, addressInfo.IPv4Mask);
var highestAddress = GetHighestIp(addressInfo.Address, addressInfo.IPv4Mask);
ranges.Add(new IpRange(lowestAddress, highestAddress));
}
}
return ranges;
}
/// <summary>
/// 获取匹配远方的本地
/// </summary>
/// <returns></returns>
public static IPAddress GetLocalIpByRemoteAddress(IPAddress remoteAddress)
{
foreach (NetworkInterface netInterface in NetworkInterface.GetAllNetworkInterfaces())
{
var ipProps = GetIpInterfaceProperties(netInterface);
if (ipProps == null) continue;
foreach (var addressInfo in ipProps.UnicastAddresses)
{
//忽略非IP4的地址
if (addressInfo.Address.AddressFamily != AddressFamily.InterNetwork) continue;
var lowestAddress = GetLowestIp(addressInfo.Address, addressInfo.IPv4Mask);
var highestAddress = GetHighestIp(addressInfo.Address, addressInfo.IPv4Mask);
if (IsBetween(remoteAddress, lowestAddress, highestAddress)) return addressInfo.Address;
}
}
return default(IPAddress);
}
/// <summary>
/// 获取局域网以及能够上网的网卡信息
/// </summary>
/// <param name="netInterface"></param>
/// <returns></returns>
private static IPInterfaceProperties GetIpInterfaceProperties(NetworkInterface netInterface)
{
IPInterfaceProperties ipProps = null;
if (netInterface.OperationalStatus != OperationalStatus.Up) return null;
ipProps = netInterface.GetIPProperties();
if (netInterface.NetworkInterfaceType != NetworkInterfaceType.Wireless80211)
{
//忽略默认网关地址为空的适配器
var dhcpServerAddresses = ipProps.DhcpServerAddresses;
if (dhcpServerAddresses.Count == 0)
ipProps = null;
}
return ipProps;
}
private static bool IsBetween(IPAddress ipAddress, IPAddress startIP, IPAddress endIP)
{
var startBytes = startIP.GetAddressBytes();
var endBytes = endIP.GetAddressBytes();
var targetBytes = ipAddress.GetAddressBytes();
if (startBytes.Length != targetBytes.Length || endBytes.Length != targetBytes.Length) return false;
bool isBetween = true;
for (int i = 0; i < startBytes.Length; i++)
{
if (startBytes[i] > targetBytes[i] || endBytes[i] < targetBytes[i])
{
isBetween = false;
break;
}
}
return isBetween;
}
private static IPAddress GetLowestIp(IPAddress address, IPAddress mask)
{
byte[] addressBytes = address.GetAddressBytes();
byte[] maskBytes = mask.GetAddressBytes();
if (addressBytes.Length != 4 || maskBytes.Length != 4)
return IPAddress.None;
byte[] lowest = new byte[4];
for (var i = 0; i < 4; i++)
lowest[i] = (byte)(addressBytes[i] & maskBytes[i]);
return new IPAddress(lowest);
}
private static IPAddress GetHighestIp(IPAddress address, IPAddress mask)
{
byte[] addressBytes = address.GetAddressBytes();
byte[] maskBytes = mask.GetAddressBytes();
if (addressBytes.Length != 4 || maskBytes.Length != 4)
return IPAddress.None;
byte[] highest = new byte[4];
for (var i = 0; i < 4; i++)
highest[i] = (byte)((addressBytes[i] & maskBytes[i]) | ~maskBytes[i]);
return new IPAddress(highest);
}
}
public class IpRange
{
/// <summary>
/// 最小动态IP
/// </summary>
public IPAddress LowestAddress { get; }
/// <summary>
/// 最大可分配动态IP
/// </summary>
public IPAddress HighestAddress { get; }
public IpRange(IPAddress lowestAddress, IPAddress highestAddress)
{
LowestAddress = lowestAddress;
HighestAddress = highestAddress;
}
}
}