Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions Generals/Code/GameEngine/Include/Common/PerfTimer.h
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,8 @@ __forceinline void GetPrecisionTimer(Int64* t)
class PerfGather
{
public:
PerfGather( const char *identifier );
// If net only (default), subtract perf timers running inside. [8/12/2003]
PerfGather( const char *identifier, Bool netOnly=true );
virtual ~PerfGather( );

__forceinline void startTimer();
Expand Down Expand Up @@ -126,6 +127,7 @@ class PerfGather
PerfGather* m_next;
PerfGather* m_prev;
Bool m_ignore;
Bool m_netTimeOnly;
};

//-------------------------------------------------------------------------------------------------
Expand Down Expand Up @@ -161,7 +163,9 @@ void PerfGather::stopTimer()
{
// don't add the time it took for us to actually get the ticks (in startTimer) to our parent...
(*m_activeHead)->m_runningTimeGross -= (s_stopStartOverhead);
(*m_activeHead)->m_runningTimeNet -= (runTime + s_stopStartOverhead);
if ((*m_activeHead)->m_netTimeOnly) {
(*m_activeHead)->m_runningTimeNet -= (runTime + s_stopStartOverhead);
}
}
}

Expand Down Expand Up @@ -224,6 +228,7 @@ AutoPerfGatherIgnore::~AutoPerfGatherIgnore()
}

//-------------------------------------------------------------------------------------------------
#define DECLARE_TOTAL_PERF_TIMER(id) static PerfGather s_##id(#id, false);
#define DECLARE_PERF_TIMER(id) static PerfGather s_##id(#id);
#define USE_PERF_TIMER(id) AutoPerfGather a_##id(s_##id);
#define IGNORE_PERF_TIMER(id) AutoPerfGatherIgnore a_##id(s_##id);
Expand Down Expand Up @@ -308,6 +313,7 @@ extern void StatMetricsDisplay( DebugDisplayInterface *dd, void *, FILE *fp );
#else // PERF_TIMERS

#define DECLARE_PERF_TIMER(id)
#define DECLARE_TOTAL_PERF_TIMER(id)
#define USE_PERF_TIMER(id)
#define IGNORE_PERF_TIMER(id)

Expand Down
3 changes: 1 addition & 2 deletions Generals/Code/GameEngine/Include/Common/StackDump.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,7 @@

#ifndef IG_DEBUG_STACKTRACE
#define IG_DEBUG_STACKTRACE 1
#endif

#endif // Unsure about this one -ML 3/25/03
#if defined(RTS_DEBUG) || defined(IG_DEBUG_STACKTRACE)

// Writes a stackdump (provide a callback : gets called per line)
Expand Down
170 changes: 125 additions & 45 deletions Generals/Code/GameEngine/Source/Common/PerfTimer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,10 @@
#include "GameClient/Display.h"
#include "GameClient/GraphDraw.h"

__forceinline void ProfileGetTime(__int64 &t)
{
t = _rdtsc();
}


//-------------------------------------------------------------------------------------------------
Expand All @@ -54,63 +58,139 @@ void GetPrecisionTimerTicksPerSec(Int64* t)
*t = s_ticksPerSec;
}

//Kris: Plugged in Martin's code to optimize timer setup.
#define HOFFESOMMER_REPLACEMENT_CODE

//-------------------------------------------------------------------------------------------------
void InitPrecisionTimer()
{
#ifdef USE_QPF
QueryPerformanceFrequency((LARGE_INTEGER*)&s_ticksPerSec);
#ifdef HOFFESOMMER_REPLACEMENT_CODE

// measure clock cycles 3 times for 20 msec each
// then take the 2 counts that are closest, average
_int64 n[ 3 ];
for( int k = 0; k < 3; k++ )
{
// wait for end of current tick
unsigned timeEnd = timeGetTime() + 2;
while( timeGetTime() < timeEnd ); //do nothing

// get cycles
_int64 start, startQPC, endQPC;
QueryPerformanceCounter( (LARGE_INTEGER *)&startQPC );
ProfileGetTime( start );
timeEnd += 20;
while( timeGetTime() < timeEnd ); //do nothing
ProfileGetTime( n[ k ] );
n[ k ] -= start;

// convert to 1 second
if( QueryPerformanceCounter( (LARGE_INTEGER*)&endQPC ) )
{
QueryPerformanceFrequency( (LARGE_INTEGER*)&s_ticksPerSec );
n[ k ] = ( n[ k ] * s_ticksPerSec ) / ( endQPC - startQPC );
}
else
{
n[ k ] = ( n[ k ] * 1000 ) / 20;
}
}

// find two closest values
_int64 d01 = n[ 1 ] - n[ 0 ];
_int64 d02 = n[ 2 ] - n[ 0 ];
_int64 d12 = n[ 2 ] - n[ 1 ];

if( d01 < 0 )
{
d01 = -d01;
}
if( d02 < 0 )
{
d02 = -d02;
}
if( d12 < 0 )
{
d12 = -d12;
}

_int64 avg;
if( d01 < d02 )
{
avg = d01 < d12 ? n[ 0 ] + n[ 1 ] : n[ 1 ] + n[ 2 ];
}
else
{
avg = d02 < d12 ? n[ 0 ] + n[ 2 ] : n[ 1 ] + n[ 2 ];
}

//s_ticksPerMSec = 1.0 * TotalTicks / totalTime;
s_ticksPerMSec = avg / 2000.0f;
s_ticksPerSec = s_ticksPerMSec * 1000.0f;
s_ticksPerUSec = s_ticksPerSec / 1000000.0f;


#else
// Init the precision timers
Int64 totalTime = 0;
Int64 TotalTicks = 0;
static int TESTS = 5;

for (int i = 0; i < TESTS; ++i)
{
int TimeStart;
int TimeStop;
Int64 StartTicks;
Int64 EndTicks;

TimeStart = timeGetTime();
GetPrecisionTimer(&StartTicks);
for(;;)
//Kris: With total disrespect, this code costs 5 real seconds of init time
//whenever we fire up the game.

#ifdef USE_QPF
QueryPerformanceFrequency((LARGE_INTEGER*)&s_ticksPerSec);
#else
// Init the precision timers
Int64 totalTime = 0;
Int64 TotalTicks = 0;
static int TESTS = 5;

for (int i = 0; i < TESTS; ++i)
{
TimeStop = timeGetTime();
if ((TimeStop - TimeStart) > 1000)
int TimeStart;
int TimeStop;
Int64 StartTicks;
Int64 EndTicks;

TimeStart = timeGetTime();
GetPrecisionTimer(&StartTicks);
for(;;)
{
GetPrecisionTimer(&EndTicks);
break;
TimeStop = timeGetTime();
if ((TimeStop - TimeStart) > 1000)
{
GetPrecisionTimer(&EndTicks);
break;
}
}
}

TotalTicks += (EndTicks - StartTicks);
TotalTicks += (EndTicks - StartTicks);

totalTime += (TimeStop - TimeStart);
}
totalTime += (TimeStop - TimeStart);
}

s_ticksPerMSec = 1.0 * TotalTicks / totalTime;
s_ticksPerSec = s_ticksPerMSec * 1000.0f;
#endif
s_ticksPerMSec = s_ticksPerSec / 1000.0f;
s_ticksPerUSec = s_ticksPerSec / 1000000.0f;
s_ticksPerMSec = 1.0 * TotalTicks / totalTime;
s_ticksPerSec = s_ticksPerMSec * 1000.0f;
#endif
s_ticksPerMSec = s_ticksPerSec / 1000.0f;
s_ticksPerUSec = s_ticksPerSec / 1000000.0f;

#ifdef NOT_IN_USE
Int64 bogus[8];
GetPrecisionTimer(&start);
for (Int ii = 0; ii < ITERS; ++ii)
{
GetPrecisionTimer(&bogus[0]);
GetPrecisionTimer(&bogus[1]);
GetPrecisionTimer(&bogus[2]);
GetPrecisionTimer(&bogus[3]);
GetPrecisionTimer(&bogus[4]);
GetPrecisionTimer(&bogus[5]);
GetPrecisionTimer(&bogus[6]);
GetPrecisionTimer(&bogus[7]);
}
TheTicksToGetTicks = (bogus[7] - start) / (ITERS*8);
DEBUG_LOG(("TheTicksToGetTicks is %d (%f usec)",(int)TheTicksToGetTicks,TheTicksToGetTicks/s_ticksPerUSec));
#endif

#ifdef NOT_IN_USE
Int64 bogus[8];
GetPrecisionTimer(&start);
for (Int ii = 0; ii < ITERS; ++ii)
{
GetPrecisionTimer(&bogus[0]);
GetPrecisionTimer(&bogus[1]);
GetPrecisionTimer(&bogus[2]);
GetPrecisionTimer(&bogus[3]);
GetPrecisionTimer(&bogus[4]);
GetPrecisionTimer(&bogus[5]);
GetPrecisionTimer(&bogus[6]);
GetPrecisionTimer(&bogus[7]);
}
TheTicksToGetTicks = (bogus[7] - start) / (ITERS*8);
DEBUG_LOG(("TheTicksToGetTicks is %d (%f usec)",(int)TheTicksToGetTicks,TheTicksToGetTicks/s_ticksPerUSec));
#endif

}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -474,6 +474,7 @@ void WriteStackLine(void*address, void (*callback)(const char*))
callback(line);
}


//*****************************************************************************
//*****************************************************************************
void DumpExceptionInfo( unsigned int u, EXCEPTION_POINTERS* e_info )
Expand Down
Loading