274 lines
No EOL
11 KiB
C#
274 lines
No EOL
11 KiB
C#
using Insight.Agent.Interfaces;
|
|
using Insight.Agent.Messages;
|
|
using System.Management;
|
|
using System.Net;
|
|
using System.Net.NetworkInformation;
|
|
using System.Runtime.InteropServices;
|
|
using System.Runtime.Versioning;
|
|
using Route = Insight.Agent.Messages.Route;
|
|
|
|
namespace Insight.Agent.Network.Handlers
|
|
{
|
|
[SupportedOSPlatform("windows")]
|
|
public class InterfaceHandler : IAgentMessageHandler<AgentSession>
|
|
{
|
|
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IAgentMessage
|
|
{
|
|
if (message is GetInventory)
|
|
{
|
|
var result = new InterfaceList();
|
|
result.AddRange(GetInterfaces());
|
|
|
|
await sender.SendAsync(result, cancellationToken);
|
|
}
|
|
}
|
|
|
|
private static List<Interface> GetInterfaces()
|
|
{
|
|
if (NetworkInterface.GetIsNetworkAvailable() is false) return null;
|
|
if (NetworkInterface.GetAllNetworkInterfaces().Any() is false) return null;
|
|
|
|
var interfaces = new List<Interface>();
|
|
|
|
foreach (var ni in NetworkInterface.GetAllNetworkInterfaces())
|
|
{
|
|
var ipProperties = ni.GetIPProperties();
|
|
var ipStatistics = ni.GetIPStatistics();
|
|
|
|
var @interface = new Interface
|
|
{
|
|
Mac = ni.GetPhysicalAddress().ToString(),
|
|
Name = ni.Name,
|
|
Description = ni.Description,
|
|
Type = ni.NetworkInterfaceType,
|
|
Speed = ni.Speed,
|
|
Status = ni.OperationalStatus,
|
|
Suffix = ipProperties.DnsSuffix,
|
|
Sent = ipStatistics.BytesSent,
|
|
Received = ipStatistics.BytesReceived,
|
|
IncomingPacketsDiscarded = ipStatistics.IncomingPacketsDiscarded,
|
|
IncomingPacketsWithErrors = ipStatistics.IncomingPacketsWithErrors,
|
|
IncomingUnknownProtocolPackets = ipStatistics.IncomingUnknownProtocolPackets,
|
|
OutgoingPacketsDiscarded = ipStatistics.OutgoingPacketsDiscarded,
|
|
OutgoingPacketsWithErrors = ipStatistics.OutgoingPacketsWithErrors
|
|
};
|
|
|
|
try
|
|
{
|
|
var propertiesV4 = ipProperties.GetIPv4Properties();
|
|
@interface.Index = uint.Parse(propertiesV4.Index.ToString());
|
|
@interface.Ipv4Mtu = propertiesV4.Mtu;
|
|
@interface.Ipv4Dhcp = propertiesV4.IsDhcpEnabled;
|
|
@interface.Ipv4Forwarding = propertiesV4.IsForwardingEnabled;
|
|
}
|
|
catch (Exception) { }
|
|
|
|
try
|
|
{
|
|
var propertiesV6 = ipProperties.GetIPv6Properties();
|
|
@interface.Index = uint.Parse(propertiesV6.Index.ToString());
|
|
@interface.Ipv6Mtu = propertiesV6.Mtu;
|
|
}
|
|
catch (Exception) { }
|
|
|
|
@interface.Gateways = GetAddresses(ipProperties.GatewayAddresses);
|
|
@interface.Addresses = GetAddresses(ipProperties.UnicastAddresses);
|
|
@interface.Dns = GetAddresses(ipProperties.DnsAddresses);
|
|
@interface.Dhcp = GetAddresses(ipProperties.DhcpServerAddresses);
|
|
|
|
if (@interface.Index.HasValue)
|
|
{
|
|
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
|
|
{
|
|
using var searcher = new ManagementObjectSearcher
|
|
{
|
|
Scope = new ManagementScope(@"root\cimv2"),
|
|
Query = new ObjectQuery($"select interfaceindex, guid, physicaladapter, manufacturer from win32_networkadapter where interfaceindex = {@interface.Index}")
|
|
};
|
|
|
|
if (searcher.TryGet(out var collection) is false)
|
|
{
|
|
searcher.Query = new ObjectQuery($"select * from win32_networkadapter where interfaceindex = {@interface.Index}");
|
|
|
|
if (searcher.TryGet(out collection) is false) throw new InvalidOperationException("WMI Collection NULL");
|
|
}
|
|
|
|
using (collection)
|
|
{
|
|
foreach (ManagementObject @object in collection)
|
|
{
|
|
var properties = @object.GetPropertyHashes();
|
|
|
|
@interface.Manufacturer = @object.GetValue<string>(properties, "manufacturer")?.Trim();
|
|
@interface.Guid = @object.GetValue<Guid>(properties, "guid");
|
|
@interface.Physical = @object.GetValue<bool>(properties, "physicaladapter");
|
|
|
|
break;
|
|
}
|
|
}
|
|
|
|
@interface.Routes = QueryInterfaceRoutes(@interface.Index.Value);
|
|
}
|
|
}
|
|
|
|
interfaces.Add(@interface);
|
|
}
|
|
|
|
return interfaces;
|
|
}
|
|
|
|
private static List<Route> QueryInterfaceRoutes(uint interfaceIndex)
|
|
{
|
|
using var searcher = new ManagementObjectSearcher
|
|
{
|
|
Scope = new ManagementScope(@"root\standardcimv2"),
|
|
Query = new ObjectQuery($"select addressFamily, state, interfaceindex, routemetric, nexthop, destinationprefix from msft_netroute where interfaceindex = {interfaceIndex}")
|
|
};
|
|
|
|
if (searcher.TryGet(out var collection) is false)
|
|
{
|
|
searcher.Query = new ObjectQuery($"select * from msft_netroute where interfaceindex = {interfaceIndex}");
|
|
|
|
if (searcher.TryGet(out collection) is false) throw new InvalidOperationException("WMI Collection NULL");
|
|
}
|
|
|
|
var routes = new List<Route>();
|
|
|
|
using (collection)
|
|
{
|
|
foreach (var @object in collection)
|
|
{
|
|
var route = new Route
|
|
{
|
|
InterfaceIndex = interfaceIndex
|
|
};
|
|
|
|
var properties = @object.GetPropertyHashes();
|
|
|
|
if (@object.TryGetValue<object>(properties, "routemetric", out var routemetric))
|
|
{
|
|
if (int.TryParse(routemetric?.ToString(), out var metric)) route.Metric = metric;
|
|
}
|
|
|
|
if (@object.TryGetValue<object>(properties, "nexthop", out var nexthop))
|
|
{
|
|
if (IPAddress.TryParse(nexthop?.ToString(), out var gateway)) route.Gateway = new IPAddress2(gateway);
|
|
}
|
|
|
|
if (@object.TryGetValue<object>(properties, "destinationprefix", out var destinationprefix))
|
|
{
|
|
var split = destinationprefix?.ToString()?.Split('/');
|
|
var cidrData = split?[1];
|
|
|
|
if (IPAddress.TryParse(split?[0], out var destination))
|
|
route.Destination = new IPAddress2(destination);
|
|
|
|
if (int.TryParse(cidrData, out var cidr))
|
|
{
|
|
var mask = ConvertCidr(cidr);
|
|
route.Mask = mask;
|
|
}
|
|
}
|
|
|
|
routes.Add(route);
|
|
}
|
|
}
|
|
|
|
return routes;
|
|
}
|
|
|
|
private static List<Unicast> GetAddresses(UnicastIPAddressInformationCollection unicastCollection)
|
|
{
|
|
var addresses = new List<Unicast>();
|
|
|
|
if (unicastCollection.Any() is false) return addresses;
|
|
|
|
foreach (var unicast in unicastCollection)
|
|
{
|
|
addresses.Add(new Unicast
|
|
{
|
|
IpAddress = new IPAddress2(unicast.Address),
|
|
AddressPreferredLifetime = unicast.AddressPreferredLifetime,
|
|
AddressValidLifetime = unicast.AddressValidLifetime,
|
|
DuplicateAddressDetectionState = unicast.DuplicateAddressDetectionState,
|
|
Ipv4Mask = new IPAddress2(unicast.IPv4Mask),
|
|
PrefixLength = unicast.PrefixLength,
|
|
PrefixOrigin = unicast.PrefixOrigin,
|
|
SuffixOrigin = unicast.SuffixOrigin,
|
|
DhcpLeaseLifetime = unicast.DhcpLeaseLifetime,
|
|
});
|
|
}
|
|
|
|
return addresses;
|
|
}
|
|
|
|
private static List<IPAddress2> GetAddresses(IPAddressCollection addressCollection)
|
|
{
|
|
var addresses = new List<IPAddress2>();
|
|
|
|
if (addressCollection.Any() is false) return addresses;
|
|
|
|
foreach (var address in addressCollection)
|
|
{
|
|
addresses.Add(new IPAddress2(address));
|
|
}
|
|
|
|
return addresses;
|
|
}
|
|
|
|
private static List<IPAddress2> GetAddresses(GatewayIPAddressInformationCollection addressCollection)
|
|
{
|
|
var addresses = new List<IPAddress2>();
|
|
|
|
if (addressCollection.Any() is false) return addresses;
|
|
|
|
foreach (var address in addressCollection)
|
|
{
|
|
addresses.Add(new IPAddress2(address.Address));
|
|
}
|
|
|
|
return addresses;
|
|
}
|
|
|
|
private static string? ConvertCidr(int cidr)
|
|
{
|
|
return cidr switch
|
|
{
|
|
0 => "0.0.0.0",
|
|
1 => "128.0.0.0",
|
|
2 => "192.0.0.0",
|
|
3 => "224.0.0.0",
|
|
4 => "240.0.0.0",
|
|
5 => "248.0.0.0",
|
|
6 => "252.0.0.0",
|
|
7 => "254.0.0.0",
|
|
8 => "255.0.0.0",
|
|
9 => "255.128.0.0",
|
|
10 => "255.192.0.0",
|
|
11 => "255.224.0.0",
|
|
12 => "255.240.0.0",
|
|
13 => "255.248.0.0",
|
|
14 => "255.252.0.0",
|
|
15 => "255.254.0.0",
|
|
16 => "255.255.0.0",
|
|
17 => "255.255.128.0",
|
|
18 => "255.255.192.0",
|
|
19 => "255.255.224.0",
|
|
20 => "255.255.240.0",
|
|
21 => "255.255.248.0",
|
|
22 => "255.255.252.0",
|
|
23 => "255.255.254.0",
|
|
24 => "255.255.255.0",
|
|
25 => "255.255.255.128",
|
|
26 => "255.255.255.192",
|
|
27 => "255.255.255.224",
|
|
28 => "255.255.255.240",
|
|
29 => "255.255.255.248",
|
|
30 => "255.255.255.252",
|
|
31 => "255.255.255.254",
|
|
32 => "255.255.255.255",
|
|
_ => null,
|
|
};
|
|
}
|
|
}
|
|
} |