OLD | NEW |
| (Empty) |
1 // Copyright 2013 the V8 project authors. All rights reserved. | |
2 // Redistribution and use in source and binary forms, with or without | |
3 // modification, are permitted provided that the following conditions are | |
4 // met: | |
5 // | |
6 // * Redistributions of source code must retain the above copyright | |
7 // notice, this list of conditions and the following disclaimer. | |
8 // * Redistributions in binary form must reproduce the above | |
9 // copyright notice, this list of conditions and the following | |
10 // disclaimer in the documentation and/or other materials provided | |
11 // with the distribution. | |
12 // * Neither the name of Google Inc. nor the names of its | |
13 // contributors may be used to endorse or promote products derived | |
14 // from this software without specific prior written permission. | |
15 // | |
16 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | |
17 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | |
18 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | |
19 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT | |
20 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | |
21 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |
22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, | |
23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | |
24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | |
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | |
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
27 | |
28 #include "src/v8.h" | |
29 #include "test/cctest/cctest.h" | |
30 | |
31 #if V8_OS_POSIX | |
32 #include <sys/time.h> // NOLINT | |
33 #endif | |
34 | |
35 #if V8_OS_WIN | |
36 #include "src/base/win32-headers.h" | |
37 #endif | |
38 | |
39 using namespace v8::base; | |
40 using namespace v8::internal; | |
41 | |
42 | |
43 TEST(TimeDeltaFromAndIn) { | |
44 CHECK(TimeDelta::FromDays(2) == TimeDelta::FromHours(48)); | |
45 CHECK(TimeDelta::FromHours(3) == TimeDelta::FromMinutes(180)); | |
46 CHECK(TimeDelta::FromMinutes(2) == TimeDelta::FromSeconds(120)); | |
47 CHECK(TimeDelta::FromSeconds(2) == TimeDelta::FromMilliseconds(2000)); | |
48 CHECK(TimeDelta::FromMilliseconds(2) == TimeDelta::FromMicroseconds(2000)); | |
49 CHECK_EQ(static_cast<int>(13), TimeDelta::FromDays(13).InDays()); | |
50 CHECK_EQ(static_cast<int>(13), TimeDelta::FromHours(13).InHours()); | |
51 CHECK_EQ(static_cast<int>(13), TimeDelta::FromMinutes(13).InMinutes()); | |
52 CHECK_EQ(static_cast<int64_t>(13), TimeDelta::FromSeconds(13).InSeconds()); | |
53 CHECK_EQ(13.0, TimeDelta::FromSeconds(13).InSecondsF()); | |
54 CHECK_EQ(static_cast<int64_t>(13), | |
55 TimeDelta::FromMilliseconds(13).InMilliseconds()); | |
56 CHECK_EQ(13.0, TimeDelta::FromMilliseconds(13).InMillisecondsF()); | |
57 CHECK_EQ(static_cast<int64_t>(13), | |
58 TimeDelta::FromMicroseconds(13).InMicroseconds()); | |
59 } | |
60 | |
61 | |
62 #if V8_OS_MACOSX | |
63 TEST(TimeDeltaFromMachTimespec) { | |
64 TimeDelta null = TimeDelta(); | |
65 CHECK(null == TimeDelta::FromMachTimespec(null.ToMachTimespec())); | |
66 TimeDelta delta1 = TimeDelta::FromMilliseconds(42); | |
67 CHECK(delta1 == TimeDelta::FromMachTimespec(delta1.ToMachTimespec())); | |
68 TimeDelta delta2 = TimeDelta::FromDays(42); | |
69 CHECK(delta2 == TimeDelta::FromMachTimespec(delta2.ToMachTimespec())); | |
70 } | |
71 #endif | |
72 | |
73 | |
74 TEST(TimeJsTime) { | |
75 Time t = Time::FromJsTime(700000.3); | |
76 CHECK_EQ(700000.3, t.ToJsTime()); | |
77 } | |
78 | |
79 | |
80 #if V8_OS_POSIX | |
81 TEST(TimeFromTimespec) { | |
82 Time null; | |
83 CHECK(null.IsNull()); | |
84 CHECK(null == Time::FromTimespec(null.ToTimespec())); | |
85 Time now = Time::Now(); | |
86 CHECK(now == Time::FromTimespec(now.ToTimespec())); | |
87 Time now_sys = Time::NowFromSystemTime(); | |
88 CHECK(now_sys == Time::FromTimespec(now_sys.ToTimespec())); | |
89 Time unix_epoch = Time::UnixEpoch(); | |
90 CHECK(unix_epoch == Time::FromTimespec(unix_epoch.ToTimespec())); | |
91 Time max = Time::Max(); | |
92 CHECK(max.IsMax()); | |
93 CHECK(max == Time::FromTimespec(max.ToTimespec())); | |
94 } | |
95 | |
96 | |
97 TEST(TimeFromTimeval) { | |
98 Time null; | |
99 CHECK(null.IsNull()); | |
100 CHECK(null == Time::FromTimeval(null.ToTimeval())); | |
101 Time now = Time::Now(); | |
102 CHECK(now == Time::FromTimeval(now.ToTimeval())); | |
103 Time now_sys = Time::NowFromSystemTime(); | |
104 CHECK(now_sys == Time::FromTimeval(now_sys.ToTimeval())); | |
105 Time unix_epoch = Time::UnixEpoch(); | |
106 CHECK(unix_epoch == Time::FromTimeval(unix_epoch.ToTimeval())); | |
107 Time max = Time::Max(); | |
108 CHECK(max.IsMax()); | |
109 CHECK(max == Time::FromTimeval(max.ToTimeval())); | |
110 } | |
111 #endif | |
112 | |
113 | |
114 #if V8_OS_WIN | |
115 TEST(TimeFromFiletime) { | |
116 Time null; | |
117 CHECK(null.IsNull()); | |
118 CHECK(null == Time::FromFiletime(null.ToFiletime())); | |
119 Time now = Time::Now(); | |
120 CHECK(now == Time::FromFiletime(now.ToFiletime())); | |
121 Time now_sys = Time::NowFromSystemTime(); | |
122 CHECK(now_sys == Time::FromFiletime(now_sys.ToFiletime())); | |
123 Time unix_epoch = Time::UnixEpoch(); | |
124 CHECK(unix_epoch == Time::FromFiletime(unix_epoch.ToFiletime())); | |
125 Time max = Time::Max(); | |
126 CHECK(max.IsMax()); | |
127 CHECK(max == Time::FromFiletime(max.ToFiletime())); | |
128 } | |
129 #endif | |
130 | |
131 | |
132 TEST(TimeTicksIsMonotonic) { | |
133 TimeTicks previous_normal_ticks; | |
134 TimeTicks previous_highres_ticks; | |
135 ElapsedTimer timer; | |
136 timer.Start(); | |
137 while (!timer.HasExpired(TimeDelta::FromMilliseconds(100))) { | |
138 TimeTicks normal_ticks = TimeTicks::Now(); | |
139 TimeTicks highres_ticks = TimeTicks::HighResolutionNow(); | |
140 CHECK_GE(normal_ticks, previous_normal_ticks); | |
141 CHECK_GE((normal_ticks - previous_normal_ticks).InMicroseconds(), 0); | |
142 CHECK_GE(highres_ticks, previous_highres_ticks); | |
143 CHECK_GE((highres_ticks - previous_highres_ticks).InMicroseconds(), 0); | |
144 previous_normal_ticks = normal_ticks; | |
145 previous_highres_ticks = highres_ticks; | |
146 } | |
147 } | |
148 | |
149 | |
150 template <typename T> | |
151 static void ResolutionTest(T (*Now)(), TimeDelta target_granularity) { | |
152 // We're trying to measure that intervals increment in a VERY small amount | |
153 // of time -- according to the specified target granularity. Unfortunately, | |
154 // if we happen to have a context switch in the middle of our test, the | |
155 // context switch could easily exceed our limit. So, we iterate on this | |
156 // several times. As long as we're able to detect the fine-granularity | |
157 // timers at least once, then the test has succeeded. | |
158 static const TimeDelta kExpirationTimeout = TimeDelta::FromSeconds(1); | |
159 ElapsedTimer timer; | |
160 timer.Start(); | |
161 TimeDelta delta; | |
162 do { | |
163 T start = Now(); | |
164 T now = start; | |
165 // Loop until we can detect that the clock has changed. Non-HighRes timers | |
166 // will increment in chunks, i.e. 15ms. By spinning until we see a clock | |
167 // change, we detect the minimum time between measurements. | |
168 do { | |
169 now = Now(); | |
170 delta = now - start; | |
171 } while (now <= start); | |
172 CHECK_NE(static_cast<int64_t>(0), delta.InMicroseconds()); | |
173 } while (delta > target_granularity && !timer.HasExpired(kExpirationTimeout)); | |
174 CHECK_LE(delta, target_granularity); | |
175 } | |
176 | |
177 | |
178 TEST(TimeNowResolution) { | |
179 // We assume that Time::Now() has at least 16ms resolution. | |
180 static const TimeDelta kTargetGranularity = TimeDelta::FromMilliseconds(16); | |
181 ResolutionTest<Time>(&Time::Now, kTargetGranularity); | |
182 } | |
183 | |
184 | |
185 TEST(TimeTicksNowResolution) { | |
186 // We assume that TimeTicks::Now() has at least 16ms resolution. | |
187 static const TimeDelta kTargetGranularity = TimeDelta::FromMilliseconds(16); | |
188 ResolutionTest<TimeTicks>(&TimeTicks::Now, kTargetGranularity); | |
189 } | |
190 | |
191 | |
192 TEST(TimeTicksHighResolutionNowResolution) { | |
193 if (!TimeTicks::IsHighResolutionClockWorking()) return; | |
194 | |
195 // We assume that TimeTicks::HighResolutionNow() has sub-ms resolution. | |
196 static const TimeDelta kTargetGranularity = TimeDelta::FromMilliseconds(1); | |
197 ResolutionTest<TimeTicks>(&TimeTicks::HighResolutionNow, kTargetGranularity); | |
198 } | |
OLD | NEW |