// Copyright 2017 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 <memory>
#include <utility>

#include "base/bind.h"
#include "base/sequenced_task_runner.h"
#include "base/synchronization/waitable_event.h"
#include "base/test/task_environment.h"
#include "base/threading/thread.h"
#include "media/audio/alive_checker.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace media {

namespace {
int kCheckIntervalMs = 10;
int kNotifyIntervalMs = 7;
int kTimeoutMs = 50;
}  // namespace

class MockPowerObserverHelper : public PowerObserverHelper {
 public:
  MockPowerObserverHelper(scoped_refptr<base::SequencedTaskRunner> task_runner,
                          base::RepeatingClosure suspend_callback,
                          base::RepeatingClosure resume_callback)

      : PowerObserverHelper(std::move(task_runner),
                            std::move(suspend_callback),
                            std::move(resume_callback)) {}

  bool IsSuspending() const override {
    DCHECK(TaskRunnerForTesting()->RunsTasksInCurrentSequence());
    return is_suspending_;
  }

  void Suspend() {
    DCHECK(TaskRunnerForTesting()->RunsTasksInCurrentSequence());
    is_suspending_ = true;
    SuspendCallbackForTesting()->Run();
  }

  void Resume() {
    DCHECK(TaskRunnerForTesting()->RunsTasksInCurrentSequence());
    is_suspending_ = false;
    ResumeCallbackForTesting()->Run();
  }

 private:
  bool is_suspending_ = false;
};

class AliveCheckerTest : public testing::Test {
 public:
  AliveCheckerTest()
      : alive_checker_thread_("AliveCheckerThread"),
        detected_dead_event_(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED) {
    alive_checker_thread_.StartAndWaitForTesting();
  }

  void OnDetectedDead() {
    EXPECT_TRUE(alive_checker_thread_.task_runner()->BelongsToCurrentThread());
    detected_dead_event_.Signal();
  }

  std::unique_ptr<PowerObserverHelper> CreatePowerObserverHelper(
      scoped_refptr<base::SequencedTaskRunner> task_runner,
      base::RepeatingClosure suspend_callback,
      base::RepeatingClosure resume_callback) {
    std::unique_ptr<MockPowerObserverHelper> mock_power_observer_helper =
        std::make_unique<MockPowerObserverHelper>(std::move(task_runner),
                                                  std::move(suspend_callback),
                                                  std::move(resume_callback));
    mock_power_observer_helper_ = mock_power_observer_helper.get();
    return mock_power_observer_helper;
  }

 protected:
  ~AliveCheckerTest() override {
    base::WaitableEvent done(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED);
    alive_checker_thread_.task_runner()->PostTask(
        FROM_HERE,
        base::BindOnce(&AliveCheckerTest::ResetAliveCheckerOnAliveCheckerThread,
                       base::Unretained(this), &done));
    done.Wait();
  }

  void CreateAliveChecker(bool stop_at_first_alive_notification,
                          bool pause_check_during_suspend) {
    base::WaitableEvent done(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED);
    alive_checker_thread_.task_runner()->PostTask(
        FROM_HERE,
        base::BindOnce(
            &AliveCheckerTest::CreateAliveCheckerOnAliveCheckerThread,
            base::Unretained(this), stop_at_first_alive_notification,
            pause_check_during_suspend, &done));
    done.Wait();
  }

  void StartAliveChecker() {
    alive_checker_thread_.task_runner()->PostTask(
        FROM_HERE, base::BindOnce(&AliveChecker::Start,
                                  base::Unretained(alive_checker_.get())));
  }

  void StopAliveChecker() {
    alive_checker_thread_.task_runner()->PostTask(
        FROM_HERE, base::BindOnce(&AliveChecker::Stop,
                                  base::Unretained(alive_checker_.get())));
  }

  // Notifies |alive_checker_| that we're alive, and if
  // |remaining_notifications| > 1, posts a delayed task to itself on
  // |alive_checker_thread_| with |remaining_notifications| decreased by 1. Can
  // be called on any task runner.
  void NotifyAliveMultipleTimes(int remaining_notifications,
                                base::TimeDelta delay) {
    alive_checker_->NotifyAlive();
    if (remaining_notifications > 1) {
      alive_checker_thread_.task_runner()->PostDelayedTask(
          FROM_HERE,
          base::BindOnce(&AliveCheckerTest::NotifyAliveMultipleTimes,
                         base::Unretained(this), remaining_notifications - 1,
                         delay),
          delay);
    }
  }

  void WaitUntilDetectedDead() {
    detected_dead_event_.Wait();
    detected_dead_event_.Reset();
  }

  // Returns true if the dead callback (AliveCheckerTest::OnDetectedDead) is run
  // by the AliveChecker, false if timed out.
  bool WaitUntilDetectedDeadWithTimeout(base::TimeDelta timeout) {
    bool signaled = detected_dead_event_.TimedWait(timeout);
    detected_dead_event_.Reset();
    return signaled;
  }

  // Calls AliveChecker::DetectedDead() on the |alive_checker_thread_| and
  // returns the result.
  bool GetDetectedDead() {
    bool detected_dead = false;
    base::WaitableEvent done(base::WaitableEvent::ResetPolicy::MANUAL,
                             base::WaitableEvent::InitialState::NOT_SIGNALED);
    alive_checker_thread_.task_runner()->PostTask(
        FROM_HERE,
        base::BindOnce(&AliveCheckerTest::GetDetectedDeadOnAliveCheckerThread,
                       base::Unretained(this), &detected_dead, &done));
    done.Wait();
    return detected_dead;
  }

  // The test task environment.
  base::test::TaskEnvironment task_environment_;

  // The thread the checker is run on.
  base::Thread alive_checker_thread_;

  // AliveChecker under test.
  std::unique_ptr<AliveChecker> alive_checker_;

  // Mocks suspend status. Set in CreatePowerObserverHelper, owned by
  // |alive_checker_|.
  MockPowerObserverHelper* mock_power_observer_helper_;

 private:
  void CreateAliveCheckerOnAliveCheckerThread(
      bool stop_at_first_alive_notification,
      bool pause_check_during_suspend,
      base::WaitableEvent* done) {
    EXPECT_TRUE(alive_checker_thread_.task_runner()->BelongsToCurrentThread());

    if (pause_check_during_suspend) {
      alive_checker_ = std::make_unique<AliveChecker>(
          base::BindRepeating(&AliveCheckerTest::OnDetectedDead,
                              base::Unretained(this)),
          base::Milliseconds(kCheckIntervalMs), base::Milliseconds(kTimeoutMs),
          stop_at_first_alive_notification,
          base::BindOnce(&AliveCheckerTest::CreatePowerObserverHelper,
                         base::Unretained(this)));
    } else {
      alive_checker_ = std::make_unique<AliveChecker>(
          base::BindRepeating(&AliveCheckerTest::OnDetectedDead,
                              base::Unretained(this)),
          base::Milliseconds(kCheckIntervalMs), base::Milliseconds(kTimeoutMs),
          stop_at_first_alive_notification, false);
    }

    done->Signal();
  }

  void GetDetectedDeadOnAliveCheckerThread(bool* detected_dead,
                                           base::WaitableEvent* done) {
    EXPECT_TRUE(alive_checker_thread_.task_runner()->BelongsToCurrentThread());
    *detected_dead = alive_checker_->DetectedDead();
    done->Signal();
  }

  void ResetAliveCheckerOnAliveCheckerThread(base::WaitableEvent* done) {
    EXPECT_TRUE(alive_checker_thread_.task_runner()->BelongsToCurrentThread());
    alive_checker_.reset();
    done->Signal();
  }

  // Event to signal that we got a dead detection callback.
  base::WaitableEvent detected_dead_event_;

  DISALLOW_COPY_AND_ASSIGN(AliveCheckerTest);
};

// Start and Stop the checker, verify that we get no dead detection.
// TODO(crbug.com/789804): Fix the test not to be flaky, e.g. by switching to
// using a mocked clock, and re-enable it.
TEST_F(AliveCheckerTest, DISABLED_StartStop) {
  CreateAliveChecker(false, false);

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  StopAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Start the checker, don't send alive notifications, and run until it detects
// dead. Verify that it only detects once. Repeat once.
TEST_F(AliveCheckerTest, NoAliveNotificationsDetectTwice) {
  CreateAliveChecker(false, false);

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());

  // Verify that AliveChecker doesn't detect (runs the callback) a second time.
  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this. The detect state should still be that we have detected
  // dead.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_TRUE(GetDetectedDead());

  // Start again, the detect state should be reset.
  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Start the checker, notify that the client is alive several times, then stop
// the checker. Verify that it doesn't detect dead.
// TODO(crbug.com/789804): Fix the test not to be flaky, e.g. by switching to
// using a mocked clock, and re-enable it.
TEST_F(AliveCheckerTest, DISABLED_NotifyThenStop) {
  CreateAliveChecker(false, false);

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  NotifyAliveMultipleTimes(10, base::Milliseconds(kNotifyIntervalMs));
  EXPECT_FALSE(GetDetectedDead());

  StopAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Start the checker, notify that the client is alive several times, then
// run until detection. Repeat once.
// TODO(crbug.com/789804): Fix the test not to be flaky, e.g. by switching to
// using a mocked clock, and re-enable it.
TEST_F(AliveCheckerTest, DISABLED_NotifyThenDetectDead) {
  CreateAliveChecker(false, false);

  StartAliveChecker();
  NotifyAliveMultipleTimes(10, base::Milliseconds(kNotifyIntervalMs));
  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());
  NotifyAliveMultipleTimes(10, base::Milliseconds(kNotifyIntervalMs));
  EXPECT_FALSE(GetDetectedDead());
  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification. Start it and notify
// that the client is alive once. Verify that we get no dead detection.
TEST_F(AliveCheckerTest, StopAtFirstAliveNotification_DoNotify) {
  CreateAliveChecker(true, false);

  StartAliveChecker();
  alive_checker_->NotifyAlive();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification. Start it and run until
// it detects dead.
TEST_F(AliveCheckerTest, StopAtFirstAliveNotification_DontNotify) {
  CreateAliveChecker(true, false);
  StartAliveChecker();
  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Setup the checker to pause checking when suspended. Start the checker, don't
// send alive notifications, and run until it detects dead. Start it again and
// notify that the client is alive several times. Suspend and verify that it
// doesn't detect dead. Resume and run until detected dead.
// TODO(crbug.com/789804): Fix the test not to be flaky, e.g. by switching to
// using a mocked clock, and re-enable it.
TEST_F(AliveCheckerTest, DISABLED_SuspendResume_StartBeforeSuspend) {
  CreateAliveChecker(false, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();
  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  NotifyAliveMultipleTimes(10, base::Milliseconds(kNotifyIntervalMs));

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Setup the checker to pause checking when suspended. Suspend and verify that
// it doesn't detect dead. Start the checker, don't send alive notifications,
// and and verify that it doesn't detect dead. Resume and run until it detects
// dead.
TEST_F(AliveCheckerTest, SuspendResume_StartBetweenSuspendAndResume) {
  CreateAliveChecker(false, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  StartAliveChecker();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification and pause checking when
// suspended. Start the checker, send one alive notifications, and verify it
// doesn't detect dead. Suspend and verify that it doesn't detect dead. Resume
// and and verify that it doesn't detect dead.
TEST_F(AliveCheckerTest, SuspendResumeWithAutoStop_NotifyBeforeSuspend) {
  CreateAliveChecker(true, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();
  alive_checker_->NotifyAlive();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification and pause checking when
// suspended. Start the checker, send one alive notifications, and verify it
// doesn't detect dead. Start it again, suspend and verify that it doesn't
// detect dead. Resume and run until detected dead.
TEST_F(AliveCheckerTest,
       SuspendResumeWithAutoStop_NotifyBeforeSuspendAndRestart) {
  CreateAliveChecker(true, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();
  alive_checker_->NotifyAlive();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  StartAliveChecker();
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification and pause checking when
// suspended. Start the checker, suspend. Send one alive notification and
// verify it doesn't detected dead. Resume and verify it doesn't detected dead.
TEST_F(AliveCheckerTest,
       SuspendResumeWithAutoStop_NotifyBetweenSuspendAndResume) {
  CreateAliveChecker(true, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  alive_checker_->NotifyAlive();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification and pause checking when
// suspended. Start the checker, suspend, resume, send one alive notification
// and verify it doesn't detected dead.
TEST_F(AliveCheckerTest, SuspendResumeWithAutoStop_NotifyAfterResume) {
  CreateAliveChecker(true, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  alive_checker_->NotifyAlive();

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());
}

// Setup the checker to stop at first alive notification and pause checking when
// suspended. Start the checker suspend, and and verify it doesn't detected
// dead. Resume and run until it detects dead.
TEST_F(AliveCheckerTest, SuspendResumeWithAutoStop_DontNotify) {
  CreateAliveChecker(true, true);
  ASSERT_TRUE(mock_power_observer_helper_);

  StartAliveChecker();

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Suspend,
                                base::Unretained(mock_power_observer_helper_)));

  // It can take up to the timeout + the check interval until detection. Add a
  // margin to this.
  EXPECT_FALSE(WaitUntilDetectedDeadWithTimeout(
      base::Milliseconds(kTimeoutMs + kCheckIntervalMs + 10)));
  EXPECT_FALSE(GetDetectedDead());

  alive_checker_thread_.task_runner()->PostTask(
      FROM_HERE, base::BindOnce(&MockPowerObserverHelper::Resume,
                                base::Unretained(mock_power_observer_helper_)));

  WaitUntilDetectedDead();
  EXPECT_TRUE(GetDetectedDead());
}

}  // namespace media
