mirror of https://github.com/tongzx/nt5src
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
228 lines
4.7 KiB
228 lines
4.7 KiB
#ifndef __PERFTIMR_HXX__
|
|
#define __PERFTIMR_HXX__
|
|
|
|
//+-------------------------------------------------------------------------
|
|
//
|
|
// Microsoft Windows
|
|
// Copyright (C) Microsoft Corporation, 1992 - 1992.
|
|
//
|
|
// File: perftimr.hxx
|
|
//
|
|
// Contents: Performance Timer class
|
|
//
|
|
// Classes: CPerfTimer
|
|
//
|
|
// History: 31-Jan-94 PeterWi Created.
|
|
//
|
|
// Notes: -- the timer will assert if you don't call an End()
|
|
// for each Start() [except for calling Reset() or the destructor]
|
|
//
|
|
// -- change DECIMAL_PLACES to the number you want to print.
|
|
// Operations will still be done internally with maximum precision.
|
|
//
|
|
// -- maximum precision on intel seems to be 1/1,193,000
|
|
// or 1 millisecond
|
|
//
|
|
//
|
|
// Usage:
|
|
//
|
|
// Say you want to time operations:
|
|
// 1) A
|
|
// 2) A and B
|
|
// 3) 3 repetitions of (A and B)
|
|
//
|
|
// ...
|
|
// cperftimer totaltimer;
|
|
//
|
|
// for (3 reps)
|
|
// {
|
|
// CPerfTimer timer;
|
|
//
|
|
// timer.Start();
|
|
//
|
|
// operation A
|
|
//
|
|
// timer.End().Add();
|
|
//
|
|
// printf("time for A is %ws\n", timer.FormatElapsedTime());
|
|
//
|
|
// timer.Start();
|
|
//
|
|
// operation B
|
|
//
|
|
// timer.End().Add();
|
|
//
|
|
// printf("time for A+B is %ws\n", timer.FormatTotalTime());
|
|
//
|
|
// totalTimer.Add(timer);
|
|
// }
|
|
//
|
|
// printf("time for 3 reps of A+B is %ws\n", totalTimer.FormatTotalTime());
|
|
//
|
|
// where the last printf() would print something like:
|
|
//
|
|
// "time for 3 reps of A+B is 3.234s"
|
|
//
|
|
//--------------------------------------------------------------------------
|
|
|
|
#define DECIMAL_PLACES 5 // number of decimal places you want
|
|
|
|
|
|
class CPerfTimer
|
|
{
|
|
private:
|
|
|
|
LONGLONG
|
|
GetLowTickCount(void)
|
|
{
|
|
_nt = NtQueryPerformanceCounter(&_liConvert1, &_liConvert2);
|
|
_liCount = _liConvert1.QuadPart;
|
|
_liFreq = _liConvert2.QuadPart;
|
|
return _liCount;
|
|
}
|
|
|
|
void
|
|
_CheckState(void)
|
|
{
|
|
if ( _fStarted )
|
|
{
|
|
ASSERT(!"in middle of timing -- need to stop timer\n");
|
|
}
|
|
}
|
|
|
|
|
|
WCHAR *
|
|
_TimeToString(LONGLONG & liTime)
|
|
{
|
|
LONGLONG liSeconds;
|
|
LONGLONG liRemainder;
|
|
LONGLONG liBigRemainder;
|
|
LONGLONG liDecimal;
|
|
|
|
|
|
liSeconds = liTime / _liFreq;
|
|
liRemainder = liTime % _liFreq;
|
|
|
|
liBigRemainder = liRemainder * (LONGLONG) _ulMult;
|
|
|
|
liDecimal = liBigRemainder / _liFreq;
|
|
|
|
wsprintf(_wszTime, _wszFormat, (LONG)liSeconds, (LONG)liDecimal);
|
|
|
|
return _wszTime;
|
|
}
|
|
|
|
|
|
LONGLONG _liCount;
|
|
LONGLONG _liFreq;
|
|
LONGLONG _totalTime;
|
|
LONGLONG _startTime;
|
|
LONGLONG _endTime;
|
|
LONGLONG _elapsedTime;
|
|
|
|
LARGE_INTEGER _liConvert1;
|
|
LARGE_INTEGER _liConvert2;
|
|
|
|
NTSTATUS _nt;
|
|
ULONG _ulMult;
|
|
|
|
BOOLEAN _fStarted;
|
|
WCHAR _wszTime[20];// allow max of "time:99999.999s" and NULL
|
|
WCHAR _wszFormat[20];
|
|
|
|
public:
|
|
|
|
CPerfTimer()
|
|
{
|
|
_ulMult = 1;
|
|
|
|
for ( ULONG j = 0; j < DECIMAL_PLACES; j++ )
|
|
{
|
|
_ulMult *= 10;
|
|
}
|
|
|
|
wsprintf(_wszFormat, L"%ws%dlus", L"%lu.%0", DECIMAL_PLACES);
|
|
|
|
Reset();
|
|
}
|
|
|
|
CPerfTimer &
|
|
Reset(void)
|
|
{
|
|
_fStarted = FALSE;
|
|
|
|
_totalTime = 0;
|
|
_elapsedTime = 0;
|
|
|
|
_endTime = _startTime = GetLowTickCount();
|
|
|
|
return *this;
|
|
}
|
|
|
|
CPerfTimer &
|
|
Start(void)
|
|
{
|
|
_CheckState();
|
|
|
|
_fStarted = TRUE;
|
|
_startTime = GetLowTickCount();
|
|
|
|
return *this;
|
|
}
|
|
|
|
CPerfTimer &
|
|
End(void)
|
|
{
|
|
_endTime = GetLowTickCount();
|
|
|
|
if ( !_fStarted )
|
|
{
|
|
ASSERT(!"end without starting timer\n");
|
|
}
|
|
|
|
_fStarted = FALSE;
|
|
|
|
_elapsedTime = _endTime - _startTime;
|
|
|
|
return *this;
|
|
}
|
|
|
|
CPerfTimer &
|
|
Add(void)
|
|
{
|
|
_CheckState();
|
|
|
|
_totalTime = _totalTime + _elapsedTime;
|
|
|
|
return *this;
|
|
}
|
|
|
|
CPerfTimer &
|
|
Add(const CPerfTimer & timer)
|
|
{
|
|
_CheckState();
|
|
|
|
_totalTime = _totalTime + timer.TotalTime();
|
|
|
|
return *this;
|
|
}
|
|
|
|
LONGLONG
|
|
TotalTime(void) const { return _totalTime; }
|
|
|
|
LONGLONG
|
|
ElapsedTime(void) const { return _elapsedTime; }
|
|
|
|
LONGLONG
|
|
TimeUnitsPerSecond(void) const { return _liFreq; }
|
|
|
|
WCHAR *
|
|
FormatTotalTime(void) { return _TimeToString(_totalTime); };
|
|
|
|
WCHAR *
|
|
FormatElapsedTime(void) { return _TimeToString(_elapsedTime); };
|
|
|
|
|
|
}; // CPerfTimer
|
|
|
|
#endif // __PERFTIMR_HXX__
|