// -*- C++ -*-
//===----------------------------------------------------------------------===//
//
// 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
//
//===----------------------------------------------------------------------===//

#ifndef _LIBCPP___THREADING_SUPPORT
#define _LIBCPP___THREADING_SUPPORT

#include <__availability>
#include <__chrono/convert_to_timespec.h>
#include <__chrono/duration.h>
#include <__compare/ordering.h>
#include <__config>
#include <__fwd/hash.h>
#include <__thread/poll_with_backoff.h>
#include <errno.h>
#include <iosfwd>
#include <limits>

#ifdef __MVS__
# include <__support/ibm/nanosleep.h>
#endif

#ifndef _LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER
#  pragma GCC system_header
#endif

#if defined(_LIBCPP_HAS_THREAD_API_EXTERNAL)
# include <__external_threading>
#elif !defined(_LIBCPP_HAS_NO_THREADS)

#if defined(_LIBCPP_HAS_THREAD_API_PTHREAD)
# include <pthread.h>
# include <sched.h>
#elif defined(_LIBCPP_HAS_THREAD_API_C11)
# include <threads.h>
#endif

#if defined(_LIBCPP_HAS_THREAD_LIBRARY_EXTERNAL) || \
    defined(_LIBCPP_BUILDING_THREAD_LIBRARY_EXTERNAL) || \
    defined(_LIBCPP_HAS_THREAD_API_WIN32)
#define _LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_FUNC_VIS
#else
#define _LIBCPP_THREAD_ABI_VISIBILITY inline _LIBCPP_INLINE_VISIBILITY
#endif

#if defined(__FreeBSD__) && defined(__clang__) && __has_attribute(no_thread_safety_analysis)
#define _LIBCPP_NO_THREAD_SAFETY_ANALYSIS __attribute__((no_thread_safety_analysis))
#else
#define _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
#endif

typedef ::timespec __libcpp_timespec_t;
#endif // !defined(_LIBCPP_HAS_NO_THREADS)

_LIBCPP_BEGIN_NAMESPACE_STD

#if !defined(_LIBCPP_HAS_NO_THREADS)

#if defined(_LIBCPP_HAS_THREAD_API_PTHREAD)
// Mutex
typedef pthread_mutex_t __libcpp_mutex_t;
#define _LIBCPP_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER

typedef pthread_mutex_t __libcpp_recursive_mutex_t;

// Condition Variable
typedef pthread_cond_t __libcpp_condvar_t;
#define _LIBCPP_CONDVAR_INITIALIZER PTHREAD_COND_INITIALIZER

// Execute once
typedef pthread_once_t __libcpp_exec_once_flag;
#define _LIBCPP_EXEC_ONCE_INITIALIZER PTHREAD_ONCE_INIT

// Thread id
#if defined(__MVS__)
  typedef unsigned long long __libcpp_thread_id;
#else
  typedef pthread_t __libcpp_thread_id;
#endif

// Thread
#define _LIBCPP_NULL_THREAD ((__libcpp_thread_t()))
typedef pthread_t __libcpp_thread_t;

// Thread Local Storage
typedef pthread_key_t __libcpp_tls_key;

#define _LIBCPP_TLS_DESTRUCTOR_CC
#elif defined(_LIBCPP_HAS_THREAD_API_C11)
// Mutex
typedef mtx_t __libcpp_mutex_t;
// mtx_t is a struct so using {} for initialization is valid.
#define _LIBCPP_MUTEX_INITIALIZER {}

typedef mtx_t __libcpp_recursive_mutex_t;

// Condition Variable
typedef cnd_t __libcpp_condvar_t;
// cnd_t is a struct so using {} for initialization is valid.
#define _LIBCPP_CONDVAR_INITIALIZER {}

// Execute once
typedef once_flag __libcpp_exec_once_flag;
#define _LIBCPP_EXEC_ONCE_INITIALIZER ONCE_FLAG_INIT

// Thread id
typedef thrd_t __libcpp_thread_id;

// Thread
#define _LIBCPP_NULL_THREAD 0U

typedef thrd_t __libcpp_thread_t;

// Thread Local Storage
typedef tss_t __libcpp_tls_key;

#define _LIBCPP_TLS_DESTRUCTOR_CC
#elif !defined(_LIBCPP_HAS_THREAD_API_EXTERNAL)
// Mutex
typedef void* __libcpp_mutex_t;
#define _LIBCPP_MUTEX_INITIALIZER 0

#if defined(_M_IX86) || defined(__i386__) || defined(_M_ARM) || defined(__arm__)
typedef void* __libcpp_recursive_mutex_t[6];
#elif defined(_M_AMD64) || defined(__x86_64__) || defined(_M_ARM64) || defined(__aarch64__)
typedef void* __libcpp_recursive_mutex_t[5];
#else
# error Unsupported architecture
#endif

// Condition Variable
typedef void* __libcpp_condvar_t;
#define _LIBCPP_CONDVAR_INITIALIZER 0

// Execute Once
typedef void* __libcpp_exec_once_flag;
#define _LIBCPP_EXEC_ONCE_INITIALIZER 0

// Thread ID
typedef long __libcpp_thread_id;

// Thread
#define _LIBCPP_NULL_THREAD 0U

typedef void* __libcpp_thread_t;

// Thread Local Storage
typedef long __libcpp_tls_key;

#define _LIBCPP_TLS_DESTRUCTOR_CC __stdcall
#endif // !defined(_LIBCPP_HAS_THREAD_API_PTHREAD) && !defined(_LIBCPP_HAS_THREAD_API_EXTERNAL)

#if !defined(_LIBCPP_HAS_THREAD_API_EXTERNAL)
// Mutex
_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_recursive_mutex_init(__libcpp_recursive_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_recursive_mutex_lock(__libcpp_recursive_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
bool __libcpp_recursive_mutex_trylock(__libcpp_recursive_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_recursive_mutex_unlock(__libcpp_recursive_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_recursive_mutex_destroy(__libcpp_recursive_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_mutex_lock(__libcpp_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
bool __libcpp_mutex_trylock(__libcpp_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_mutex_unlock(__libcpp_mutex_t *__m);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_mutex_destroy(__libcpp_mutex_t *__m);

// Condition variable
_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_condvar_signal(__libcpp_condvar_t* __cv);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_condvar_broadcast(__libcpp_condvar_t* __cv);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_condvar_wait(__libcpp_condvar_t* __cv, __libcpp_mutex_t* __m);

_LIBCPP_THREAD_ABI_VISIBILITY _LIBCPP_NO_THREAD_SAFETY_ANALYSIS
int __libcpp_condvar_timedwait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m,
                               __libcpp_timespec_t *__ts);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_condvar_destroy(__libcpp_condvar_t* __cv);

// Execute once
_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_execute_once(__libcpp_exec_once_flag *__flag,
                          void (*__init_routine)());

// Thread id
_LIBCPP_THREAD_ABI_VISIBILITY
bool __libcpp_thread_id_equal(__libcpp_thread_id __t1, __libcpp_thread_id __t2);

_LIBCPP_THREAD_ABI_VISIBILITY
bool __libcpp_thread_id_less(__libcpp_thread_id __t1, __libcpp_thread_id __t2);

// Thread
_LIBCPP_THREAD_ABI_VISIBILITY
bool __libcpp_thread_isnull(const __libcpp_thread_t *__t);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_thread_create(__libcpp_thread_t *__t, void *(*__func)(void *),
                           void *__arg);

_LIBCPP_THREAD_ABI_VISIBILITY
__libcpp_thread_id __libcpp_thread_get_current_id();

_LIBCPP_THREAD_ABI_VISIBILITY
__libcpp_thread_id __libcpp_thread_get_id(const __libcpp_thread_t *__t);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_thread_join(__libcpp_thread_t *__t);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_thread_detach(__libcpp_thread_t *__t);

_LIBCPP_THREAD_ABI_VISIBILITY
void __libcpp_thread_yield();

_LIBCPP_THREAD_ABI_VISIBILITY
void __libcpp_thread_sleep_for(const chrono::nanoseconds& __ns);

// Thread local storage
_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_tls_create(__libcpp_tls_key* __key,
                        void(_LIBCPP_TLS_DESTRUCTOR_CC* __at_exit)(void*));

_LIBCPP_THREAD_ABI_VISIBILITY
void *__libcpp_tls_get(__libcpp_tls_key __key);

_LIBCPP_THREAD_ABI_VISIBILITY
int __libcpp_tls_set(__libcpp_tls_key __key, void *__p);

#endif // !defined(_LIBCPP_HAS_THREAD_API_EXTERNAL)

#if (!defined(_LIBCPP_HAS_THREAD_LIBRARY_EXTERNAL) || \
     defined(_LIBCPP_BUILDING_THREAD_LIBRARY_EXTERNAL))

#if defined(_LIBCPP_HAS_THREAD_API_PTHREAD)

int __libcpp_recursive_mutex_init(__libcpp_recursive_mutex_t *__m)
{
  pthread_mutexattr_t __attr;
  int __ec = pthread_mutexattr_init(&__attr);
  if (__ec)
    return __ec;
  __ec = pthread_mutexattr_settype(&__attr, PTHREAD_MUTEX_RECURSIVE);
  if (__ec) {
    pthread_mutexattr_destroy(&__attr);
    return __ec;
  }
  __ec = pthread_mutex_init(__m, &__attr);
  if (__ec) {
    pthread_mutexattr_destroy(&__attr);
    return __ec;
  }
  __ec = pthread_mutexattr_destroy(&__attr);
  if (__ec) {
    pthread_mutex_destroy(__m);
    return __ec;
  }
  return 0;
}

int __libcpp_recursive_mutex_lock(__libcpp_recursive_mutex_t *__m)
{
  return pthread_mutex_lock(__m);
}

bool __libcpp_recursive_mutex_trylock(__libcpp_recursive_mutex_t *__m)
{
  return pthread_mutex_trylock(__m) == 0;
}

int __libcpp_recursive_mutex_unlock(__libcpp_recursive_mutex_t *__m)
{
  return pthread_mutex_unlock(__m);
}

int __libcpp_recursive_mutex_destroy(__libcpp_recursive_mutex_t *__m)
{
  return pthread_mutex_destroy(__m);
}

int __libcpp_mutex_lock(__libcpp_mutex_t *__m)
{
  return pthread_mutex_lock(__m);
}

bool __libcpp_mutex_trylock(__libcpp_mutex_t *__m)
{
  return pthread_mutex_trylock(__m) == 0;
}

int __libcpp_mutex_unlock(__libcpp_mutex_t *__m)
{
  return pthread_mutex_unlock(__m);
}

int __libcpp_mutex_destroy(__libcpp_mutex_t *__m)
{
  return pthread_mutex_destroy(__m);
}

// Condition Variable
int __libcpp_condvar_signal(__libcpp_condvar_t *__cv)
{
  return pthread_cond_signal(__cv);
}

int __libcpp_condvar_broadcast(__libcpp_condvar_t *__cv)
{
  return pthread_cond_broadcast(__cv);
}

int __libcpp_condvar_wait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m)
{
  return pthread_cond_wait(__cv, __m);
}

int __libcpp_condvar_timedwait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m,
                               __libcpp_timespec_t *__ts)
{
  return pthread_cond_timedwait(__cv, __m, __ts);
}

int __libcpp_condvar_destroy(__libcpp_condvar_t *__cv)
{
  return pthread_cond_destroy(__cv);
}

// Execute once
int __libcpp_execute_once(__libcpp_exec_once_flag *__flag,
                          void (*__init_routine)()) {
  return pthread_once(__flag, __init_routine);
}

// Thread id
// Returns non-zero if the thread ids are equal, otherwise 0
bool __libcpp_thread_id_equal(__libcpp_thread_id __t1, __libcpp_thread_id __t2)
{
  return __t1 == __t2;
}

// Returns non-zero if t1 < t2, otherwise 0
bool __libcpp_thread_id_less(__libcpp_thread_id __t1, __libcpp_thread_id __t2)
{
  return __t1 < __t2;
}

// Thread
bool __libcpp_thread_isnull(const __libcpp_thread_t *__t) {
  return __libcpp_thread_get_id(__t) == 0;
}

int __libcpp_thread_create(__libcpp_thread_t *__t, void *(*__func)(void *),
                           void *__arg)
{
  return pthread_create(__t, nullptr, __func, __arg);
}

__libcpp_thread_id __libcpp_thread_get_current_id()
{
  const __libcpp_thread_t __current_thread = pthread_self();
  return __libcpp_thread_get_id(&__current_thread);
}

__libcpp_thread_id __libcpp_thread_get_id(const __libcpp_thread_t *__t)
{
#if defined(__MVS__)
  return __t->__;
#else
  return *__t;
#endif
}

int __libcpp_thread_join(__libcpp_thread_t *__t)
{
  return pthread_join(*__t, nullptr);
}

int __libcpp_thread_detach(__libcpp_thread_t *__t)
{
  return pthread_detach(*__t);
}

void __libcpp_thread_yield()
{
  sched_yield();
}

void __libcpp_thread_sleep_for(const chrono::nanoseconds& __ns)
{
   __libcpp_timespec_t __ts = _VSTD::__convert_to_timespec<__libcpp_timespec_t>(__ns);
   while (nanosleep(&__ts, &__ts) == -1 && errno == EINTR);
}

// Thread local storage
int __libcpp_tls_create(__libcpp_tls_key *__key, void (*__at_exit)(void *))
{
  return pthread_key_create(__key, __at_exit);
}

void *__libcpp_tls_get(__libcpp_tls_key __key)
{
  return pthread_getspecific(__key);
}

int __libcpp_tls_set(__libcpp_tls_key __key, void *__p)
{
    return pthread_setspecific(__key, __p);
}

#elif defined(_LIBCPP_HAS_THREAD_API_C11)

int __libcpp_recursive_mutex_init(__libcpp_recursive_mutex_t *__m)
{
  return mtx_init(__m, mtx_plain | mtx_recursive) == thrd_success ? 0 : EINVAL;
}

int __libcpp_recursive_mutex_lock(__libcpp_recursive_mutex_t *__m)
{
  return mtx_lock(__m) == thrd_success ? 0 : EINVAL;
}

bool __libcpp_recursive_mutex_trylock(__libcpp_recursive_mutex_t *__m)
{
  return mtx_trylock(__m) == thrd_success;
}

int __libcpp_recursive_mutex_unlock(__libcpp_recursive_mutex_t *__m)
{
  return mtx_unlock(__m) == thrd_success ? 0 : EINVAL;
}

int __libcpp_recursive_mutex_destroy(__libcpp_recursive_mutex_t *__m)
{
  mtx_destroy(__m);
  return 0;
}

int __libcpp_mutex_lock(__libcpp_mutex_t *__m)
{
  return mtx_lock(__m) == thrd_success ? 0 : EINVAL;
}

bool __libcpp_mutex_trylock(__libcpp_mutex_t *__m)
{
  return mtx_trylock(__m) == thrd_success;
}

int __libcpp_mutex_unlock(__libcpp_mutex_t *__m)
{
  return mtx_unlock(__m) == thrd_success ? 0 : EINVAL;
}

int __libcpp_mutex_destroy(__libcpp_mutex_t *__m)
{
  mtx_destroy(__m);
  return 0;
}

// Condition Variable
int __libcpp_condvar_signal(__libcpp_condvar_t *__cv)
{
  return cnd_signal(__cv) == thrd_success ? 0 : EINVAL;
}

int __libcpp_condvar_broadcast(__libcpp_condvar_t *__cv)
{
  return cnd_broadcast(__cv) == thrd_success ? 0 : EINVAL;
}

int __libcpp_condvar_wait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m)
{
  return cnd_wait(__cv, __m) == thrd_success ? 0 : EINVAL;
}

int __libcpp_condvar_timedwait(__libcpp_condvar_t *__cv, __libcpp_mutex_t *__m,
                               timespec *__ts)
{
  int __ec = cnd_timedwait(__cv, __m, __ts);
  return __ec == thrd_timedout ? ETIMEDOUT : __ec;
}

int __libcpp_condvar_destroy(__libcpp_condvar_t *__cv)
{
  cnd_destroy(__cv);
  return 0;
}

// Execute once
int __libcpp_execute_once(__libcpp_exec_once_flag *flag,
                          void (*init_routine)(void)) {
  ::call_once(flag, init_routine);
  return 0;
}

// Thread id
// Returns non-zero if the thread ids are equal, otherwise 0
bool __libcpp_thread_id_equal(__libcpp_thread_id t1, __libcpp_thread_id t2)
{
  return thrd_equal(t1, t2) != 0;
}

// Returns non-zero if t1 < t2, otherwise 0
bool __libcpp_thread_id_less(__libcpp_thread_id t1, __libcpp_thread_id t2)
{
  return t1 < t2;
}

// Thread
bool __libcpp_thread_isnull(const __libcpp_thread_t *__t) {
  return __libcpp_thread_get_id(__t) == 0;
}

int __libcpp_thread_create(__libcpp_thread_t *__t, void *(*__func)(void *),
                           void *__arg)
{
  int __ec = thrd_create(__t, reinterpret_cast<thrd_start_t>(__func), __arg);
  return __ec == thrd_nomem ? ENOMEM : __ec;
}

__libcpp_thread_id __libcpp_thread_get_current_id()
{
  return thrd_current();
}

__libcpp_thread_id __libcpp_thread_get_id(const __libcpp_thread_t *__t)
{
  return *__t;
}

int __libcpp_thread_join(__libcpp_thread_t *__t)
{
  return thrd_join(*__t, nullptr) == thrd_success ? 0 : EINVAL;
}

int __libcpp_thread_detach(__libcpp_thread_t *__t)
{
  return thrd_detach(*__t) == thrd_success ? 0 : EINVAL;
}

void __libcpp_thread_yield()
{
  thrd_yield();
}

void __libcpp_thread_sleep_for(const chrono::nanoseconds& __ns)
{
   __libcpp_timespec_t __ts = _VSTD::__convert_to_timespec<__libcpp_timespec_t>(__ns);
  thrd_sleep(&__ts, nullptr);
}

// Thread local storage
int __libcpp_tls_create(__libcpp_tls_key *__key, void (*__at_exit)(void *))
{
  return tss_create(__key, __at_exit) == thrd_success ? 0 : EINVAL;
}

void *__libcpp_tls_get(__libcpp_tls_key __key)
{
  return tss_get(__key);
}

int __libcpp_tls_set(__libcpp_tls_key __key, void *__p)
{
  return tss_set(__key, __p) == thrd_success ? 0 : EINVAL;
}

#endif


#endif // !_LIBCPP_HAS_THREAD_LIBRARY_EXTERNAL || _LIBCPP_BUILDING_THREAD_LIBRARY_EXTERNAL

class _LIBCPP_TYPE_VIS thread;
class _LIBCPP_TYPE_VIS __thread_id;

namespace this_thread
{

_LIBCPP_INLINE_VISIBILITY __thread_id get_id() _NOEXCEPT;

} // namespace this_thread

template<> struct hash<__thread_id>;

class _LIBCPP_TEMPLATE_VIS __thread_id
{
    // FIXME: pthread_t is a pointer on Darwin but a long on Linux.
    // NULL is the no-thread value on Darwin.  Someone needs to check
    // on other platforms.  We assume 0 works everywhere for now.
    __libcpp_thread_id __id_;

    static _LIBCPP_HIDE_FROM_ABI
        bool __lt_impl(__thread_id __x, __thread_id __y) _NOEXCEPT
        { // id==0 is always less than any other thread_id
        if (__x.__id_ == 0) return __y.__id_ != 0;
        if (__y.__id_ == 0) return false;
        return  __libcpp_thread_id_less(__x.__id_, __y.__id_);
        }

public:
    _LIBCPP_INLINE_VISIBILITY
    __thread_id() _NOEXCEPT : __id_(0) {}

    _LIBCPP_INLINE_VISIBILITY
    void __reset() { __id_ = 0; }

    friend _LIBCPP_HIDE_FROM_ABI bool operator==(__thread_id __x, __thread_id __y) _NOEXCEPT;
#if _LIBCPP_STD_VER <= 17
    friend _LIBCPP_HIDE_FROM_ABI bool operator<(__thread_id __x, __thread_id __y) _NOEXCEPT;
#else // _LIBCPP_STD_VER <= 17
    friend _LIBCPP_HIDE_FROM_ABI strong_ordering operator<=>(__thread_id __x, __thread_id __y) noexcept;
#endif // _LIBCPP_STD_VER <= 17

    template<class _CharT, class _Traits>
    friend
    _LIBCPP_INLINE_VISIBILITY
    basic_ostream<_CharT, _Traits>&
    operator<<(basic_ostream<_CharT, _Traits>& __os, __thread_id __id);

private:
    _LIBCPP_INLINE_VISIBILITY
    __thread_id(__libcpp_thread_id __id) : __id_(__id) {}

    _LIBCPP_HIDE_FROM_ABI friend __libcpp_thread_id __get_underlying_id(const __thread_id __id) { return __id.__id_; }

    friend __thread_id this_thread::get_id() _NOEXCEPT;
    friend class _LIBCPP_TYPE_VIS thread;
    friend struct _LIBCPP_TEMPLATE_VIS hash<__thread_id>;
};

inline _LIBCPP_HIDE_FROM_ABI
bool operator==(__thread_id __x, __thread_id __y) _NOEXCEPT {
  // Don't pass id==0 to underlying routines
  if (__x.__id_ == 0)
    return __y.__id_ == 0;
  if (__y.__id_ == 0)
    return false;
  return __libcpp_thread_id_equal(__x.__id_, __y.__id_);
}

#if _LIBCPP_STD_VER <= 17

inline _LIBCPP_HIDE_FROM_ABI
bool operator!=(__thread_id __x, __thread_id __y) _NOEXCEPT {
  return !(__x == __y);
}

inline _LIBCPP_HIDE_FROM_ABI
bool operator<(__thread_id __x, __thread_id __y) _NOEXCEPT {
  return __thread_id::__lt_impl(__x.__id_, __y.__id_);
}

inline _LIBCPP_HIDE_FROM_ABI bool operator<=(__thread_id __x, __thread_id __y) _NOEXCEPT { return !(__y < __x); }
inline _LIBCPP_HIDE_FROM_ABI bool operator>(__thread_id __x, __thread_id __y) _NOEXCEPT { return __y < __x; }
inline _LIBCPP_HIDE_FROM_ABI bool operator>=(__thread_id __x, __thread_id __y) _NOEXCEPT { return !(__x < __y); }

#else // _LIBCPP_STD_VER <= 17

inline _LIBCPP_HIDE_FROM_ABI
strong_ordering operator<=>(__thread_id __x, __thread_id __y) noexcept {
  if (__x == __y)
    return strong_ordering::equal;
  if (__thread_id::__lt_impl(__x, __y))
    return strong_ordering::less;
  return strong_ordering::greater;
}

#endif // _LIBCPP_STD_VER <= 17

namespace this_thread
{

inline _LIBCPP_INLINE_VISIBILITY
__thread_id
get_id() _NOEXCEPT
{
    return __libcpp_thread_get_current_id();
}

} // namespace this_thread

#endif // !_LIBCPP_HAS_NO_THREADS

_LIBCPP_END_NAMESPACE_STD

#endif // _LIBCPP___THREADING_SUPPORT
