// Copyright 2017 The Fuchsia 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 "real_loop.h"

#include <lib/async/cpp/task.h>
#include <lib/zx/clock.h>

namespace loop_fixture {

namespace {

bool RunGivenLoopWithTimeout(async::Loop* loop, zx::duration timeout) {
  // This cannot be a local variable because the delayed task below can execute
  // after this function returns.
  auto canceled = std::make_shared<bool>(false);
  bool timed_out = false;
  async::PostDelayedTask(
      loop->dispatcher(),
      [loop, canceled, &timed_out] {
        if (*canceled) {
          return;
        }
        timed_out = true;
        loop->Quit();
      },
      timeout);
  loop->Run();
  loop->ResetQuit();
  // Another task can call Quit() on the message loop, which exits the
  // message loop before the delayed task executes, in which case |timed_out| is
  // still false here because the delayed task hasn't run yet.
  // Since the message loop isn't destroyed then (as it usually would after
  // Quit()), and presumably can be reused after this function returns we
  // still need to prevent the delayed task to quit it again at some later time
  // using the canceled pointer.
  if (!timed_out) {
    *canceled = true;
  }
  return timed_out;
}

}  // namespace

RealLoop::RealLoop() : loop_(&kAsyncLoopConfigAttachToCurrentThread) {}

RealLoop::~RealLoop() = default;

async_dispatcher_t* RealLoop::dispatcher() { return loop_.dispatcher(); }

void RealLoop::RunLoop() {
  loop_.Run();
  loop_.ResetQuit();
}

bool RealLoop::RunLoopWithTimeout(zx::duration timeout) {
  return RunGivenLoopWithTimeout(&loop_, timeout);
}

bool RealLoop::RunLoopWithTimeoutOrUntil(fit::function<bool()> condition, zx::duration timeout,
                                         zx::duration step) {
  const zx::time timeout_deadline = zx::deadline_after(timeout);

  while (zx::clock::get_monotonic() < timeout_deadline && loop_.GetState() == ASYNC_LOOP_RUNNABLE) {
    if (condition()) {
      loop_.ResetQuit();
      return true;
    }

    if (step == zx::duration::infinite()) {
      // Performs a single unit of work, possibly blocking until there is work
      // to do or the timeout deadline arrives.
      loop_.Run(timeout_deadline, true);
    } else {
      // Performs work until the step deadline arrives.
      RunGivenLoopWithTimeout(&loop_, step);
    }
  }

  loop_.ResetQuit();
  return condition();
}

void RealLoop::RunLoopUntil(fit::function<bool()> condition, zx::duration step) {
  RunLoopWithTimeoutOrUntil(std::move(condition), zx::duration::infinite(), step);
}

void RealLoop::RunLoopUntilIdle() {
  loop_.RunUntilIdle();
  loop_.ResetQuit();
}

void RealLoop::QuitLoop() { loop_.Quit(); }

fit::closure RealLoop::QuitLoopClosure() {
  return [this] { loop_.Quit(); };
}

}  // namespace loop_fixture
