summaryrefslogtreecommitdiffstats
path: root/base/time_unittest_win.cc
diff options
context:
space:
mode:
authordeanm@google.com <deanm@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2008-09-02 08:28:37 +0000
committerdeanm@google.com <deanm@google.com@0039d316-1c4b-4281-b951-d872f2087c98>2008-09-02 08:28:37 +0000
commit5f6eee53a4ba6995b68a8ec6f22d3281529060c8 (patch)
tree1464c7ca7fdaaa3b7f387da90db9667988c1f25d /base/time_unittest_win.cc
parent38f70a3e2ade7049c09831ed8f5b8ea90d9e68d6 (diff)
downloadchromium_src-5f6eee53a4ba6995b68a8ec6f22d3281529060c8.zip
chromium_src-5f6eee53a4ba6995b68a8ec6f22d3281529060c8.tar.gz
chromium_src-5f6eee53a4ba6995b68a8ec6f22d3281529060c8.tar.bz2
Cleanup some Windows TimeTicks functions. Move TickTicks::Now and TicksTicks::UnreliableHighResNow to Singletons, which cleans up the code and removes some possible unsafe cross-thread access.
Move the Windows-specific rollover tests to time_unittests_win. git-svn-id: svn://svn.chromium.org/chrome/trunk/src@1633 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'base/time_unittest_win.cc')
-rw-r--r--base/time_unittest_win.cc102
1 files changed, 102 insertions, 0 deletions
diff --git a/base/time_unittest_win.cc b/base/time_unittest_win.cc
new file mode 100644
index 0000000..5b29db2
--- /dev/null
+++ b/base/time_unittest_win.cc
@@ -0,0 +1,102 @@
+// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <windows.h>
+#include <process.h>
+
+#include "base/time.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace {
+
+class MockTimeTicks : public TimeTicks {
+ public:
+ static int Ticker() {
+ return static_cast<int>(InterlockedIncrement(&ticker_));
+ }
+
+ static void InstallTicker() {
+ old_tick_function_ = tick_function_;
+ tick_function_ = reinterpret_cast<TickFunction>(&Ticker);
+ ticker_ = -5;
+ }
+
+ static void UninstallTicker() {
+ tick_function_ = old_tick_function_;
+ }
+
+ private:
+ static volatile LONG ticker_;
+ static TickFunction old_tick_function_;
+};
+
+volatile LONG MockTimeTicks::ticker_;
+MockTimeTicks::TickFunction MockTimeTicks::old_tick_function_;
+
+HANDLE g_rollover_test_start;
+
+unsigned __stdcall RolloverTestThreadMain(void* param) {
+ int64 counter = reinterpret_cast<int64>(param);
+ DWORD rv = WaitForSingleObject(g_rollover_test_start, INFINITE);
+ EXPECT_EQ(rv, WAIT_OBJECT_0);
+
+ TimeTicks last = TimeTicks::Now();
+ for (int index = 0; index < counter; index++) {
+ TimeTicks now = TimeTicks::Now();
+ int64 milliseconds = (now - last).InMilliseconds();
+ EXPECT_GT(milliseconds, 0);
+ EXPECT_LT(milliseconds, 250);
+ last = now;
+ }
+ return 0;
+}
+
+} // namespace
+
+TEST(TimeTicks, WinRollover) {
+ // The internal counter rolls over at ~49days. We'll use a mock
+ // timer to test this case.
+ // Basic test algorithm:
+ // 1) Set clock to rollover - N
+ // 2) Create N threads
+ // 3) Start the threads
+ // 4) Each thread loops through TimeTicks() N times
+ // 5) Each thread verifies integrity of result.
+
+ const int kThreads = 8;
+ // Use int64 so we can cast into a void* without a compiler warning.
+ const int64 kChecks = 10;
+
+ // It takes a lot of iterations to reproduce the bug!
+ // (See bug 1081395)
+ for (int loop = 0; loop < 4096; loop++) {
+ // Setup
+ MockTimeTicks::InstallTicker();
+ g_rollover_test_start = CreateEvent(0, TRUE, FALSE, 0);
+ HANDLE threads[kThreads];
+
+ for (int index = 0; index < kThreads; index++) {
+ void* argument = reinterpret_cast<void*>(kChecks);
+ unsigned thread_id;
+ threads[index] = reinterpret_cast<HANDLE>(
+ _beginthreadex(NULL, 0, RolloverTestThreadMain, argument, 0,
+ &thread_id));
+ EXPECT_NE((HANDLE)NULL, threads[index]);
+ }
+
+ // Start!
+ SetEvent(g_rollover_test_start);
+
+ // Wait for threads to finish
+ for (int index = 0; index < kThreads; index++) {
+ DWORD rv = WaitForSingleObject(threads[index], INFINITE);
+ EXPECT_EQ(rv, WAIT_OBJECT_0);
+ }
+
+ CloseHandle(g_rollover_test_start);
+
+ // Teardown
+ MockTimeTicks::UninstallTicker();
+ }
+}