// Copyright 2015 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/test/test_mock_time_task_runner.h"

#include "base/logging.h"
#include "base/memory/ref_counted.h"
#include "base/time/clock.h"
#include "base/time/tick_clock.h"

namespace base {

namespace {

// MockTickClock --------------------------------------------------------------

// TickClock that always returns the then-current mock time ticks of
// |task_runner| as the current time ticks.
class MockTickClock : public TickClock {
 public:
  explicit MockTickClock(
      scoped_refptr<const TestMockTimeTaskRunner> task_runner);

  // TickClock:
  TimeTicks NowTicks() override;

 private:
  scoped_refptr<const TestMockTimeTaskRunner> task_runner_;

  DISALLOW_COPY_AND_ASSIGN(MockTickClock);
};

MockTickClock::MockTickClock(
    scoped_refptr<const TestMockTimeTaskRunner> task_runner)
    : task_runner_(task_runner) {
}

TimeTicks MockTickClock::NowTicks() {
  return task_runner_->NowTicks();
}

// MockClock ------------------------------------------------------------------

// Clock that always returns the then-current mock time of |task_runner| as the
// current time.
class MockClock : public Clock {
 public:
  explicit MockClock(scoped_refptr<const TestMockTimeTaskRunner> task_runner);

  // Clock:
  Time Now() override;

 private:
  scoped_refptr<const TestMockTimeTaskRunner> task_runner_;

  DISALLOW_COPY_AND_ASSIGN(MockClock);
};

MockClock::MockClock(scoped_refptr<const TestMockTimeTaskRunner> task_runner)
    : task_runner_(task_runner) {
}

Time MockClock::Now() {
  return task_runner_->Now();
}

}  // namespace

// TestMockTimeTaskRunner -----------------------------------------------------

bool TestMockTimeTaskRunner::TemporalOrder::operator()(
    const TestPendingTask& first_task,
    const TestPendingTask& second_task) const {
  return first_task.GetTimeToRun() > second_task.GetTimeToRun();
}

TestMockTimeTaskRunner::TestMockTimeTaskRunner() : now_(Time::UnixEpoch()) {
}

TestMockTimeTaskRunner::~TestMockTimeTaskRunner() {
}

void TestMockTimeTaskRunner::FastForwardBy(TimeDelta delta) {
  DCHECK(thread_checker_.CalledOnValidThread());
  DCHECK_GE(delta, TimeDelta());

  const TimeTicks original_now_ticks = now_ticks_;
  ProcessAllTasksNoLaterThan(delta);
  ForwardClocksUntilTickTime(original_now_ticks + delta);
}

void TestMockTimeTaskRunner::RunUntilIdle() {
  DCHECK(thread_checker_.CalledOnValidThread());
  ProcessAllTasksNoLaterThan(TimeDelta());
}

void TestMockTimeTaskRunner::FastForwardUntilNoTasksRemain() {
  DCHECK(thread_checker_.CalledOnValidThread());
  ProcessAllTasksNoLaterThan(TimeDelta::Max());
}

Time TestMockTimeTaskRunner::Now() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return now_;
}

TimeTicks TestMockTimeTaskRunner::NowTicks() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return now_ticks_;
}

scoped_ptr<Clock> TestMockTimeTaskRunner::GetMockClock() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return make_scoped_ptr(new MockClock(this));
}

scoped_ptr<TickClock> TestMockTimeTaskRunner::GetMockTickClock() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return make_scoped_ptr(new MockTickClock(this));
}

bool TestMockTimeTaskRunner::HasPendingTask() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return !tasks_.empty();
}

size_t TestMockTimeTaskRunner::GetPendingTaskCount() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return tasks_.size();
}

TimeDelta TestMockTimeTaskRunner::NextPendingTaskDelay() const {
  DCHECK(thread_checker_.CalledOnValidThread());
  return tasks_.empty() ? TimeDelta::Max()
                        : tasks_.top().GetTimeToRun() - now_ticks_;
}

bool TestMockTimeTaskRunner::RunsTasksOnCurrentThread() const {
  return thread_checker_.CalledOnValidThread();
}

bool TestMockTimeTaskRunner::PostDelayedTask(
    const tracked_objects::Location& from_here,
    const Closure& task,
    TimeDelta delay) {
  AutoLock scoped_lock(tasks_lock_);
  tasks_.push(TestPendingTask(from_here, task, now_ticks_, delay,
                              TestPendingTask::NESTABLE));
  return true;
}

bool TestMockTimeTaskRunner::PostNonNestableDelayedTask(
    const tracked_objects::Location& from_here,
    const Closure& task,
    TimeDelta delay) {
  NOTREACHED();
  return false;
}

void TestMockTimeTaskRunner::OnBeforeSelectingTask() {
  // Empty default implementation.
}

void TestMockTimeTaskRunner::OnAfterTimePassed() {
  // Empty default implementation.
}

void TestMockTimeTaskRunner::OnAfterTaskRun() {
  // Empty default implementation.
}

void TestMockTimeTaskRunner::ProcessAllTasksNoLaterThan(TimeDelta max_delta) {
  DCHECK_GE(max_delta, TimeDelta());
  const TimeTicks original_now_ticks = now_ticks_;
  while (true) {
    OnBeforeSelectingTask();
    TestPendingTask task_info;
    if (!DequeueNextTask(original_now_ticks, max_delta, &task_info))
      break;
    // If tasks were posted with a negative delay, task_info.GetTimeToRun() will
    // be less than |now_ticks_|. ForwardClocksUntilTickTime() takes care of not
    // moving the clock backwards in this case.
    ForwardClocksUntilTickTime(task_info.GetTimeToRun());
    task_info.task.Run();
    OnAfterTaskRun();
  }
}

void TestMockTimeTaskRunner::ForwardClocksUntilTickTime(TimeTicks later_ticks) {
  if (later_ticks <= now_ticks_)
    return;

  now_ += later_ticks - now_ticks_;
  now_ticks_ = later_ticks;
  OnAfterTimePassed();
}

bool TestMockTimeTaskRunner::DequeueNextTask(const TimeTicks& reference,
                                             const TimeDelta& max_delta,
                                             TestPendingTask* next_task) {
  AutoLock scoped_lock(tasks_lock_);
  if (!tasks_.empty() &&
      (tasks_.top().GetTimeToRun() - reference) <= max_delta) {
    *next_task = tasks_.top();
    tasks_.pop();
    return true;
  }
  return false;
}

}  // namespace base
