OLD | NEW |
| (Empty) |
1 /* | |
2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. | |
3 * | |
4 * Use of this source code is governed by a BSD-style license | |
5 * that can be found in the LICENSE file in the root of the source | |
6 * tree. An additional intellectual property rights grant can be found | |
7 * in the file PATENTS. All contributing project authors may | |
8 * be found in the AUTHORS file in the root of the source tree. | |
9 */ | |
10 | |
11 // System independant wrapper for polling elapsed time in ms and us. | |
12 // The implementation works in the tick domain which can be mapped over to the | |
13 // time domain. | |
14 #ifndef WEBRTC_SYSTEM_WRAPPERS_INTERFACE_TICK_UTIL_H_ | |
15 #define WEBRTC_SYSTEM_WRAPPERS_INTERFACE_TICK_UTIL_H_ | |
16 | |
17 #if _WIN32 | |
18 // Note: The Windows header must always be included before mmsystem.h | |
19 #include <windows.h> | |
20 #include <mmsystem.h> | |
21 #elif WEBRTC_LINUX | |
22 #include <time.h> | |
23 #elif WEBRTC_MAC | |
24 #include <mach/mach_time.h> | |
25 #include <string.h> | |
26 #else | |
27 #include <sys/time.h> | |
28 #include <time.h> | |
29 #endif | |
30 | |
31 #include "webrtc/typedefs.h" | |
32 | |
33 namespace webrtc { | |
34 | |
35 class TickInterval; | |
36 | |
37 // Class representing the current time. | |
38 class TickTime { | |
39 public: | |
40 TickTime(); | |
41 explicit TickTime(int64_t ticks); | |
42 | |
43 // Current time in the tick domain. | |
44 static TickTime Now(); | |
45 | |
46 // Now in the time domain in ms. | |
47 static int64_t MillisecondTimestamp(); | |
48 | |
49 // Now in the time domain in us. | |
50 static int64_t MicrosecondTimestamp(); | |
51 | |
52 // Returns the number of ticks in the tick domain. | |
53 int64_t Ticks() const; | |
54 | |
55 static int64_t MillisecondsToTicks(const int64_t ms); | |
56 | |
57 static int64_t TicksToMilliseconds(const int64_t ticks); | |
58 | |
59 // Returns a TickTime that is ticks later than the passed TickTime. | |
60 friend TickTime operator+(const TickTime lhs, const int64_t ticks); | |
61 TickTime& operator+=(const int64_t& ticks); | |
62 | |
63 // Returns a TickInterval that is the difference in ticks beween rhs and lhs. | |
64 friend TickInterval operator-(const TickTime& lhs, const TickTime& rhs); | |
65 | |
66 // Call to engage the fake clock. This is useful for tests since relying on | |
67 // a real clock often makes the test flaky. | |
68 static void UseFakeClock(int64_t start_millisecond); | |
69 | |
70 // Advance the fake clock. Must be called after UseFakeClock. | |
71 static void AdvanceFakeClock(int64_t milliseconds); | |
72 | |
73 private: | |
74 static int64_t QueryOsForTicks(); | |
75 | |
76 static bool use_fake_clock_; | |
77 static int64_t fake_ticks_; | |
78 | |
79 int64_t ticks_; | |
80 }; | |
81 | |
82 // Represents a time delta in ticks. | |
83 class TickInterval { | |
84 public: | |
85 TickInterval(); | |
86 | |
87 int64_t Milliseconds() const; | |
88 int64_t Microseconds() const; | |
89 | |
90 // Returns the sum of two TickIntervals as a TickInterval. | |
91 friend TickInterval operator+(const TickInterval& lhs, | |
92 const TickInterval& rhs); | |
93 TickInterval& operator+=(const TickInterval& rhs); | |
94 | |
95 // Returns a TickInterval corresponding to rhs - lhs. | |
96 friend TickInterval operator-(const TickInterval& lhs, | |
97 const TickInterval& rhs); | |
98 TickInterval& operator-=(const TickInterval& rhs); | |
99 | |
100 friend bool operator>(const TickInterval& lhs, const TickInterval& rhs); | |
101 friend bool operator<=(const TickInterval& lhs, const TickInterval& rhs); | |
102 friend bool operator<(const TickInterval& lhs, const TickInterval& rhs); | |
103 friend bool operator>=(const TickInterval& lhs, const TickInterval& rhs); | |
104 | |
105 private: | |
106 explicit TickInterval(int64_t interval); | |
107 | |
108 friend class TickTime; | |
109 friend TickInterval operator-(const TickTime& lhs, const TickTime& rhs); | |
110 | |
111 private: | |
112 int64_t interval_; | |
113 }; | |
114 | |
115 inline TickInterval operator+(const TickInterval& lhs, | |
116 const TickInterval& rhs) { | |
117 return TickInterval(lhs.interval_ + rhs.interval_); | |
118 } | |
119 | |
120 inline TickInterval operator-(const TickInterval& lhs, | |
121 const TickInterval& rhs) { | |
122 return TickInterval(lhs.interval_ - rhs.interval_); | |
123 } | |
124 | |
125 inline TickInterval operator-(const TickTime& lhs, const TickTime& rhs) { | |
126 return TickInterval(lhs.ticks_ - rhs.ticks_); | |
127 } | |
128 | |
129 inline TickTime operator+(const TickTime lhs, const int64_t ticks) { | |
130 TickTime time = lhs; | |
131 time.ticks_ += ticks; | |
132 return time; | |
133 } | |
134 | |
135 inline bool operator>(const TickInterval& lhs, const TickInterval& rhs) { | |
136 return lhs.interval_ > rhs.interval_; | |
137 } | |
138 | |
139 inline bool operator<=(const TickInterval& lhs, const TickInterval& rhs) { | |
140 return lhs.interval_ <= rhs.interval_; | |
141 } | |
142 | |
143 inline bool operator<(const TickInterval& lhs, const TickInterval& rhs) { | |
144 return lhs.interval_ <= rhs.interval_; | |
145 } | |
146 | |
147 inline bool operator>=(const TickInterval& lhs, const TickInterval& rhs) { | |
148 return lhs.interval_ >= rhs.interval_; | |
149 } | |
150 | |
151 inline TickTime::TickTime() | |
152 : ticks_(0) { | |
153 } | |
154 | |
155 inline TickTime::TickTime(int64_t ticks) | |
156 : ticks_(ticks) { | |
157 } | |
158 | |
159 inline TickTime TickTime::Now() { | |
160 if (use_fake_clock_) | |
161 return TickTime(fake_ticks_); | |
162 else | |
163 return TickTime(QueryOsForTicks()); | |
164 } | |
165 | |
166 inline int64_t TickTime::MillisecondTimestamp() { | |
167 int64_t ticks = TickTime::Now().Ticks(); | |
168 #if _WIN32 | |
169 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
170 LARGE_INTEGER qpfreq; | |
171 QueryPerformanceFrequency(&qpfreq); | |
172 return (ticks * 1000) / qpfreq.QuadPart; | |
173 #else | |
174 return ticks; | |
175 #endif | |
176 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
177 return ticks / 1000000LL; | |
178 #else | |
179 return ticks / 1000LL; | |
180 #endif | |
181 } | |
182 | |
183 inline int64_t TickTime::MicrosecondTimestamp() { | |
184 int64_t ticks = TickTime::Now().Ticks(); | |
185 #if _WIN32 | |
186 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
187 LARGE_INTEGER qpfreq; | |
188 QueryPerformanceFrequency(&qpfreq); | |
189 return (ticks * 1000) / (qpfreq.QuadPart / 1000); | |
190 #else | |
191 return ticks * 1000LL; | |
192 #endif | |
193 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
194 return ticks / 1000LL; | |
195 #else | |
196 return ticks; | |
197 #endif | |
198 } | |
199 | |
200 inline int64_t TickTime::Ticks() const { | |
201 return ticks_; | |
202 } | |
203 | |
204 inline int64_t TickTime::MillisecondsToTicks(const int64_t ms) { | |
205 #if _WIN32 | |
206 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
207 LARGE_INTEGER qpfreq; | |
208 QueryPerformanceFrequency(&qpfreq); | |
209 return (qpfreq.QuadPart * ms) / 1000; | |
210 #else | |
211 return ms; | |
212 #endif | |
213 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
214 return ms * 1000000LL; | |
215 #else | |
216 return ms * 1000LL; | |
217 #endif | |
218 } | |
219 | |
220 inline int64_t TickTime::TicksToMilliseconds(const int64_t ticks) { | |
221 #if _WIN32 | |
222 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
223 LARGE_INTEGER qpfreq; | |
224 QueryPerformanceFrequency(&qpfreq); | |
225 return (ticks * 1000) / qpfreq.QuadPart; | |
226 #else | |
227 return ticks; | |
228 #endif | |
229 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
230 return ticks / 1000000LL; | |
231 #else | |
232 return ticks / 1000LL; | |
233 #endif | |
234 } | |
235 | |
236 inline TickTime& TickTime::operator+=(const int64_t& ticks) { | |
237 ticks_ += ticks; | |
238 return *this; | |
239 } | |
240 | |
241 inline TickInterval::TickInterval() : interval_(0) { | |
242 } | |
243 | |
244 inline TickInterval::TickInterval(const int64_t interval) | |
245 : interval_(interval) { | |
246 } | |
247 | |
248 inline int64_t TickInterval::Milliseconds() const { | |
249 #if _WIN32 | |
250 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
251 LARGE_INTEGER qpfreq; | |
252 QueryPerformanceFrequency(&qpfreq); | |
253 return (interval_ * 1000) / qpfreq.QuadPart; | |
254 #else | |
255 // interval_ is in ms | |
256 return interval_; | |
257 #endif | |
258 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
259 // interval_ is in ns | |
260 return interval_ / 1000000; | |
261 #else | |
262 // interval_ is usecs | |
263 return interval_ / 1000; | |
264 #endif | |
265 } | |
266 | |
267 inline int64_t TickInterval::Microseconds() const { | |
268 #if _WIN32 | |
269 #ifdef USE_QUERY_PERFORMANCE_COUNTER | |
270 LARGE_INTEGER qpfreq; | |
271 QueryPerformanceFrequency(&qpfreq); | |
272 return (interval_ * 1000000) / qpfreq.QuadPart; | |
273 #else | |
274 // interval_ is in ms | |
275 return interval_ * 1000LL; | |
276 #endif | |
277 #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) | |
278 // interval_ is in ns | |
279 return interval_ / 1000; | |
280 #else | |
281 // interval_ is usecs | |
282 return interval_; | |
283 #endif | |
284 } | |
285 | |
286 inline TickInterval& TickInterval::operator+=(const TickInterval& rhs) { | |
287 interval_ += rhs.interval_; | |
288 return *this; | |
289 } | |
290 | |
291 inline TickInterval& TickInterval::operator-=(const TickInterval& rhs) { | |
292 interval_ -= rhs.interval_; | |
293 return *this; | |
294 } | |
295 | |
296 } // namespace webrtc | |
297 | |
298 #endif // WEBRTC_SYSTEM_WRAPPERS_INTERFACE_TICK_UTIL_H_ | |
OLD | NEW |