Bug 470455 - test_database_sync_embed_visits.js leaks, r=sdwilsh
[wine-gecko.git] / modules / libutil / src / stopwatch.cpp
blobc7529667d61a6c6db145f724b0a854725a84d7b4
1 #include "stopwatch.h"
2 #include <stdio.h>
3 #include <time.h>
4 #ifdef XP_UNIX
5 #include <unistd.h>
6 #include <sys/times.h>
7 #endif
8 #ifdef XP_WIN
9 #include "windows.h"
10 #endif
11 #include "nsDebug.h"
13 // #define MILLISECOND_RESOLUTION to track time with greater precision
14 // If not defined the resolution is to the second only
16 #define MILLISECOND_RESOLUTION
17 #ifdef MILLISECOND_RESOLUTION
18 double gTicks = 1.0e-4; // for millisecond resolution
19 #else
20 double gTicks = 1.0e-7; // for second resolution
21 #endif
23 Stopwatch::Stopwatch() {
25 #ifdef R__UNIX
26 if (!gTicks) gTicks = (clock_t)sysconf(_SC_CLK_TCK);
27 #endif
28 fState = kUndefined;
29 fTotalCpuTime = 0;
30 fTotalRealTime = 0;
31 mCreatedStack = PR_FALSE;
32 mSavedStates = nsnull;
33 Start();
36 Stopwatch::~Stopwatch() {
37 EState* state = 0;
38 if (mSavedStates) {
39 while ((state = (EState*) mSavedStates->Pop())) {
40 delete state;
42 delete mSavedStates;
46 void Stopwatch::Start(PRBool reset) {
47 if (reset) {
48 fTotalCpuTime = 0;
49 fTotalRealTime = 0;
51 if (fState != kRunning) {
52 #ifndef R__UNIX
53 fStartRealTime = GetRealTime();
54 fStartCpuTime = GetCPUTime();
55 #else
56 struct tms cpt;
57 fStartRealTime = (double)times(&cpt) / gTicks;
58 fStartCpuTime = (double)(cpt.tms_utime+cpt.tms_stime) / gTicks;
59 #endif
61 fState = kRunning;
64 void Stopwatch::Stop() {
66 #ifndef R__UNIX
67 fStopRealTime = GetRealTime();
68 fStopCpuTime = GetCPUTime();
69 #else
70 struct tms cpt;
71 fStopRealTime = (double)times(&cpt) / gTicks;
72 fStopCpuTime = (double)(cpt.tms_utime+cpt.tms_stime) / gTicks;
73 #endif
74 if (fState == kRunning) {
75 fTotalCpuTime += fStopCpuTime - fStartCpuTime;
76 fTotalRealTime += fStopRealTime - fStartRealTime;
78 fState = kStopped;
82 void Stopwatch::SaveState() {
83 if (!mCreatedStack) {
84 mSavedStates = new nsDeque(nsnull);
85 if (!mSavedStates)
86 return;
87 mCreatedStack = PR_TRUE;
89 EState* state = new EState();
90 if (state) {
91 *state = fState;
92 mSavedStates->PushFront((void*) state);
96 void Stopwatch::RestoreState() {
97 EState* state = nsnull;
98 state = (EState*) mSavedStates->Pop();
99 if (state) {
100 if (*state == kRunning && fState == kStopped)
101 Start(PR_FALSE);
102 else if (*state == kStopped && fState == kRunning)
103 Stop();
104 delete state;
106 else {
107 NS_WARNING("Stopwatch::RestoreState(): The saved state stack is empty.\n");
111 void Stopwatch::Continue() {
113 if (fState != kUndefined) {
115 if (fState == kStopped) {
116 fTotalCpuTime -= fStopCpuTime - fStartCpuTime;
117 fTotalRealTime -= fStopRealTime - fStartRealTime;
120 fState = kRunning;
125 // NOTE: returns seconds regardless of the state of the MILLISECOND_RESOLUTION #define
127 double Stopwatch::RealTime() {
129 if (fState != kUndefined) {
130 if (fState == kRunning)
131 Stop();
134 #ifdef MILLISECOND_RESOLUTION
135 return fTotalRealTime/1000;
136 #else
137 return fTotalRealTime;
138 #endif
141 // NOTE: returns milliseconds regardless of the state of the MILLISECOND_RESOLUTION #define
143 double Stopwatch::RealTimeInMilliseconds() {
145 if (fState != kUndefined) {
146 if (fState == kRunning)
147 Stop();
150 #ifdef MILLISECOND_RESOLUTION
151 return fTotalRealTime;
152 #else
153 return fTotalRealTime * 1000; // we don;t have milliseconds, so fake it
154 #endif
157 // NOTE: returns seconds regardless of the state of the MILLISECOND_RESOLUTION define
159 double Stopwatch::CpuTime() {
160 if (fState != kUndefined) {
162 if (fState == kRunning)
163 Stop();
166 #ifdef MILLISECOND_RESOLUTION
167 return fTotalCpuTime / 1000; // adjust from milliseconds to seconds
168 #else
169 return fTotalCpuTime;
170 #endif
174 double Stopwatch::GetRealTime(){
175 #if defined(R__MAC)
176 // return(double)clock() / gTicks;
177 return(double)clock() / 1000000L;
178 #elif defined(R__UNIX)
179 struct tms cpt;
180 return (double)times(&cpt) / gTicks;
181 #elif defined(R__VMS)
182 return(double)clock()/gTicks;
183 #elif defined(WIN32)
184 union {FILETIME ftFileTime;
185 __int64 ftInt64;
186 } ftRealTime; // time the process has spent in kernel mode
187 SYSTEMTIME st;
188 GetSystemTime(&st);
189 SystemTimeToFileTime(&st,&ftRealTime.ftFileTime);
190 return (double)ftRealTime.ftInt64 * gTicks;
191 #endif
195 double Stopwatch::GetCPUTime(){
196 #if defined(R__MAC)
197 // return(double)clock() / gTicks;
198 return(double)clock();
199 #elif defined(R__UNIX)
200 struct tms cpt;
201 times(&cpt);
202 return (double)(cpt.tms_utime+cpt.tms_stime) / gTicks;
203 #elif defined(R__VMS)
204 return(double)clock()/gTicks;
205 #elif defined(WINCE)
206 return 0;
207 #elif defined(WIN32)
209 DWORD ret;
210 FILETIME ftCreate, // when the process was created
211 ftExit; // when the process exited
213 union {FILETIME ftFileTime;
214 __int64 ftInt64;
215 } ftKernel; // time the process has spent in kernel mode
217 union {FILETIME ftFileTime;
218 __int64 ftInt64;
219 } ftUser; // time the process has spent in user mode
221 HANDLE hProcess = GetCurrentProcess();
222 ret = GetProcessTimes (hProcess, &ftCreate, &ftExit,
223 &ftKernel.ftFileTime,
224 &ftUser.ftFileTime);
225 if (ret != PR_TRUE){
226 ret = GetLastError ();
227 #ifdef DEBUG
228 printf("%s 0x%lx\n"," Error on GetProcessTimes", (int)ret);
229 #endif
233 * Process times are returned in a 64-bit structure, as the number of
234 * 100 nanosecond ticks since 1 January 1601. User mode and kernel mode
235 * times for this process are in separate 64-bit structures.
236 * To convert to floating point seconds, we will:
238 * Convert sum of high 32-bit quantities to 64-bit int
241 return (double) (ftKernel.ftInt64 + ftUser.ftInt64) * gTicks;
243 #endif
247 void Stopwatch::Print(void) {
248 // Print the real and cpu time passed between the start and stop events.
250 double realt = RealTimeInMilliseconds();
252 int hours = int(realt / 3600000);
253 realt -= hours * 3600000;
254 int min = int(realt / 60000);
255 realt -= min * 60000;
256 int sec = int(realt/1000);
257 realt -= sec * 1000;
258 #ifdef MOZ_PERF_METRICS
259 int ms = int(realt);
260 RAPTOR_STOPWATCH_TRACE(("Real time %d:%d:%d.%d, CP time %.3f\n", hours, min, sec, ms, CpuTime()));
261 #elif defined(DEBUG)
262 int ms = int(realt);
263 printf("Real time %d:%d:%d.%d, CP time %.3f\n", hours, min, sec, ms, CpuTime());
264 #endif