00001 #ifndef Impala_Basis_Timer_h
00002 #define Impala_Basis_Timer_h
00003
00004 #ifdef unix
00005
00006 #include <sys/param.h>
00007 #include <sys/times.h>
00008 #include <limits.h>
00009 #include <unistd.h>
00010
00011 #include <sys/time.h>
00012 #else
00013
00014 #include <ctime>
00015
00016 #include <windows.h>
00017 #undef small // the fucking idiots define this to char apparently
00018 #endif
00019
00020 #include <stdio.h>
00021 #include "Basis/String.h"
00022
00023 namespace Impala
00024 {
00025
00026
00027 class Timer
00028 {
00029 public:
00030
00031
00032
00033 Timer(int mode = 1) : mMode(mode)
00034 {
00035 #ifdef unix
00036
00037 #else
00038 LARGE_INTEGER freqStruct;
00039 if (QueryPerformanceFrequency(&freqStruct))
00040 {
00041 mFreq = freqStruct.HighPart;
00042 mFreq = mFreq << 32;
00043 mFreq |= freqStruct.LowPart;
00044 }
00045 else
00046 {
00047 std::cout << "Timer: no QueryPerformanceFrequency" << std::endl;
00048 }
00049 if (! QueryPerformanceCounter(&freqStruct))
00050 std::cout << "Timer: no QueryPerformanceCounter" << std::endl;
00051 #endif
00052 Start();
00053 }
00054
00055 void
00056 Start()
00057 {
00058 #ifdef unix
00059 if (mMode == 0)
00060 {
00061 times(&mCpuTime);
00062 mUsrTime = mCpuTime.tms_utime;
00063 mSysTime = mCpuTime.tms_stime;
00064 }
00065 else
00066 {
00067 gettimeofday(&mStartTime, 0);
00068 }
00069 #else
00070 if (mMode == 0)
00071 {
00072 mCpuTime = clock();
00073 }
00074 else
00075 {
00076 LARGE_INTEGER countStruct;
00077 QueryPerformanceCounter(&countStruct);
00078 mStartTime = countStruct.HighPart;
00079 mStartTime = mStartTime << 32;
00080 mStartTime |= countStruct.LowPart;
00081 }
00082 #endif
00083 }
00084
00085 double
00086 SplitTime()
00087 {
00088 double val;
00089 #ifdef unix
00090 if (mMode == 0)
00091 {
00092 times(&mCpuTime);
00093 time_t splitUsrTime = mCpuTime.tms_utime - mUsrTime;
00094 time_t splitSysTime = mCpuTime.tms_stime - mSysTime;
00095 val = (double) (splitUsrTime + splitSysTime) / HZ;
00096 }
00097 else
00098 {
00099 struct timeval splitTime;
00100 gettimeofday(&splitTime, 0);
00101 val = (double) (splitTime.tv_sec - mStartTime.tv_sec);
00102 long uSec = splitTime.tv_usec - mStartTime.tv_usec;
00103 val += (double) uSec / 1000000;
00104 }
00105 #else
00106 if (mMode == 0)
00107 {
00108 clock_t splitCpuTime = clock() - mCpuTime;
00109 val = (double) splitCpuTime / CLOCKS_PER_SEC;
00110 }
00111 else
00112 {
00113 LARGE_INTEGER splitTimeStruct;
00114 QueryPerformanceCounter(&splitTimeStruct);
00115 LONGLONG splitTime = splitTimeStruct.HighPart;
00116 splitTime = splitTime << 32;
00117 splitTime |= splitTimeStruct.LowPart;
00118 splitTime -= mStartTime;
00119 val = (double) splitTime / mFreq;
00120 }
00121 #endif
00122 return val;
00123 }
00124
00125 String
00126 SplitTimeStr(double divide = 1.0)
00127 {
00128 return Format(SplitTime() / divide);
00129 }
00130
00131 double
00132 Stop()
00133 {
00134 double val;
00135 #ifdef unix
00136 if (mMode == 0)
00137 {
00138 times(&mCpuTime);
00139 mUsrTime = mCpuTime.tms_utime - mUsrTime;
00140 mSysTime = mCpuTime.tms_stime - mSysTime;
00141 val = (double) (mUsrTime + mSysTime) / HZ;
00142 }
00143 else
00144 {
00145 struct timeval splitTime;
00146 gettimeofday(&splitTime, 0);
00147 val = (double) (splitTime.tv_sec - mStartTime.tv_sec);
00148 long uSec = splitTime.tv_usec - mStartTime.tv_usec;
00149 val += (double) uSec / 1000000;
00150 }
00151 #else
00152 if (mMode == 0)
00153 {
00154 mCpuTime = clock() - mCpuTime;
00155 val = (double) mCpuTime / CLOCKS_PER_SEC;
00156 }
00157 else
00158 {
00159 LARGE_INTEGER splitTimeStruct;
00160 QueryPerformanceCounter(&splitTimeStruct);
00161 LONGLONG splitTime = splitTimeStruct.HighPart;
00162 splitTime = splitTime << 32;
00163 splitTime |= splitTimeStruct.LowPart;
00164 splitTime -= mStartTime;
00165 val = (double) splitTime / mFreq;
00166 }
00167 #endif
00168 return val;
00169 }
00170
00171 static String
00172 Format(double secs)
00173 {
00174 char printBuf[2048];
00175 int hours = int (secs / 3600);
00176 secs -= hours * 3600;
00177 int minutes = int (secs / 60);
00178 secs -= minutes * 60;
00179 sprintf(printBuf, "%dh%dm%.2fs", hours, minutes, secs);
00180 return String(printBuf);
00181 }
00182
00183 private:
00184
00185 int mMode;
00186
00187 #ifdef unix
00188
00189 struct tms mCpuTime;
00190 time_t mSysTime;
00191 time_t mUsrTime;
00192
00193 struct timeval mStartTime;
00194 #else
00195
00196 clock_t mCpuTime;
00197
00198 LONGLONG mFreq;
00199 LONGLONG mStartTime;
00200 #endif
00201
00202 };
00203
00204 }
00205
00206 #endif