2011-11-25 35 views
18

.NETのSystem.Managementのものを使用して、WMIを使用して一部のマシンを監視しています。私はよく知られている式を使用してCPU使用率%を計算することから、過去のWMI、負のCPU使用率とTimestamp_Sys100NS

SELECT Timestamp_Sys100NS, PercentProcessorTime 
FROM Win32_PerfRawData_PerfOS_Processor 
WHERE Name='_Total' 

double cpu_usage = (1 - (double)delta_cpu/delta_time) * 100; 

それは非常によく、すべてのマシンが、1つを(これまでに)働く私が使用していたクエリはこれです。

問題は、Windows 2003サーバー(ハイパースレッディングが有効な場合は重要)の1台のマシンで、CPU使用率がマイナスになることがあります。換言すれば、という表現は数字> 1を生成する。私はなぜこれが起こっているかもしれないかのヒントについてウェブを検索しましたが、何も見つかりませんでした。

このWindows 2003サーバーは特定ですか?それともハイパースレッディング関連の問題ですか?または、それはちょうど期待されていると私はちょうどいくつかの範囲にCPU使用量の値またはcpu_deltaの値をクランプする必要がありますか?

編集:私はこの1台のマシンで観察しています 二奇妙なことは、Timestamp_Sys100NS値は、日付のようなFILETIMEを示していないことである(エポック1600年1月1日以降ティック)が、代わりに、それはブート時以来ティックのように見えます。

EDIT 2: この問題は、多くのWindows 2003サーバーで確認されています。そして私は明らかにnot the only one with the same problemです。

EDIT 3: 私はWin32_OperatingSystemからLastBootUpTimeを照会し、Timestamp_Sys100NSの値が過去に遠すぎるときTimestamp_Sys100NSにそれを追加することにより、タイムスタンプの問題を解決しました。それは正しい日時を与えるようです。その後、boot_time単に時間に加算されて...

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); 

...その後UTCに調整...

boot_time = boot_time.UtcDateTime; 

:それはWin32_OperatingSystemから取得された後の日付を操作するコードは次のようになります。スタンプ(currentは)... Timestamp_Sys100NSフィールドにWMIによってで返さ

if (time.Year < 2000) 
    time = boot_time + current; 

EDIT 4: それはTimestamp_Sys100NSに関してシステムの3つのクラスがあることが表示されます。

  1. はまずTimestamp_Sys100NSはUTCにおけるエポックからのティックの時間であるVistaの+システムです。
  2. 第2に、妥当な時間を得るためTimestamp_Sys100NSWin32_OperatingSystem.LastBootUpTimeに追加する必要があるWindows 2003システムがあります。
  3. 第3クラスは、上記の追加を行うことで、依然として正しい日時の日付が失われるシステムです。

EDIT 5:影響を受けたマシンのいくつかは、仮想マシンではなく、それらのすべてだったかもしれません。

+18

これはCPUがあなたを使用していることを意味します:) –

+0

どのようにしてLastBootUpTimeをTimeStamp_Sys100NSに追加しましたか?どのような変換をしましたか? – raz3r

+0

@ raz3r:私は 'System.DateTime(Int64)' ctor(ティックを取る)を使用しています。それをLastBootUpTimeに追加します。私は明日の正確な詳細のみを確認することができます。 – wilx

答えて

0

コードを使用してみてくださいそのマシン上でアプリケーションを作成し、あなたが右の測定値 http://www.microsoft.com/download/en/details.aspx?id=8572

+0

生の値は、 'System.Management' APIと' wmic'の両方から、そして上記のツールと同じです。 – wilx

0

あなたは特に話している式を取得するかどうかを確認PERF_100NSEC_TIMER_INV あるhttp://msdn.microsoft.com/en-us/library/ms803963.aspx

私は個人的にこの問題に対処していない

私はゼロ以下の値を見たことがないからです。

この

は私がやっているすべてです:

/// <summary> 
/// PERF_100NSEC_TIMER_INV algorithm. 
/// </summary> 
/// <param name="n2"></param> 
/// <param name="d2"></param> 
/// <param name="n1"></param> 
/// <param name="d1"></param> 
/// <returns></returns> 
public static int CalculatePerf100NsecTimerInv(long n2, UInt64 d2, 
               long n1, UInt64 d1) 
{ 
    int usage = 0; 
    try 
    { 
     double dataDiff = (n2 - n1); 
     double timeDiff = (d2 - d1); 
     double dUsage = (1 - (dataDiff/timeDiff)) * 100; 

     // Evaluate 
     usage = (dUsage >= 0.5) ? Convert.ToInt32(Math.Ceiling(dUsage)) : 0; 
    } 
    catch { } 

    // Return 
    return usage; 
} 

使用法:

// Calculate 
int cpuTime = 
    MSPerformanceAlgorithms.CalculatePerf100NsecTimerInv(
     current.PercentProcessorTime, current.TimestampSys100Ns, 
     previous.PercentProcessorTime, previous.TimestampSys100Ns); 

私は2003箱のためのタスクマネージャでCPU使用率を見れば、それがうまくマッチします。私はあなたがこれらの値で計算している限り、ゼロよりも小さいものは無視することができると思います。

+0

残念ながら、私は正しい数式を使用しています。 – wilx

+0

他にもできることがたくさんあるとは確信していません。あなたの所見から、スタンプが間違っているという直接的な指標として、LastBootUpTime> Timestamp_Sys100NSかどうかを確認するチェックを追加します。 WMIのリリース間で多くの矛盾がありました。彼らは実際には、Windows 2003まで、ネットワークデータとカウンタを追加すると、それほど効果的になることはありませんでした。 これはWindows 2003 R1でのみ可能ですか? x86とx64の違いはありますか? これはすばらしいトピックであり、多くの人がこの恩恵を受ける可能性があります。 – Xcalibur37

1

私は標準的な「時間同期」のように聞こえます。

システムのクロックは...クロックです。あなたのコンピュータが外部クロック(Windowsタイムサービスなど)と同期すると、システム時間が後ろにジャンプすることがありますので、あなたの時計は高速に実行されている可能性があります(おそらく実際の時間の99%で1分を完了します)。

代わりに、ユーザーが手動でシステム時間(例:日付と時刻コントロールパネル)を調整することができるので、それはあなたがのために設計する必要があり何か(自分のシステムの時刻を設定すると、アプリケーションをクラッシュした場合、ユーザーは非常に不幸になる!)

私がこれを解決する方法は、クランプすることです。通過するのに少なくとも0.0秒の「リアルタイム」を必要とするが、時間調整が後方だけでなく前進するので、最大0.5秒にクランプする。

私は役立つことを望みます。

+0

0を忘れないでください。0秒の最小値は、ゼロ除算にも注意する必要があることを意味します。 – JasonS

+0

私はこれがあなたの問題だと確信していますので、私の解決策がうまくいけば返信してください。 – JasonS

+0

悪い時刻情報の効果は一貫していますが、しばらくの間は1回だけではなく、常に発生します。私のコードは5秒ごとにチェックしていました。それは、NTPデーモン/サービスによる段階的な時間調整に苦しんでいないほど長く思える。あなたの答えがその問題を説明するものは何もしません。 – wilx

関連する問題