b311480e |
1 | // Created on: 1992-11-16 |
2 | // Created by: Mireille MERCIEN |
3 | // Copyright (c) 1992-1999 Matra Datavision |
973c2be1 |
4 | // Copyright (c) 1999-2014 OPEN CASCADE SAS |
b311480e |
5 | // |
973c2be1 |
6 | // This file is part of Open CASCADE Technology software library. |
b311480e |
7 | // |
d5f74e42 |
8 | // This library is free software; you can redistribute it and/or modify it under |
9 | // the terms of the GNU Lesser General Public License version 2.1 as published |
973c2be1 |
10 | // by the Free Software Foundation, with special exception defined in the file |
11 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
12 | // distribution for complete text of the license and disclaimer of any warranty. |
b311480e |
13 | // |
973c2be1 |
14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. |
7fd59977 |
16 | |
42cf5bc1 |
17 | |
18 | #include <OSD_Chronometer.hxx> |
7fd59977 |
19 | #include <Standard_Stream.hxx> |
20 | |
57c28b61 |
21 | #ifndef _WIN32 |
7fd59977 |
22 | |
03155c18 |
23 | #include <sys/times.h> |
24 | #include <unistd.h> |
7fd59977 |
25 | |
26 | #ifdef SOLARIS |
2da51263 |
27 | #include <sys/resource.h> |
7fd59977 |
28 | #endif |
29 | |
270a5d4e |
30 | #ifndef sysconf |
2da51263 |
31 | #define _sysconf sysconf |
7fd59977 |
32 | #endif |
33 | |
03155c18 |
34 | #if defined(DECOSF1) |
2da51263 |
35 | #include <time.h> |
7fd59977 |
36 | #endif |
37 | |
2da51263 |
38 | #ifndef CLK_TCK |
39 | #define CLK_TCK CLOCKS_PER_SEC |
40 | #endif |
7fd59977 |
41 | |
270a5d4e |
42 | #if (defined(__APPLE__)) |
43 | #include <mach/task.h> |
44 | #include <mach/mach.h> |
45 | #endif |
46 | |
7fd59977 |
47 | //======================================================================= |
48 | //function : GetProcessCPU |
270a5d4e |
49 | //purpose : |
7fd59977 |
50 | //======================================================================= |
2da51263 |
51 | void OSD_Chronometer::GetProcessCPU (Standard_Real& theUserSeconds, |
52 | Standard_Real& theSystemSeconds) |
7fd59977 |
53 | { |
c381fda2 |
54 | #if defined(__linux__) || defined(__FreeBSD__) || defined(__ANDROID__) || defined(__QNX__) |
7fd59977 |
55 | static const long aCLK_TCK = sysconf(_SC_CLK_TCK); |
56 | #else |
57 | static const long aCLK_TCK = CLK_TCK; |
58 | #endif |
270a5d4e |
59 | |
2da51263 |
60 | tms aCurrentTMS; |
61 | times (&aCurrentTMS); |
7fd59977 |
62 | |
2da51263 |
63 | theUserSeconds = (Standard_Real)aCurrentTMS.tms_utime / aCLK_TCK; |
64 | theSystemSeconds = (Standard_Real)aCurrentTMS.tms_stime / aCLK_TCK; |
7fd59977 |
65 | } |
66 | |
67 | //======================================================================= |
68 | //function : GetThreadCPU |
270a5d4e |
69 | //purpose : |
7fd59977 |
70 | //======================================================================= |
270a5d4e |
71 | void OSD_Chronometer::GetThreadCPU (Standard_Real& theUserSeconds, |
72 | Standard_Real& theSystemSeconds) |
7fd59977 |
73 | { |
270a5d4e |
74 | theUserSeconds = theSystemSeconds = 0.0; |
75 | #if (defined(__APPLE__)) |
76 | struct task_thread_times_info aTaskInfo; |
77 | mach_msg_type_number_t aTaskInfoCount = TASK_THREAD_TIMES_INFO_COUNT; |
78 | if (KERN_SUCCESS == task_info(mach_task_self(), TASK_THREAD_TIMES_INFO, |
79 | (task_info_t )&aTaskInfo, &aTaskInfoCount)) |
80 | { |
81 | theUserSeconds = Standard_Real(aTaskInfo.user_time.seconds) + 0.000001 * aTaskInfo.user_time.microseconds; |
82 | theSystemSeconds = Standard_Real(aTaskInfo.system_time.seconds) + 0.000001 * aTaskInfo.system_time.microseconds; |
83 | } |
d8d01f6e |
84 | #elif (defined(_POSIX_TIMERS) && defined(_POSIX_THREAD_CPUTIME)) || defined(__ANDROID__) || defined(__QNX__) |
7fd59977 |
85 | // on Linux, only user times are available for threads via clock_gettime() |
86 | struct timespec t; |
270a5d4e |
87 | if (!clock_gettime (CLOCK_THREAD_CPUTIME_ID, &t)) |
7fd59977 |
88 | { |
270a5d4e |
89 | theUserSeconds = t.tv_sec + 0.000000001 * t.tv_nsec; |
7fd59977 |
90 | } |
91 | #elif defined(SOLARIS) |
92 | // on Solaris, both user and system times are available as LWP times |
93 | struct rusage rut; |
270a5d4e |
94 | if (!getrusage (RUSAGE_LWP, &rut)) |
7fd59977 |
95 | { |
270a5d4e |
96 | theUserSeconds = rut.ru_utime.tv_sec + 0.000001 * rut.ru_utime.tv_usec; |
97 | theSystemSeconds = rut.ru_stime.tv_sec + 0.000001 * rut.ru_stime.tv_usec; |
7fd59977 |
98 | } |
99 | #else |
270a5d4e |
100 | #pragma error "OS is not supported yet; code to be ported" |
101 | #endif |
7fd59977 |
102 | } |
103 | |
104 | #else |
105 | |
7fd59977 |
106 | #include <windows.h> |
107 | |
108 | //======================================================================= |
109 | //function : EncodeFILETIME |
110 | //purpose : Encode time defined by FILETIME structure |
111 | // (100s nanoseconds since January 1, 1601) to 64-bit integer |
112 | //======================================================================= |
270a5d4e |
113 | static inline __int64 EncodeFILETIME (PFILETIME pFt) |
7fd59977 |
114 | { |
115 | __int64 qw; |
116 | |
117 | qw = pFt -> dwHighDateTime; |
118 | qw <<= 32; |
119 | qw |= pFt -> dwLowDateTime; |
120 | |
121 | return qw; |
270a5d4e |
122 | } |
7fd59977 |
123 | |
124 | //======================================================================= |
125 | //function : GetProcessCPU |
270a5d4e |
126 | //purpose : |
7fd59977 |
127 | //======================================================================= |
2da51263 |
128 | void OSD_Chronometer::GetProcessCPU (Standard_Real& theUserSeconds, |
129 | Standard_Real& theSystemSeconds) |
7fd59977 |
130 | { |
742cc8b0 |
131 | #ifndef OCCT_UWP |
7fd59977 |
132 | FILETIME ftStart, ftExit, ftKernel, ftUser; |
133 | ::GetProcessTimes (GetCurrentProcess(), &ftStart, &ftExit, &ftKernel, &ftUser); |
2da51263 |
134 | theUserSeconds = 0.0000001 * EncodeFILETIME (&ftUser); |
135 | theSystemSeconds = 0.0000001 * EncodeFILETIME (&ftKernel); |
742cc8b0 |
136 | #else |
2da51263 |
137 | theUserSeconds = 0.0; |
138 | theSystemSeconds = 0.0; |
742cc8b0 |
139 | #endif |
7fd59977 |
140 | } |
141 | |
142 | //======================================================================= |
143 | //function : GetThreadCPU |
270a5d4e |
144 | //purpose : |
7fd59977 |
145 | //======================================================================= |
2da51263 |
146 | void OSD_Chronometer::GetThreadCPU (Standard_Real& theUserSeconds, |
147 | Standard_Real& theSystemSeconds) |
7fd59977 |
148 | { |
742cc8b0 |
149 | #ifndef OCCT_UWP |
7fd59977 |
150 | FILETIME ftStart, ftExit, ftKernel, ftUser; |
151 | ::GetThreadTimes (GetCurrentThread(), &ftStart, &ftExit, &ftKernel, &ftUser); |
2da51263 |
152 | theUserSeconds = 0.0000001 * EncodeFILETIME (&ftUser); |
153 | theSystemSeconds = 0.0000001 * EncodeFILETIME (&ftKernel); |
742cc8b0 |
154 | #else |
2da51263 |
155 | theUserSeconds = 0.0; |
156 | theSystemSeconds = 0.0; |
742cc8b0 |
157 | #endif |
7fd59977 |
158 | } |
159 | |
57c28b61 |
160 | #endif /* _WIN32 */ |
7fd59977 |
161 | |
7fd59977 |
162 | //======================================================================= |
163 | //function : OSD_Chronometer |
270a5d4e |
164 | //purpose : |
7fd59977 |
165 | //======================================================================= |
2da51263 |
166 | OSD_Chronometer::OSD_Chronometer (Standard_Boolean theThisThreadOnly) |
167 | : myStartCpuUser (0.0), |
168 | myStartCpuSys (0.0), |
169 | myCumulCpuUser (0.0), |
170 | myCumulCpuSys (0.0), |
171 | myIsStopped (Standard_True), |
172 | myIsThreadOnly (theThisThreadOnly) |
7fd59977 |
173 | { |
2da51263 |
174 | // |
7fd59977 |
175 | } |
176 | |
177 | //======================================================================= |
6da30ff1 |
178 | //function : ~OSD_Chronometer |
179 | //purpose : Destructor |
7fd59977 |
180 | //======================================================================= |
6da30ff1 |
181 | OSD_Chronometer::~OSD_Chronometer() |
7fd59977 |
182 | { |
183 | } |
184 | |
185 | //======================================================================= |
186 | //function : Reset |
270a5d4e |
187 | //purpose : |
7fd59977 |
188 | //======================================================================= |
189 | void OSD_Chronometer::Reset () |
190 | { |
2da51263 |
191 | myIsStopped = Standard_True; |
192 | myStartCpuUser = myStartCpuSys = 0.; |
193 | myCumulCpuUser = myCumulCpuSys = 0.; |
7fd59977 |
194 | } |
195 | |
44fae8b1 |
196 | |
197 | //======================================================================= |
198 | //function : Restart |
199 | //purpose : |
200 | //======================================================================= |
201 | void OSD_Chronometer::Restart () |
202 | { |
6b55f8e3 |
203 | Reset(); |
44fae8b1 |
204 | Start(); |
205 | } |
206 | |
7fd59977 |
207 | //======================================================================= |
208 | //function : Stop |
270a5d4e |
209 | //purpose : |
7fd59977 |
210 | //======================================================================= |
2da51263 |
211 | void OSD_Chronometer::Stop() |
7fd59977 |
212 | { |
2da51263 |
213 | if (!myIsStopped) |
214 | { |
7fd59977 |
215 | Standard_Real Curr_user, Curr_sys; |
2da51263 |
216 | if (myIsThreadOnly) |
7fd59977 |
217 | GetThreadCPU (Curr_user, Curr_sys); |
218 | else |
219 | GetProcessCPU (Curr_user, Curr_sys); |
220 | |
2da51263 |
221 | myCumulCpuUser += Curr_user - myStartCpuUser; |
222 | myCumulCpuSys += Curr_sys - myStartCpuSys; |
7fd59977 |
223 | |
2da51263 |
224 | myIsStopped = Standard_True; |
270a5d4e |
225 | } |
7fd59977 |
226 | } |
227 | |
228 | //======================================================================= |
229 | //function : Start |
270a5d4e |
230 | //purpose : |
7fd59977 |
231 | //======================================================================= |
270a5d4e |
232 | void OSD_Chronometer::Start () |
7fd59977 |
233 | { |
2da51263 |
234 | if (myIsStopped) |
235 | { |
236 | if (myIsThreadOnly) |
237 | GetThreadCPU (myStartCpuUser, myStartCpuSys); |
7fd59977 |
238 | else |
2da51263 |
239 | GetProcessCPU (myStartCpuUser, myStartCpuSys); |
270a5d4e |
240 | |
2da51263 |
241 | myIsStopped = Standard_False; |
270a5d4e |
242 | } |
7fd59977 |
243 | } |
244 | |
245 | //======================================================================= |
246 | //function : Show |
270a5d4e |
247 | //purpose : |
7fd59977 |
248 | //======================================================================= |
7e7bbb3a |
249 | void OSD_Chronometer::Show() const |
7fd59977 |
250 | { |
2da51263 |
251 | Show (std::cout); |
7fd59977 |
252 | } |
253 | |
254 | //======================================================================= |
255 | //function : Show |
270a5d4e |
256 | //purpose : |
7fd59977 |
257 | //======================================================================= |
2da51263 |
258 | void OSD_Chronometer::Show (Standard_OStream& theOStream) const |
7fd59977 |
259 | { |
2da51263 |
260 | Standard_Real aCumulUserSec = 0.0, aCumulSysSec = 0.0; |
261 | Show (aCumulUserSec, aCumulSysSec); |
262 | std::streamsize prec = theOStream.precision (12); |
263 | theOStream << "CPU user time: " << aCumulUserSec << " seconds\n"; |
264 | theOStream << "CPU system time: " << aCumulSysSec << " seconds\n"; |
265 | theOStream.precision (prec); |
7fd59977 |
266 | } |
267 | |
268 | //======================================================================= |
269 | //function : Show |
2da51263 |
270 | //purpose : |
7fd59977 |
271 | //======================================================================= |
2da51263 |
272 | void OSD_Chronometer::Show (Standard_Real& theUserSec, Standard_Real& theSystemSec) const |
7fd59977 |
273 | { |
2da51263 |
274 | theUserSec = myCumulCpuUser; |
275 | theSystemSec = myCumulCpuSys; |
276 | if (myIsStopped) |
7e7bbb3a |
277 | { |
278 | return; |
279 | } |
280 | |
281 | Standard_Real aCurrUser, aCurrSys; |
2da51263 |
282 | if (myIsThreadOnly) |
7e7bbb3a |
283 | GetThreadCPU (aCurrUser, aCurrSys); |
284 | else |
285 | GetProcessCPU (aCurrUser, aCurrSys); |
7fd59977 |
286 | |
2da51263 |
287 | theUserSec += aCurrUser - myStartCpuUser; |
288 | theSystemSec += aCurrSys - myStartCpuSys; |
7e7bbb3a |
289 | } |