wil*_*ilx 18 .net c# windows wmi
我使用.NET的System.Management东西监视一些使用WMI的机器.我正在使用的查询是这样的:
SELECT Timestamp_Sys100NS, PercentProcessorTime
FROM Win32_PerfRawData_PerfOS_Processor
WHERE Name='_Total'
Run Code Online (Sandbox Code Playgroud)
从那里我使用众所周知的公式计算CPU使用率%:
double cpu_usage = (1 - (double)delta_cpu / delta_time) * 100;
Run Code Online (Sandbox Code Playgroud)
除了一台机器(目前为止),它的效果非常好.
问题是,对于一台机器,即Windows 2003服务器(启用超线程,如果重要),我有时会得到负CPU使用率值.换句话说,(double)delta_cpu / delta_time表达式产生数量> 1.我确实在网上搜索了为什么会发生这种情况,但我什么都没发现.
这个Windows 2003服务器是否具体?或者是超线程相关的问题?或者只是预期,我应该将CPU使用值或cpu_delta值限制在某个范围内?
编辑:
我用这台机器观察的第二个奇怪的事情是,该Timestamp_Sys100NS值并不表示FILETIME日期(自1600年1月1日以来的刻度),而是从启动时开始看起来像刻度.
编辑2:我现在已经验证了这个问题是在许多Windows 2003服务器上.而且我显然不是唯一一个有同样问题的人.
编辑3:我已经通过查询解决的时间邮票LastBootUpTime从Win32_OperatingSystem和补充说,到Timestamp_Sys100NS时的值Timestamp_Sys100NS是过去太远.这似乎给出了正确的日期和时间.从中检索日期之后操作日期的代码Win32_OperatingSystem如下所示:
WbemScripting.SWbemDateTime swbem_time = new WbemScripting.SWbemDateTime();
swbem_time.Value = date_str;
string time_as_file_time_str = swbem_time.GetFileTime(true);
return new DateTimeOffset(epoch.Ticks + long.Parse(time_as_file_time_str),
swbem_time.UTCSpecified
? TimeSpan.FromMinutes(swbem_time.UTC)
: TimeSpan.Zero);
Run Code Online (Sandbox Code Playgroud)
...然后调整到UTC ......
boot_time = boot_time.UtcDateTime;
Run Code Online (Sandbox Code Playgroud)
...然后boot_time简单地添加到currentWMI在Timestamp_Sys100NS字段中返回的时间戳()...
if (time.Year < 2000)
time = boot_time + current;
Run Code Online (Sandbox Code Playgroud)
编辑4:似乎有3类系统Timestamp_Sys100NS:
Timestamp_Sys100NS是UTC时代以来的时间.Timestamp_Sys100NS需要添加Win32_OperatingSystem.LastBootUpTime以获得合理的时间.编辑5:一些受影响的计算机可能是虚拟机,但不是全部.