Fixed bug with incorrect FILETIME conversion to DateTime for ETW and Performance Counter sources

This commit is contained in:
Sergey Baranchenkov 2015-09-30 20:47:27 -07:00
Родитель 7fa2d741c2
Коммит 6149c056ff
7 изменённых файлов: 81 добавлений и 5 удалений

Просмотреть файл

@ -5,5 +5,5 @@ using System.Reflection;
[assembly: AssemblyCompany("MS Open Tech")]
[assembly: AssemblyProduct("Tx (LINQ to Logs and Traces)")]
[assembly: AssemblyCopyright("Copyright © MS Open Tech 2012")]
[assembly: AssemblyVersion("1.0.50917.0")]
[assembly: AssemblyFileVersion("1.0.50917.0")]
[assembly: AssemblyVersion("1.0.50930.0")]
[assembly: AssemblyFileVersion("1.0.50930.0")]

Просмотреть файл

@ -64,7 +64,7 @@ namespace Tx.Windows
public DateTimeOffset TimeStamp
{
get { return DateTime.FromFileTimeUtc(record->EventHeader.TimeStamp); }
get { return TimeUtil.DateTimeOffsetFromFileTime(record->EventHeader.TimeStamp); }
}
public Int64 TimeStampRaw

Просмотреть файл

@ -55,7 +55,7 @@ namespace Tx.Windows
break;
PdhUtils.CheckStatus(status, PdhStatus.PDH_CSTATUS_VALID_DATA);
DateTime timestamp = DateTime.FromFileTimeUtc(time);
DateTime timestamp = TimeUtil.FromFileTime(time);
foreach (PerfCounterInfo counterInfo in _counters)
{

Просмотреть файл

@ -40,7 +40,7 @@ namespace Tx.Windows
long time;
PdhStatus status = PdhNativeMethods.PdhCollectQueryDataWithTime(_query, out time);
PdhUtils.CheckStatus(status, PdhStatus.PDH_CSTATUS_VALID_DATA);
DateTime timestamp = DateTime.FromFileTimeUtc(time);
DateTime timestamp = TimeUtil.FromFileTime(time);
foreach (PerfCounterInfo counterInfo in _counters)
{

Просмотреть файл

@ -0,0 +1,40 @@
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved. See License.txt in the project root for license information.
using System;
namespace Tx.Windows
{
public sealed class TimeUtil
{
private const Int64 TicksPerMillisecond = 10000;
private const Int64 TicksPerSecond = TicksPerMillisecond * 1000;
private const Int64 TicksPerMinute = TicksPerSecond * 60;
private const Int64 TicksPerHour = TicksPerMinute * 60;
private const Int64 TicksPerDay = TicksPerHour * 24;
// Number of days in a non-leap year
private const int DaysPerYear = 365;
// Number of days in 4 years
const int DaysPer4Years = DaysPerYear * 4 + 1;
// Number of days in 100 years
private const int DaysPer100Years = DaysPer4Years * 25 - 1;
// Number of days in 400 years
private const int DaysPer400Years = DaysPer100Years * 4 + 1;
// Number of days from 1/1/0001 to 12/31/1600
private const int DaysTo1601 = DaysPer400Years * 4;
private const Int64 FileTimeOffset = DaysTo1601 * TicksPerDay;
public static DateTimeOffset DateTimeOffsetFromFileTime(Int64 fileTime)
{
return new DateTimeOffset(FileTimeOffset + fileTime, TimeSpan.Zero);
}
public static DateTime FromFileTime(Int64 fileTime)
{
return new DateTime(FileTimeOffset + fileTime, DateTimeKind.Local);
}
}
}

Просмотреть файл

@ -87,6 +87,7 @@
<Compile Include="PerfCounters\PerformanceSample.cs" />
<Compile Include="PerfMetadata.cs" />
<Compile Include="SystemEvent.cs" />
<Compile Include="TimeUtil.cs" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Tx.Core\Tx.Core.csproj">

Просмотреть файл

@ -10,6 +10,8 @@ using Tx.Windows;
namespace Tests.Tx
{
using System.Globalization;
[TestClass]
public class PerfCounterTest
{
@ -140,6 +142,39 @@ namespace Tests.Tx
Assert.AreEqual(600, disk.Count());
}
[TestMethod]
public void PerformanceCounterProbeFirst()
{
PerformanceSample[] result;
var startTime = DateTimeOffset.UtcNow;
using (var playback = new Playback())
{
((IPlaybackConfiguration)playback).AddInput(
() => PerfCounterObservable.FromRealTime(TimeSpan.FromSeconds(1), @"\Processor(_Total)\% User Time").Take(1),
typeof(PerfCounterPartitionTypeMap),
typeof(PerfCounterTypeMap));
var query = playback.GetObservable<PerformanceSample>();
var enumerable = playback.BufferOutput(query);
playback.Run();
result = enumerable.ToArray();
}
var endTime = DateTimeOffset.UtcNow;
Assert.AreEqual(1, result.Length);
Assert.AreEqual("% User Time", result[0].CounterName, false, CultureInfo.InvariantCulture);
Assert.AreEqual("Processor", result[0].CounterSet, false, CultureInfo.InvariantCulture);
Assert.AreEqual("_Total", result[0].Instance, false, CultureInfo.InvariantCulture);
var dto = new DateTimeOffset(result[0].Timestamp);
Assert.IsTrue(dto >= startTime);
Assert.IsTrue(dto <= endTime);
}
IEnumerable<InstanceCounterSnapshot> PivotToInstanceSnapshots(Playback playback, string counterSet)
{
var all = playback.GetObservable<PerformanceSample>();