Battery, BIOS, CPU - processor, storage drive, keyboard, RAM - memory, monitor, motherboard, mouse, NIC - network adapter, printer, sound card - audio card, graphics card - video card. Hardware.Info is a .NET Standard 2.0 library and uses WMI on Windows, /dev, /proc, /sys on Linux and sysctl, system_profiler on macOS.
Battery, BIOS, CPU - processor, storage drive, keyboard, RAM - memory, monitor, motherboard, mouse, NIC - network adapter, printer, sound card - audio card, graphics card - video card. Hardware.Info is a .NET Standard 2.0 library and uses WMI on Windows, /dev, /proc, /sys on Linux and sysctl, system_profiler on macOS.
Include NuGet package from https://www.nuget.org/packages/Hardware.Info
<ItemGroup>
<PackageReference Include="Hardware.Info" Version="100.1.0.0" />
</ItemGroup>
Call RefreshAll()
or one of the other Refresh*()
methods:
class Program
{
static IHardwareInfo hardwareInfo;
static void Main(string[] _)
{
try
{
hardwareInfo = new HardwareInfo();
//hardwareInfo.RefreshOperatingSystem();
//hardwareInfo.RefreshMemoryStatus();
//hardwareInfo.RefreshBatteryList();
//hardwareInfo.RefreshBIOSList();
//hardwareInfo.RefreshCPUList();
//hardwareInfo.RefreshDriveList();
//hardwareInfo.RefreshKeyboardList();
//hardwareInfo.RefreshMemoryList();
//hardwareInfo.RefreshMonitorList();
//hardwareInfo.RefreshMotherboardList();
//hardwareInfo.RefreshMouseList();
//hardwareInfo.RefreshNetworkAdapterList();
//hardwareInfo.RefreshPrinterList();
//hardwareInfo.RefreshSoundDeviceList();
//hardwareInfo.RefreshVideoControllerList();
hardwareInfo.RefreshAll();
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
Console.WriteLine(hardwareInfo.OperatingSystem);
Console.WriteLine(hardwareInfo.MemoryStatus);
foreach (var hardware in hardwareInfo.BatteryList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.BiosList)
Console.WriteLine(hardware);
foreach (var cpu in hardwareInfo.CpuList)
{
Console.WriteLine(cpu);
foreach (var cpuCore in cpu.CpuCoreList)
Console.WriteLine(cpuCore);
}
foreach (var drive in hardwareInfo.DriveList)
{
Console.WriteLine(drive);
foreach (var partition in drive.PartitionList)
{
Console.WriteLine(partition);
foreach (var volume in partition.VolumeList)
Console.WriteLine(volume);
}
}
foreach (var hardware in hardwareInfo.KeyboardList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MemoryList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MonitorList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MotherboardList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.MouseList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.NetworkAdapterList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.PrinterList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.SoundDeviceList)
Console.WriteLine(hardware);
foreach (var hardware in hardwareInfo.VideoControllerList)
Console.WriteLine(hardware);
foreach (var address in HardwareInfo.GetLocalIPv4Addresses(NetworkInterfaceType.Ethernet, OperationalStatus.Up))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in HardwareInfo.GetLocalIPv4Addresses(NetworkInterfaceType.Wireless80211))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in HardwareInfo.GetLocalIPv4Addresses(OperationalStatus.Up))
Console.WriteLine(address);
Console.WriteLine();
foreach (var address in HardwareInfo.GetLocalIPv4Addresses())
Console.WriteLine(address);
Console.ReadLine();
}
}
Hardware.Info uses WMI (Windows Management Instrumentation) on Windows OS. For certain queries WMI takes 21 seconds to initialize the first time you use it, after that all subsequent queries will execute immediately. If WMI isn't used for 15 minutes it will have to be initialized again the next time you use it.
The 21 second initialization delay is caused by RPC that WMI uses internally. In RPC documentation it says that the RPC/TCP time-out interval is defined with a SCMApiConnectionParam
registry value located at HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control
and that the default value is set to 21,000 (21 seconds).
You can avoid the 21 second delay by excluding the queries that cause it (see Settings).
NetworkAdapter.Speed
in WindowsSometimes NetworkAdapter.Speed
in Win32_NetworkAdapter
can be 0
or long.MaxValue
. The correct value can be retrived from CurrentBandwidth
in Win32_PerfFormattedData_Tcpip_NetworkAdapter
but unfortunately reading from Win32_PerfFormattedData_Tcpip_NetworkAdapter
causes a 21 second delay on the first read, like mentioned in the previous paragraph. Calling RefreshNetworkAdapterList
with includeBytesPersec = true
will also read the CurrentBandwidth
.
WmiNetUtilsHelper
will throw an exception in Windows if publish settings use <PublishTrimmed>true</PublishTrimmed>
This is a known error: https://github.com/dotnet/core/issues/7051#issuecomment-1071484354
HardwareInfo(bool useAsteriskInWMI = true, TimeSpan? timeoutInWMI = null)
The construcotr accepts two settings for WMI:
useAsteriskInWMI
causes WMI queries to use SELECT * FROM
instead of SELECT
with a list of property names. This is slower, but safer, more compatible with older Windows (XP, Vista, 7, 8) where a certain WMI property might be missing and throw an exception when queried by name. The default value is true
.
timeoutInWMI
sets the Timeout
property of the EnumerationOptions
in the ManagementObjectSearcher
that executes each query. The default value is EnumerationOptions.InfiniteTimeout
. There are one or more queries for each hardware component, so there are more than 16 queries executed on RefreshAll()
. If a query reaches the timeout it will throw a System.Management.ManagementException
exception where ErrorCode
will be System.Management.ManagementStatus.Timedout
. If you set the timeoutInWMI
then use a try-catch
block like this:
IHardwareInfo hardwareInfo;
try
{
hardwareInfo = new HardwareInfo(timeoutInWMI: TimeSpan.FromMilliseconds(100));
hardwareInfo.RefreshAll();
}
catch (ManagementException ex) when (ex.ErrorCode == ManagementStatus.Timedout)
{
Console.WriteLine(ex);
}
In these two methods you can exclude some slow queries by setting the parameters to false
:
RefreshCPUList(bool includePercentProcessorTime = true)
RefreshNetworkAdapterList(bool includeBytesPersec = true, bool includeNetworkAdapterConfiguration = true)
Setting includePercentProcessorTime
and includeBytesPersec
to false
will exclude the queries that:
Setting includeNetworkAdapterConfiguration
to false
has only a small impact on performance.
Method | Mean | Error | StdDev |
---|---|---|---|
RefreshMemoryStatus | 947.8 ns | 3.77 ns | 3.53 ns |
RefreshBatteryList | 1,811,885.7 ns | 12,921.05 ns | 11,454.17 ns |
RefreshBIOSList | 2,086,001.0 ns | 23,896.69 ns | 22,352.98 ns |
RefreshCPUList | 1,543,579,005.2 ns | 2,405,376.47 ns | 2,132,303.59 ns |
RefreshDriveList | 409,137,516.3 ns | 8,612,410.99 ns | 25,258,710.57 ns |
RefreshKeyboardList | 5,568,039.5 ns | 44,228.57 ns | 41,371.43 ns |
RefreshMemoryList | 2,120,024.5 ns | 26,103.39 ns | 24,417.13 ns |
RefreshMonitorList | 5,669,237.8 ns | 50,801.76 ns | 45,034.44 ns |
RefreshMotherboardList | 1,965,222.9 ns | 14,387.30 ns | 13,457.89 ns |
RefreshMouseList | 6,003,924.9 ns | 60,725.05 ns | 50,708.17 ns |
RefreshNetworkAdapterList | 1,412,244,738.6 ns | 14,681,615.28 ns | 12,259,813.69 ns |
RefreshPrinterList | 28,244,822.2 ns | 143,359.60 ns | 134,098.66 ns |
RefreshSoundDeviceList | 3,608,577.5 ns | 68,688.62 ns | 73,496.06 ns |
RefreshVideoControllerList | 11,568,549.2 ns | 54,666.07 ns | 48,460.05 ns |
Method | Mean | Error | StdDev |
---|---|---|---|
RefreshOperatingSystem | 2.946 ns | 0.0052 ns | 0.0047 ns |
RefreshMemoryStatus | 460.552 ns | 4.4810 ns | 3.9723 ns |
RefreshBatteryList | 1,624,392.057 ns | 22,526.9314 ns | 21,071.7057 ns |
RefreshBIOSList | 1,785,673.828 ns | 8,812.8115 ns | 8,243.5094 ns |
RefreshCPUList | 1,964,995,539.000 ns | 171,465,934.5051 ns | 505,571,176.5574 ns |
RefreshDriveList | 62,452,668.148 ns | 342,662.0413 ns | 320,526.2860 ns |
RefreshKeyboardList | 4,303,528.516 ns | 47,355.1733 ns | 41,979.1277 ns |
RefreshMemoryList | 1,926,931.367 ns | 19,754.4179 ns | 18,478.2948 ns |
RefreshMonitorList | 3,884,362.370 ns | 29,422.1438 ns | 27,521.4916 ns |
RefreshMotherboardList | 1,782,235.664 ns | 12,974.2296 ns | 12,136.1024 ns |
RefreshMouseList | 4,700,086.615 ns | 44,435.0631 ns | 41,564.5856 ns |
RefreshNetworkAdapterList | 945,004,493.333 ns | 8,568,978.4607 ns | 8,015,427.7687 ns |
RefreshPrinterList | 48,126,103.030 ns | 729,958.0933 ns | 682,803.2534 ns |
RefreshSoundDeviceList | 4,154,082.924 ns | 46,922.5501 ns | 41,595.6184 ns |
RefreshVideoControllerList | 8,784,372.500 ns | 125,080.5212 ns | 117,000.3971 ns |
GetDriveList
in Linux - thanks to @GusanoGris
Microsoft.SourceLink.GitHub
- by @andreas-eriksson
Disk.Description
in LinuxDisk.FirmwareRevision
in LinuxDisk.Name
in LinuxDisk.SerialNumber
in LinuxDisk.Size
in LinuxHardwareInfo.snk
to sign the assembly with a strong name keyGetCpuList
in Linux - thanks to @inelisoni
GetMonitorList
in Windows - by @Geevo
GetMonitorList
in Windows - by @Geevo
NetworkAdapter.Speed
in Windows - by @isenmann
Keyboard
info in LinuxMouse
info in LinuxSoundDevice
info in LinuxVideoController.CurrentHorizontalResolution
in LinuxVideoController.CurrentVerticalResolution
in LinuxVideoController.CurrentRefreshRate
in LinuxVideoController.AdapterRAM
in Windows - by @jesperll
L1DataCacheSize
and L1InstructionCacheSize
in Windows, macOS, LinuxL2CacheSize
and L3CacheSize
in Windows, LinuxGetNetworkAdapterList
in Windows - thanks to @isenmann
CurrentClockSpeed
in Windows - thanks to @jason-c-daniels
GetCpuUsage
in Linux - thanks to @glebov21
CPU.Name
and CPU.CurrentClockSpeed
in macOS - by @davidaramant
CPU.MaxClockSpeed
in macOS - by @davidaramant
PercentProcessorTime
in Windows - thanks to @C6OI
GetOperatingSystem()
in Windows, macOS, Linux - thanks to @adhip94
GetBatteryList()
in macOS - by @Tadelsucht
GetBatteryList()
in Linux - by @Tadelsucht
GetDriveList()
and GetMemoryList()
in Linux - thanks to @misaka00251
Memory.BankLabel
, Memory.MinVoltage
, Memory.MaxVoltage
in Windows - by @AathifMahir
CPU.SocketDesignation
, CPU.SecondLevelAddressTranslationExtensions
in Windows - by @AathifMahir
IHardwareInfo
so that HardwareInfo
can be mocked - by @240026763
MemAvailable
instead of MemFree
in Linux - by @schotime
Battery.EstimatedChargeRemaining
in Windows, Linux - by @reptail
Battery.ExpectedLife
in LinuxBattery.EstimatedRunTime
in LinuxBattery.MaxRechargeTime
in LinuxBattery.TimeToFullCharge
in LinuxBattery.DesignCapacity
in LinuxBattery.FullChargeCapacity
in LinuxBattery.BatteryStatusDescription
in LinuxMonitor
info in macOSVideoController
info in macOSCPU.L2CacheSize
in macOSCPU.L3CacheSize
in macOSMemory
info in macOSBIOS.ReleaseDate
in LinuxCPU.Manufacturer
in LinuxCPU.L3CacheSize
in LinuxMotherboard.SerialNumber
in LinuxNetworkAdapter
info in LinuxGetLocalIPv4Addresses()
in macOSGetLocalIPv4Addresses()
in Windows, macOS, LinuxMotherboard.SerialNumber
in WindowsDrive
, NetworkAdapter
info in macOS, Linux