//===----------------------------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
//
// UNSUPPORTED: no-threads
// UNSUPPORTED: c++03, c++11, c++14, c++17

// template<class C>
// explicit stop_callback(stop_token&& st, C&& cb)
//   noexcept(is_nothrow_constructible_v<Callback, C>);

#include <atomic>
#include <cassert>
#include <chrono>
#include <stop_token>
#include <type_traits>
#include <utility>
#include <vector>

#include "make_test_thread.h"
#include "test_macros.h"

struct Cb {
  void operator()() const;
};

// Constraints: Callback and C satisfy constructible_from<Callback, C>.
static_assert(std::is_constructible_v<std::stop_callback<void (*)()>, std::stop_token&&, void (*)()>);
static_assert(!std::is_constructible_v<std::stop_callback<void (*)()>, std::stop_token&&, void (*)(int)>);
static_assert(std::is_constructible_v<std::stop_callback<Cb>, std::stop_token&&, Cb&>);
static_assert(std::is_constructible_v<std::stop_callback<Cb&>, std::stop_token&&, Cb&>);
static_assert(!std::is_constructible_v<std::stop_callback<Cb>, std::stop_token&&, int>);

// explicit
template <class T>
void conversion_test(T);

template <class T, class... Args>
concept ImplicitlyConstructible = requires(Args&&... args) { conversion_test<T>({std::forward<Args>(args)...}); };
static_assert(ImplicitlyConstructible<int, int>);
static_assert(!ImplicitlyConstructible<std::stop_callback<Cb>, std::stop_token&&, Cb>);

// noexcept
template <bool NoExceptCtor>
struct CbNoExcept {
  CbNoExcept(int) noexcept(NoExceptCtor);
  void operator()() const;
};
static_assert(std::is_nothrow_constructible_v<std::stop_callback<CbNoExcept<true>>, std::stop_token&&, int>);
static_assert(!std::is_nothrow_constructible_v<std::stop_callback<CbNoExcept<false>>, std::stop_token&&, int>);

int main(int, char**) {
  // was requested
  {
    std::stop_source ss;
    ss.request_stop();

    bool called = false;
    std::stop_callback sc(ss.get_token(), [&] { called = true; });
    assert(called);
  }

  // was not requested
  {
    std::stop_source ss;

    bool called = false;
    std::stop_callback sc(ss.get_token(), [&] { called = true; });
    assert(!called);

    ss.request_stop();
    assert(called);
  }

  // token has no state
  {
    std::stop_token st;
    bool called = false;
    std::stop_callback sc(std::move(st), [&] { called = true; });
    assert(!called);
  }

  // should not be called multiple times
  {
    std::stop_source ss;

    int calledTimes = 0;
    std::stop_callback sc(ss.get_token(), [&] { ++calledTimes; });

    std::vector<std::thread> threads;
    for (auto i = 0; i < 10; ++i) {
      threads.emplace_back(support::make_test_thread([&] { ss.request_stop(); }));
    }

    for (auto& thread : threads) {
      thread.join();
    }
    assert(calledTimes == 1);
  }

  // adding more callbacks during invoking other callbacks
  {
    std::stop_source ss;

    std::atomic<bool> startedFlag = false;
    std::atomic<bool> finishFlag  = false;
    std::stop_callback sc(ss.get_token(), [&] {
      startedFlag = true;
      startedFlag.notify_all();
      finishFlag.wait(false);
    });

    auto thread = support::make_test_thread([&] { ss.request_stop(); });

    startedFlag.wait(false);

    // first callback is still running, adding another one;
    bool secondCallbackCalled = false;
    std::stop_callback sc2(ss.get_token(), [&] { secondCallbackCalled = true; });

    finishFlag = true;
    finishFlag.notify_all();

    thread.join();
    assert(secondCallbackCalled);
  }

  // adding callbacks on different threads
  {
    std::stop_source ss;

    std::vector<std::thread> threads;
    std::atomic<int> callbackCalledTimes = 0;
    std::atomic<bool> done               = false;
    for (auto i = 0; i < 10; ++i) {
      threads.emplace_back(support::make_test_thread([&] {
        std::stop_callback sc{ss.get_token(), [&] { callbackCalledTimes.fetch_add(1, std::memory_order_relaxed); }};
        done.wait(false);
      }));
    }
    using namespace std::chrono_literals;
    std::this_thread::sleep_for(1ms);
    ss.request_stop();
    done = true;
    done.notify_all();
    for (auto& thread : threads) {
      thread.join();
    }
    assert(callbackCalledTimes.load(std::memory_order_relaxed) == 10);
  }

  // correct overload
  {
    struct CBWithTracking {
      bool& lvalueCalled;
      bool& lvalueConstCalled;
      bool& rvalueCalled;
      bool& rvalueConstCalled;

      void operator()() & { lvalueCalled = true; }
      void operator()() const& { lvalueConstCalled = true; }
      void operator()() && { rvalueCalled = true; }
      void operator()() const&& { rvalueConstCalled = true; }
    };

    // RValue
    {
      bool lvalueCalled      = false;
      bool lvalueConstCalled = false;
      bool rvalueCalled      = false;
      bool rvalueConstCalled = false;
      std::stop_source ss;
      ss.request_stop();

      std::stop_callback<CBWithTracking> sc(
          ss.get_token(), CBWithTracking{lvalueCalled, lvalueConstCalled, rvalueCalled, rvalueConstCalled});
      assert(rvalueCalled);
    }

    // RValue
    {
      bool lvalueCalled      = false;
      bool lvalueConstCalled = false;
      bool rvalueCalled      = false;
      bool rvalueConstCalled = false;
      std::stop_source ss;
      ss.request_stop();

      std::stop_callback<const CBWithTracking> sc(
          ss.get_token(), CBWithTracking{lvalueCalled, lvalueConstCalled, rvalueCalled, rvalueConstCalled});
      assert(rvalueConstCalled);
    }

    // LValue
    {
      bool lvalueCalled      = false;
      bool lvalueConstCalled = false;
      bool rvalueCalled      = false;
      bool rvalueConstCalled = false;
      std::stop_source ss;
      ss.request_stop();
      CBWithTracking cb{lvalueCalled, lvalueConstCalled, rvalueCalled, rvalueConstCalled};
      std::stop_callback<CBWithTracking&> sc(ss.get_token(), cb);
      assert(lvalueCalled);
    }

    // const LValue
    {
      bool lvalueCalled      = false;
      bool lvalueConstCalled = false;
      bool rvalueCalled      = false;
      bool rvalueConstCalled = false;
      std::stop_source ss;
      ss.request_stop();
      CBWithTracking cb{lvalueCalled, lvalueConstCalled, rvalueCalled, rvalueConstCalled};
      std::stop_callback<const CBWithTracking&> sc(ss.get_token(), cb);
      assert(lvalueConstCalled);
    }
  }

  return 0;
}
