123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138 |
- // Copyright (c) 2012 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 "base/threading/watchdog.h"
- #include "base/logging.h"
- #include "base/test/spin_wait.h"
- #include "base/threading/platform_thread.h"
- #include "base/time/time.h"
- #include "testing/gtest/include/gtest/gtest.h"
- namespace base {
- namespace {
- //------------------------------------------------------------------------------
- // Provide a derived class to facilitate testing.
- class WatchdogCounter : public Watchdog {
- public:
- WatchdogCounter(const TimeDelta& duration,
- const std::string& thread_watched_name,
- bool enabled)
- : Watchdog(duration, thread_watched_name, enabled),
- alarm_counter_(0) {
- }
- WatchdogCounter(const WatchdogCounter&) = delete;
- WatchdogCounter& operator=(const WatchdogCounter&) = delete;
- ~WatchdogCounter() override = default;
- void Alarm() override {
- alarm_counter_++;
- Watchdog::Alarm();
- }
- int alarm_counter() { return alarm_counter_; }
- private:
- int alarm_counter_;
- };
- class WatchdogTest : public testing::Test {
- public:
- void SetUp() override { Watchdog::ResetStaticData(); }
- };
- } // namespace
- //------------------------------------------------------------------------------
- // Actual tests
- // Minimal constructor/destructor test.
- TEST_F(WatchdogTest, StartupShutdownTest) {
- Watchdog watchdog1(Milliseconds(300), "Disabled", false);
- Watchdog watchdog2(Milliseconds(300), "Enabled", true);
- }
- // Test ability to call Arm and Disarm repeatedly.
- TEST_F(WatchdogTest, ArmDisarmTest) {
- Watchdog watchdog1(Milliseconds(300), "Disabled", false);
- watchdog1.Arm();
- watchdog1.Disarm();
- watchdog1.Arm();
- watchdog1.Disarm();
- Watchdog watchdog2(Milliseconds(300), "Enabled", true);
- watchdog2.Arm();
- watchdog2.Disarm();
- watchdog2.Arm();
- watchdog2.Disarm();
- }
- // Make sure a basic alarm fires when the time has expired.
- TEST_F(WatchdogTest, AlarmTest) {
- WatchdogCounter watchdog(Milliseconds(10), "Enabled", true);
- watchdog.Arm();
- SPIN_FOR_TIMEDELTA_OR_UNTIL_TRUE(Minutes(5), watchdog.alarm_counter() > 0);
- EXPECT_EQ(1, watchdog.alarm_counter());
- }
- // Make sure a basic alarm fires when the time has expired.
- TEST_F(WatchdogTest, AlarmPriorTimeTest) {
- WatchdogCounter watchdog(TimeDelta(), "Enabled2", true);
- // Set a time in the past.
- watchdog.ArmSomeTimeDeltaAgo(Seconds(2));
- // It should instantly go off, but certainly in less than 5 minutes.
- SPIN_FOR_TIMEDELTA_OR_UNTIL_TRUE(Minutes(5), watchdog.alarm_counter() > 0);
- EXPECT_EQ(1, watchdog.alarm_counter());
- }
- // Make sure a disable alarm does nothing, even if we arm it.
- TEST_F(WatchdogTest, ConstructorDisabledTest) {
- WatchdogCounter watchdog(Milliseconds(10), "Disabled", false);
- watchdog.Arm();
- // Alarm should not fire, as it was disabled.
- PlatformThread::Sleep(Milliseconds(500));
- EXPECT_EQ(0, watchdog.alarm_counter());
- }
- // Make sure Disarming will prevent firing, even after Arming.
- TEST_F(WatchdogTest, DisarmTest) {
- WatchdogCounter watchdog(Seconds(1), "Enabled3", true);
- TimeTicks start = TimeTicks::Now();
- watchdog.Arm();
- // Sleep a bit, but not past the alarm point.
- PlatformThread::Sleep(Milliseconds(100));
- watchdog.Disarm();
- TimeTicks end = TimeTicks::Now();
- if (end - start > Milliseconds(500)) {
- LOG(WARNING) << "100ms sleep took over 500ms, making the results of this "
- << "timing-sensitive test suspicious. Aborting now.";
- return;
- }
- // Alarm should not have fired before it was disarmed.
- EXPECT_EQ(0, watchdog.alarm_counter());
- // Sleep past the point where it would have fired if it wasn't disarmed,
- // and verify that it didn't fire.
- PlatformThread::Sleep(Seconds(1));
- EXPECT_EQ(0, watchdog.alarm_counter());
- // ...but even after disarming, we can still use the alarm...
- // Set a time greater than the timeout into the past.
- watchdog.ArmSomeTimeDeltaAgo(Seconds(10));
- // It should almost instantly go off, but certainly in less than 5 minutes.
- SPIN_FOR_TIMEDELTA_OR_UNTIL_TRUE(Minutes(5), watchdog.alarm_counter() > 0);
- EXPECT_EQ(1, watchdog.alarm_counter());
- }
- } // namespace base
|