/*
 * z_Windows_NT_util.cpp -- platform specific routines.
 */

//===----------------------------------------------------------------------===//
//
// 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
//
//===----------------------------------------------------------------------===//

#include "kmp.h"
#include "kmp_affinity.h"
#include "kmp_i18n.h"
#include "kmp_io.h"
#include "kmp_itt.h"
#include "kmp_wait_release.h"

/* This code is related to NtQuerySystemInformation() function. This function
   is used in the Load balance algorithm for OMP_DYNAMIC=true to find the
   number of running threads in the system. */

#include <ntsecapi.h> // UNICODE_STRING
#undef WIN32_NO_STATUS
#include <ntstatus.h>
#include <psapi.h>
#ifdef _MSC_VER
#pragma comment(lib, "psapi.lib")
#endif

enum SYSTEM_INFORMATION_CLASS {
  SystemProcessInformation = 5
}; // SYSTEM_INFORMATION_CLASS

struct CLIENT_ID {
  HANDLE UniqueProcess;
  HANDLE UniqueThread;
}; // struct CLIENT_ID

enum THREAD_STATE {
  StateInitialized,
  StateReady,
  StateRunning,
  StateStandby,
  StateTerminated,
  StateWait,
  StateTransition,
  StateUnknown
}; // enum THREAD_STATE

struct VM_COUNTERS {
  SIZE_T PeakVirtualSize;
  SIZE_T VirtualSize;
  ULONG PageFaultCount;
  SIZE_T PeakWorkingSetSize;
  SIZE_T WorkingSetSize;
  SIZE_T QuotaPeakPagedPoolUsage;
  SIZE_T QuotaPagedPoolUsage;
  SIZE_T QuotaPeakNonPagedPoolUsage;
  SIZE_T QuotaNonPagedPoolUsage;
  SIZE_T PagefileUsage;
  SIZE_T PeakPagefileUsage;
  SIZE_T PrivatePageCount;
}; // struct VM_COUNTERS

struct SYSTEM_THREAD {
  LARGE_INTEGER KernelTime;
  LARGE_INTEGER UserTime;
  LARGE_INTEGER CreateTime;
  ULONG WaitTime;
  LPVOID StartAddress;
  CLIENT_ID ClientId;
  DWORD Priority;
  LONG BasePriority;
  ULONG ContextSwitchCount;
  THREAD_STATE State;
  ULONG WaitReason;
}; // SYSTEM_THREAD

KMP_BUILD_ASSERT(offsetof(SYSTEM_THREAD, KernelTime) == 0);
#if KMP_ARCH_X86 || KMP_ARCH_ARM
KMP_BUILD_ASSERT(offsetof(SYSTEM_THREAD, StartAddress) == 28);
KMP_BUILD_ASSERT(offsetof(SYSTEM_THREAD, State) == 52);
#else
KMP_BUILD_ASSERT(offsetof(SYSTEM_THREAD, StartAddress) == 32);
KMP_BUILD_ASSERT(offsetof(SYSTEM_THREAD, State) == 68);
#endif

struct SYSTEM_PROCESS_INFORMATION {
  ULONG NextEntryOffset;
  ULONG NumberOfThreads;
  LARGE_INTEGER Reserved[3];
  LARGE_INTEGER CreateTime;
  LARGE_INTEGER UserTime;
  LARGE_INTEGER KernelTime;
  UNICODE_STRING ImageName;
  DWORD BasePriority;
  HANDLE ProcessId;
  HANDLE ParentProcessId;
  ULONG HandleCount;
  ULONG Reserved2[2];
  VM_COUNTERS VMCounters;
  IO_COUNTERS IOCounters;
  SYSTEM_THREAD Threads[1];
}; // SYSTEM_PROCESS_INFORMATION
typedef SYSTEM_PROCESS_INFORMATION *PSYSTEM_PROCESS_INFORMATION;

KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, NextEntryOffset) == 0);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, CreateTime) == 32);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, ImageName) == 56);
#if KMP_ARCH_X86 || KMP_ARCH_ARM
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, ProcessId) == 68);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, HandleCount) == 76);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, VMCounters) == 88);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, IOCounters) == 136);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, Threads) == 184);
#else
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, ProcessId) == 80);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, HandleCount) == 96);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, VMCounters) == 112);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, IOCounters) == 208);
KMP_BUILD_ASSERT(offsetof(SYSTEM_PROCESS_INFORMATION, Threads) == 256);
#endif

typedef NTSTATUS(NTAPI *NtQuerySystemInformation_t)(SYSTEM_INFORMATION_CLASS,
                                                    PVOID, ULONG, PULONG);
NtQuerySystemInformation_t NtQuerySystemInformation = NULL;

HMODULE ntdll = NULL;

/* End of NtQuerySystemInformation()-related code */

static HMODULE kernel32 = NULL;

#if KMP_HANDLE_SIGNALS
typedef void (*sig_func_t)(int);
static sig_func_t __kmp_sighldrs[NSIG];
static int __kmp_siginstalled[NSIG];
#endif

#if KMP_USE_MONITOR
static HANDLE __kmp_monitor_ev;
#endif
static kmp_int64 __kmp_win32_time;
double __kmp_win32_tick;

int __kmp_init_runtime = FALSE;
CRITICAL_SECTION __kmp_win32_section;

void __kmp_win32_mutex_init(kmp_win32_mutex_t *mx) {
  InitializeCriticalSection(&mx->cs);
#if USE_ITT_BUILD
  __kmp_itt_system_object_created(&mx->cs, "Critical Section");
#endif /* USE_ITT_BUILD */
}

void __kmp_win32_mutex_destroy(kmp_win32_mutex_t *mx) {
  DeleteCriticalSection(&mx->cs);
}

void __kmp_win32_mutex_lock(kmp_win32_mutex_t *mx) {
  EnterCriticalSection(&mx->cs);
}

int __kmp_win32_mutex_trylock(kmp_win32_mutex_t *mx) {
  return TryEnterCriticalSection(&mx->cs);
}

void __kmp_win32_mutex_unlock(kmp_win32_mutex_t *mx) {
  LeaveCriticalSection(&mx->cs);
}

void __kmp_win32_cond_init(kmp_win32_cond_t *cv) {
  cv->waiters_count_ = 0;
  cv->wait_generation_count_ = 0;
  cv->release_count_ = 0;

  /* Initialize the critical section */
  __kmp_win32_mutex_init(&cv->waiters_count_lock_);

  /* Create a manual-reset event. */
  cv->event_ = CreateEvent(NULL, // no security
                           TRUE, // manual-reset
                           FALSE, // non-signaled initially
                           NULL); // unnamed
#if USE_ITT_BUILD
  __kmp_itt_system_object_created(cv->event_, "Event");
#endif /* USE_ITT_BUILD */
}

void __kmp_win32_cond_destroy(kmp_win32_cond_t *cv) {
  __kmp_win32_mutex_destroy(&cv->waiters_count_lock_);
  __kmp_free_handle(cv->event_);
  memset(cv, '\0', sizeof(*cv));
}

/* TODO associate cv with a team instead of a thread so as to optimize
   the case where we wake up a whole team */

template <class C>
static void __kmp_win32_cond_wait(kmp_win32_cond_t *cv, kmp_win32_mutex_t *mx,
                                  kmp_info_t *th, C *flag) {
  int my_generation;
  int last_waiter;

  /* Avoid race conditions */
  __kmp_win32_mutex_lock(&cv->waiters_count_lock_);

  /* Increment count of waiters */
  cv->waiters_count_++;

  /* Store current generation in our activation record. */
  my_generation = cv->wait_generation_count_;

  __kmp_win32_mutex_unlock(&cv->waiters_count_lock_);
  __kmp_win32_mutex_unlock(mx);

  for (;;) {
    int wait_done = 0;
    DWORD res, timeout = 5000; // just tried to quess an appropriate number
    /* Wait until the event is signaled */
    res = WaitForSingleObject(cv->event_, timeout);

    if (res == WAIT_OBJECT_0) {
      // event signaled
      __kmp_win32_mutex_lock(&cv->waiters_count_lock_);
      /* Exit the loop when the <cv->event_> is signaled and there are still
         waiting threads from this <wait_generation> that haven't been released
         from this wait yet. */
      wait_done = (cv->release_count_ > 0) &&
                  (cv->wait_generation_count_ != my_generation);
      __kmp_win32_mutex_unlock(&cv->waiters_count_lock_);
    } else if (res == WAIT_TIMEOUT || res == WAIT_FAILED) {
      // check if the flag and cv counters are in consistent state
      // as MS sent us debug dump whith inconsistent state of data
      __kmp_win32_mutex_lock(mx);
      typename C::flag_t old_f = flag->set_sleeping();
      if (!flag->done_check_val(old_f & ~KMP_BARRIER_SLEEP_STATE)) {
        __kmp_win32_mutex_unlock(mx);
        continue;
      }
      // condition fulfilled, exiting
      flag->unset_sleeping();
      TCW_PTR(th->th.th_sleep_loc, NULL);
      th->th.th_sleep_loc_type = flag_unset;
      KF_TRACE(50, ("__kmp_win32_cond_wait: exiting, condition "
                    "fulfilled: flag's loc(%p): %u\n",
                    flag->get(), (unsigned int)flag->load()));

      __kmp_win32_mutex_lock(&cv->waiters_count_lock_);
      KMP_DEBUG_ASSERT(cv->waiters_count_ > 0);
      cv->release_count_ = cv->waiters_count_;
      cv->wait_generation_count_++;
      wait_done = 1;
      __kmp_win32_mutex_unlock(&cv->waiters_count_lock_);

      __kmp_win32_mutex_unlock(mx);
    }
    /* there used to be a semicolon after the if statement, it looked like a
       bug, so i removed it */
    if (wait_done)
      break;
  }

  __kmp_win32_mutex_lock(mx);
  __kmp_win32_mutex_lock(&cv->waiters_count_lock_);

  cv->waiters_count_--;
  cv->release_count_--;

  last_waiter = (cv->release_count_ == 0);

  __kmp_win32_mutex_unlock(&cv->waiters_count_lock_);

  if (last_waiter) {
    /* We're the last waiter to be notified, so reset the manual event. */
    ResetEvent(cv->event_);
  }
}

void __kmp_win32_cond_broadcast(kmp_win32_cond_t *cv) {
  __kmp_win32_mutex_lock(&cv->waiters_count_lock_);

  if (cv->waiters_count_ > 0) {
    SetEvent(cv->event_);
    /* Release all the threads in this generation. */

    cv->release_count_ = cv->waiters_count_;

    /* Start a new generation. */
    cv->wait_generation_count_++;
  }

  __kmp_win32_mutex_unlock(&cv->waiters_count_lock_);
}

void __kmp_win32_cond_signal(kmp_win32_cond_t *cv) {
  __kmp_win32_cond_broadcast(cv);
}

void __kmp_enable(int new_state) {
  if (__kmp_init_runtime)
    LeaveCriticalSection(&__kmp_win32_section);
}

void __kmp_disable(int *old_state) {
  *old_state = 0;

  if (__kmp_init_runtime)
    EnterCriticalSection(&__kmp_win32_section);
}

void __kmp_suspend_initialize(void) { /* do nothing */
}

void __kmp_suspend_initialize_thread(kmp_info_t *th) {
  int old_value = KMP_ATOMIC_LD_RLX(&th->th.th_suspend_init);
  int new_value = TRUE;
  // Return if already initialized
  if (old_value == new_value)
    return;
  // Wait, then return if being initialized
  if (old_value == -1 ||
      !__kmp_atomic_compare_store(&th->th.th_suspend_init, old_value, -1)) {
    while (KMP_ATOMIC_LD_ACQ(&th->th.th_suspend_init) != new_value) {
      KMP_CPU_PAUSE();
    }
  } else {
    // Claim to be the initializer and do initializations
    __kmp_win32_cond_init(&th->th.th_suspend_cv);
    __kmp_win32_mutex_init(&th->th.th_suspend_mx);
    KMP_ATOMIC_ST_REL(&th->th.th_suspend_init, new_value);
  }
}

void __kmp_suspend_uninitialize_thread(kmp_info_t *th) {
  if (KMP_ATOMIC_LD_ACQ(&th->th.th_suspend_init)) {
    /* this means we have initialize the suspension pthread objects for this
       thread in this instance of the process */
    __kmp_win32_cond_destroy(&th->th.th_suspend_cv);
    __kmp_win32_mutex_destroy(&th->th.th_suspend_mx);
    KMP_ATOMIC_ST_REL(&th->th.th_suspend_init, FALSE);
  }
}

int __kmp_try_suspend_mx(kmp_info_t *th) {
  return __kmp_win32_mutex_trylock(&th->th.th_suspend_mx);
}

void __kmp_lock_suspend_mx(kmp_info_t *th) {
  __kmp_win32_mutex_lock(&th->th.th_suspend_mx);
}

void __kmp_unlock_suspend_mx(kmp_info_t *th) {
  __kmp_win32_mutex_unlock(&th->th.th_suspend_mx);
}

/* This routine puts the calling thread to sleep after setting the
   sleep bit for the indicated flag variable to true. */
template <class C>
static inline void __kmp_suspend_template(int th_gtid, C *flag) {
  kmp_info_t *th = __kmp_threads[th_gtid];
  typename C::flag_t old_spin;

  KF_TRACE(30, ("__kmp_suspend_template: T#%d enter for flag's loc(%p)\n",
                th_gtid, flag->get()));

  __kmp_suspend_initialize_thread(th);
  __kmp_lock_suspend_mx(th);

  KF_TRACE(10, ("__kmp_suspend_template: T#%d setting sleep bit for flag's"
                " loc(%p)\n",
                th_gtid, flag->get()));

  /* TODO: shouldn't this use release semantics to ensure that
     __kmp_suspend_initialize_thread gets called first? */
  old_spin = flag->set_sleeping();
  TCW_PTR(th->th.th_sleep_loc, (void *)flag);
  th->th.th_sleep_loc_type = flag->get_type();
  if (__kmp_dflt_blocktime == KMP_MAX_BLOCKTIME &&
      __kmp_pause_status != kmp_soft_paused) {
    flag->unset_sleeping();
    TCW_PTR(th->th.th_sleep_loc, NULL);
    th->th.th_sleep_loc_type = flag_unset;
    __kmp_unlock_suspend_mx(th);
    return;
  }

  KF_TRACE(5, ("__kmp_suspend_template: T#%d set sleep bit for flag's"
               " loc(%p)==%u\n",
               th_gtid, flag->get(), (unsigned int)flag->load()));

  if (flag->done_check_val(old_spin) || flag->done_check()) {
    flag->unset_sleeping();
    TCW_PTR(th->th.th_sleep_loc, NULL);
    th->th.th_sleep_loc_type = flag_unset;
    KF_TRACE(5, ("__kmp_suspend_template: T#%d false alarm, reset sleep bit "
                 "for flag's loc(%p)\n",
                 th_gtid, flag->get()));
  } else {
#ifdef DEBUG_SUSPEND
    __kmp_suspend_count++;
#endif
    /* Encapsulate in a loop as the documentation states that this may "with
       low probability" return when the condition variable has not been signaled
       or broadcast */
    int deactivated = FALSE;

    while (flag->is_sleeping()) {
      KF_TRACE(15, ("__kmp_suspend_template: T#%d about to perform "
                    "kmp_win32_cond_wait()\n",
                    th_gtid));
      // Mark the thread as no longer active (only in the first iteration of the
      // loop).
      if (!deactivated) {
        th->th.th_active = FALSE;
        if (th->th.th_active_in_pool) {
          th->th.th_active_in_pool = FALSE;
          KMP_ATOMIC_DEC(&__kmp_thread_pool_active_nth);
          KMP_DEBUG_ASSERT(TCR_4(__kmp_thread_pool_active_nth) >= 0);
        }
        deactivated = TRUE;
      }

      KMP_DEBUG_ASSERT(th->th.th_sleep_loc);
      KMP_DEBUG_ASSERT(th->th.th_sleep_loc_type == flag->get_type());

      __kmp_win32_cond_wait(&th->th.th_suspend_cv, &th->th.th_suspend_mx, th,
                            flag);

#ifdef KMP_DEBUG
      if (flag->is_sleeping()) {
        KF_TRACE(100,
                 ("__kmp_suspend_template: T#%d spurious wakeup\n", th_gtid));
      }
#endif /* KMP_DEBUG */

    } // while

    // We may have had the loop variable set before entering the loop body;
    // so we need to reset sleep_loc.
    TCW_PTR(th->th.th_sleep_loc, NULL);
    th->th.th_sleep_loc_type = flag_unset;

    KMP_DEBUG_ASSERT(!flag->is_sleeping());
    KMP_DEBUG_ASSERT(!th->th.th_sleep_loc);

    // Mark the thread as active again (if it was previous marked as inactive)
    if (deactivated) {
      th->th.th_active = TRUE;
      if (TCR_4(th->th.th_in_pool)) {
        KMP_ATOMIC_INC(&__kmp_thread_pool_active_nth);
        th->th.th_active_in_pool = TRUE;
      }
    }
  }

  __kmp_unlock_suspend_mx(th);
  KF_TRACE(30, ("__kmp_suspend_template: T#%d exit\n", th_gtid));
}

template <bool C, bool S>
void __kmp_suspend_32(int th_gtid, kmp_flag_32<C, S> *flag) {
  __kmp_suspend_template(th_gtid, flag);
}
template <bool C, bool S>
void __kmp_suspend_64(int th_gtid, kmp_flag_64<C, S> *flag) {
  __kmp_suspend_template(th_gtid, flag);
}
template <bool C, bool S>
void __kmp_atomic_suspend_64(int th_gtid, kmp_atomic_flag_64<C, S> *flag) {
  __kmp_suspend_template(th_gtid, flag);
}
void __kmp_suspend_oncore(int th_gtid, kmp_flag_oncore *flag) {
  __kmp_suspend_template(th_gtid, flag);
}

template void __kmp_suspend_32<false, false>(int, kmp_flag_32<false, false> *);
template void __kmp_suspend_64<false, true>(int, kmp_flag_64<false, true> *);
template void __kmp_suspend_64<true, false>(int, kmp_flag_64<true, false> *);
template void
__kmp_atomic_suspend_64<false, true>(int, kmp_atomic_flag_64<false, true> *);
template void
__kmp_atomic_suspend_64<true, false>(int, kmp_atomic_flag_64<true, false> *);

/* This routine signals the thread specified by target_gtid to wake up
   after setting the sleep bit indicated by the flag argument to FALSE */
template <class C>
static inline void __kmp_resume_template(int target_gtid, C *flag) {
  kmp_info_t *th = __kmp_threads[target_gtid];

#ifdef KMP_DEBUG
  int gtid = TCR_4(__kmp_init_gtid) ? __kmp_get_gtid() : -1;
#endif

  KF_TRACE(30, ("__kmp_resume_template: T#%d wants to wakeup T#%d enter\n",
                gtid, target_gtid));

  __kmp_suspend_initialize_thread(th);
  __kmp_lock_suspend_mx(th);

  if (!flag || flag != th->th.th_sleep_loc) {
    // coming from __kmp_null_resume_wrapper, or thread is now sleeping on a
    // different location; wake up at new location
    flag = (C *)th->th.th_sleep_loc;
  }

  // First, check if the flag is null or its type has changed. If so, someone
  // else woke it up.
  if (!flag || flag->get_type() != th->th.th_sleep_loc_type) {
    // simply shows what flag was cast to
    KF_TRACE(5, ("__kmp_resume_template: T#%d exiting, thread T#%d already "
                 "awake: flag's loc(%p)\n",
                 gtid, target_gtid, NULL));
    __kmp_unlock_suspend_mx(th);
    return;
  } else {
    if (!flag->is_sleeping()) {
      KF_TRACE(5, ("__kmp_resume_template: T#%d exiting, thread T#%d already "
                   "awake: flag's loc(%p): %u\n",
                   gtid, target_gtid, flag->get(), (unsigned int)flag->load()));
      __kmp_unlock_suspend_mx(th);
      return;
    }
  }
  KMP_DEBUG_ASSERT(flag);
  flag->unset_sleeping();
  TCW_PTR(th->th.th_sleep_loc, NULL);
  th->th.th_sleep_loc_type = flag_unset;

  KF_TRACE(5, ("__kmp_resume_template: T#%d about to wakeup T#%d, reset sleep "
               "bit for flag's loc(%p)\n",
               gtid, target_gtid, flag->get()));

  __kmp_win32_cond_signal(&th->th.th_suspend_cv);
  __kmp_unlock_suspend_mx(th);

  KF_TRACE(30, ("__kmp_resume_template: T#%d exiting after signaling wake up"
                " for T#%d\n",
                gtid, target_gtid));
}

template <bool C, bool S>
void __kmp_resume_32(int target_gtid, kmp_flag_32<C, S> *flag) {
  __kmp_resume_template(target_gtid, flag);
}
template <bool C, bool S>
void __kmp_resume_64(int target_gtid, kmp_flag_64<C, S> *flag) {
  __kmp_resume_template(target_gtid, flag);
}
template <bool C, bool S>
void __kmp_atomic_resume_64(int target_gtid, kmp_atomic_flag_64<C, S> *flag) {
  __kmp_resume_template(target_gtid, flag);
}
void __kmp_resume_oncore(int target_gtid, kmp_flag_oncore *flag) {
  __kmp_resume_template(target_gtid, flag);
}

template void __kmp_resume_32<false, true>(int, kmp_flag_32<false, true> *);
template void __kmp_resume_32<false, false>(int, kmp_flag_32<false, false> *);
template void __kmp_resume_64<false, true>(int, kmp_flag_64<false, true> *);
template void
__kmp_atomic_resume_64<false, true>(int, kmp_atomic_flag_64<false, true> *);

void __kmp_yield() { Sleep(0); }

void __kmp_gtid_set_specific(int gtid) {
  if (__kmp_init_gtid) {
    KA_TRACE(50, ("__kmp_gtid_set_specific: T#%d key:%d\n", gtid,
                  __kmp_gtid_threadprivate_key));
    kmp_intptr_t g = (kmp_intptr_t)gtid;
    if (!TlsSetValue(__kmp_gtid_threadprivate_key, (LPVOID)(g + 1)))
      KMP_FATAL(TLSSetValueFailed);
  } else {
    KA_TRACE(50, ("__kmp_gtid_set_specific: runtime shutdown, returning\n"));
  }
}

int __kmp_gtid_get_specific() {
  int gtid;
  if (!__kmp_init_gtid) {
    KA_TRACE(50, ("__kmp_gtid_get_specific: runtime shutdown, returning "
                  "KMP_GTID_SHUTDOWN\n"));
    return KMP_GTID_SHUTDOWN;
  }
  gtid = (int)(kmp_intptr_t)TlsGetValue(__kmp_gtid_threadprivate_key);
  if (gtid == 0) {
    gtid = KMP_GTID_DNE;
  } else {
    gtid--;
  }
  KA_TRACE(50, ("__kmp_gtid_get_specific: key:%d gtid:%d\n",
                __kmp_gtid_threadprivate_key, gtid));
  return gtid;
}

void __kmp_affinity_bind_thread(int proc) {
  if (__kmp_num_proc_groups > 1) {
    // Form the GROUP_AFFINITY struct directly, rather than filling
    // out a bit vector and calling __kmp_set_system_affinity().
    GROUP_AFFINITY ga;
    KMP_DEBUG_ASSERT((proc >= 0) && (proc < (__kmp_num_proc_groups * CHAR_BIT *
                                             sizeof(DWORD_PTR))));
    ga.Group = proc / (CHAR_BIT * sizeof(DWORD_PTR));
    ga.Mask = (unsigned long long)1 << (proc % (CHAR_BIT * sizeof(DWORD_PTR)));
    ga.Reserved[0] = ga.Reserved[1] = ga.Reserved[2] = 0;

    KMP_DEBUG_ASSERT(__kmp_SetThreadGroupAffinity != NULL);
    if (__kmp_SetThreadGroupAffinity(GetCurrentThread(), &ga, NULL) == 0) {
      DWORD error = GetLastError();
      // AC: continue silently if not verbose
      if (__kmp_affinity.flags.verbose) {
        kmp_msg_t err_code = KMP_ERR(error);
        __kmp_msg(kmp_ms_warning, KMP_MSG(CantSetThreadAffMask), err_code,
                  __kmp_msg_null);
        if (__kmp_generate_warnings == kmp_warnings_off) {
          __kmp_str_free(&err_code.str);
        }
      }
    }
  } else {
    kmp_affin_mask_t *mask;
    KMP_CPU_ALLOC_ON_STACK(mask);
    KMP_CPU_ZERO(mask);
    KMP_CPU_SET(proc, mask);
    __kmp_set_system_affinity(mask, TRUE);
    KMP_CPU_FREE_FROM_STACK(mask);
  }
}

void __kmp_affinity_determine_capable(const char *env_var) {
  // All versions of Windows* OS (since Win '95) support
  // SetThreadAffinityMask().

#if KMP_GROUP_AFFINITY
  KMP_AFFINITY_ENABLE(__kmp_num_proc_groups * sizeof(DWORD_PTR));
#else
  KMP_AFFINITY_ENABLE(sizeof(DWORD_PTR));
#endif

  KA_TRACE(10, ("__kmp_affinity_determine_capable: "
                "Windows* OS affinity interface functional (mask size = "
                "%" KMP_SIZE_T_SPEC ").\n",
                __kmp_affin_mask_size));
}

double __kmp_read_cpu_time(void) {
  FILETIME CreationTime, ExitTime, KernelTime, UserTime;
  int status;
  double cpu_time;

  cpu_time = 0;

  status = GetProcessTimes(GetCurrentProcess(), &CreationTime, &ExitTime,
                           &KernelTime, &UserTime);

  if (status) {
    double sec = 0;

    sec += KernelTime.dwHighDateTime;
    sec += UserTime.dwHighDateTime;

    /* Shift left by 32 bits */
    sec *= (double)(1 << 16) * (double)(1 << 16);

    sec += KernelTime.dwLowDateTime;
    sec += UserTime.dwLowDateTime;

    cpu_time += (sec * 100.0) / KMP_NSEC_PER_SEC;
  }

  return cpu_time;
}

int __kmp_read_system_info(struct kmp_sys_info *info) {
  info->maxrss = 0; /* the maximum resident set size utilized (in kilobytes) */
  info->minflt = 0; /* the number of page faults serviced without any I/O */
  info->majflt = 0; /* the number of page faults serviced that required I/O */
  info->nswap = 0; // the number of times a process was "swapped" out of memory
  info->inblock = 0; // the number of times the file system had to perform input
  info->oublock = 0; // number of times the file system had to perform output
  info->nvcsw = 0; /* the number of times a context switch was voluntarily */
  info->nivcsw = 0; /* the number of times a context switch was forced */

  return 1;
}

void __kmp_runtime_initialize(void) {
  SYSTEM_INFO info;
  kmp_str_buf_t path;
  UINT path_size;

  if (__kmp_init_runtime) {
    return;
  }

#if KMP_DYNAMIC_LIB
  /* Pin dynamic library for the lifetime of application */
  {
    // First, turn off error message boxes
    UINT err_mode = SetErrorMode(SEM_FAILCRITICALERRORS);
    HMODULE h;
    BOOL ret = GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS |
                                     GET_MODULE_HANDLE_EX_FLAG_PIN,
                                 (LPCTSTR)&__kmp_serial_initialize, &h);
    (void)ret;
    KMP_DEBUG_ASSERT2(h && ret, "OpenMP RTL cannot find itself loaded");
    SetErrorMode(err_mode); // Restore error mode
    KA_TRACE(10, ("__kmp_runtime_initialize: dynamic library pinned\n"));
  }
#endif

  InitializeCriticalSection(&__kmp_win32_section);
#if USE_ITT_BUILD
  __kmp_itt_system_object_created(&__kmp_win32_section, "Critical Section");
#endif /* USE_ITT_BUILD */
  __kmp_initialize_system_tick();

#if (KMP_ARCH_X86 || KMP_ARCH_X86_64)
  if (!__kmp_cpuinfo.initialized) {
    __kmp_query_cpuid(&__kmp_cpuinfo);
  }
#endif /* KMP_ARCH_X86 || KMP_ARCH_X86_64 */

/* Set up minimum number of threads to switch to TLS gtid */
#if KMP_OS_WINDOWS && !KMP_DYNAMIC_LIB
  // Windows* OS, static library.
  /* New thread may use stack space previously used by another thread,
     currently terminated. On Windows* OS, in case of static linking, we do not
     know the moment of thread termination, and our structures (__kmp_threads
     and __kmp_root arrays) are still keep info about dead threads. This leads
     to problem in __kmp_get_global_thread_id() function: it wrongly finds gtid
     (by searching through stack addresses of all known threads) for
     unregistered foreign tread.

     Setting __kmp_tls_gtid_min to 0 workarounds this problem:
     __kmp_get_global_thread_id() does not search through stacks, but get gtid
     from TLS immediately.
      --ln
  */
  __kmp_tls_gtid_min = 0;
#else
  __kmp_tls_gtid_min = KMP_TLS_GTID_MIN;
#endif

  /* for the static library */
  if (!__kmp_gtid_threadprivate_key) {
    __kmp_gtid_threadprivate_key = TlsAlloc();
    if (__kmp_gtid_threadprivate_key == TLS_OUT_OF_INDEXES) {
      KMP_FATAL(TLSOutOfIndexes);
    }
  }

  // Load ntdll.dll.
  /* Simple GetModuleHandle( "ntdll.dl" ) is not suitable due to security issue
     (see http://www.microsoft.com/technet/security/advisory/2269637.mspx). We
     have to specify full path to the library. */
  __kmp_str_buf_init(&path);
  path_size = GetSystemDirectory(path.str, path.size);
  KMP_DEBUG_ASSERT(path_size > 0);
  if (path_size >= path.size) {
    // Buffer is too short.  Expand the buffer and try again.
    __kmp_str_buf_reserve(&path, path_size);
    path_size = GetSystemDirectory(path.str, path.size);
    KMP_DEBUG_ASSERT(path_size > 0);
  }
  if (path_size > 0 && path_size < path.size) {
    // Now we have system directory name in the buffer.
    // Append backslash and name of dll to form full path,
    path.used = path_size;
    __kmp_str_buf_print(&path, "\\%s", "ntdll.dll");

    // Now load ntdll using full path.
    ntdll = GetModuleHandle(path.str);
  }

  KMP_DEBUG_ASSERT(ntdll != NULL);
  if (ntdll != NULL) {
    NtQuerySystemInformation = (NtQuerySystemInformation_t)GetProcAddress(
        ntdll, "NtQuerySystemInformation");
  }
  KMP_DEBUG_ASSERT(NtQuerySystemInformation != NULL);

#if KMP_GROUP_AFFINITY
  // Load kernel32.dll.
  // Same caveat - must use full system path name.
  if (path_size > 0 && path_size < path.size) {
    // Truncate the buffer back to just the system path length,
    // discarding "\\ntdll.dll", and replacing it with "kernel32.dll".
    path.used = path_size;
    __kmp_str_buf_print(&path, "\\%s", "kernel32.dll");

    // Load kernel32.dll using full path.
    kernel32 = GetModuleHandle(path.str);
    KA_TRACE(10, ("__kmp_runtime_initialize: kernel32.dll = %s\n", path.str));

    // Load the function pointers to kernel32.dll routines
    // that may or may not exist on this system.
    if (kernel32 != NULL) {
      __kmp_GetActiveProcessorCount =
          (kmp_GetActiveProcessorCount_t)GetProcAddress(
              kernel32, "GetActiveProcessorCount");
      __kmp_GetActiveProcessorGroupCount =
          (kmp_GetActiveProcessorGroupCount_t)GetProcAddress(
              kernel32, "GetActiveProcessorGroupCount");
      __kmp_GetThreadGroupAffinity =
          (kmp_GetThreadGroupAffinity_t)GetProcAddress(
              kernel32, "GetThreadGroupAffinity");
      __kmp_SetThreadGroupAffinity =
          (kmp_SetThreadGroupAffinity_t)GetProcAddress(
              kernel32, "SetThreadGroupAffinity");

      KA_TRACE(10, ("__kmp_runtime_initialize: __kmp_GetActiveProcessorCount"
                    " = %p\n",
                    __kmp_GetActiveProcessorCount));
      KA_TRACE(10, ("__kmp_runtime_initialize: "
                    "__kmp_GetActiveProcessorGroupCount = %p\n",
                    __kmp_GetActiveProcessorGroupCount));
      KA_TRACE(10, ("__kmp_runtime_initialize:__kmp_GetThreadGroupAffinity"
                    " = %p\n",
                    __kmp_GetThreadGroupAffinity));
      KA_TRACE(10, ("__kmp_runtime_initialize: __kmp_SetThreadGroupAffinity"
                    " = %p\n",
                    __kmp_SetThreadGroupAffinity));
      KA_TRACE(10, ("__kmp_runtime_initialize: sizeof(kmp_affin_mask_t) = %d\n",
                    sizeof(kmp_affin_mask_t)));

      // See if group affinity is supported on this system.
      // If so, calculate the #groups and #procs.
      //
      // Group affinity was introduced with Windows* 7 OS and
      // Windows* Server 2008 R2 OS.
      if ((__kmp_GetActiveProcessorCount != NULL) &&
          (__kmp_GetActiveProcessorGroupCount != NULL) &&
          (__kmp_GetThreadGroupAffinity != NULL) &&
          (__kmp_SetThreadGroupAffinity != NULL) &&
          ((__kmp_num_proc_groups = __kmp_GetActiveProcessorGroupCount()) >
           1)) {
        // Calculate the total number of active OS procs.
        int i;

        KA_TRACE(10, ("__kmp_runtime_initialize: %d processor groups"
                      " detected\n",
                      __kmp_num_proc_groups));

        __kmp_xproc = 0;

        for (i = 0; i < __kmp_num_proc_groups; i++) {
          DWORD size = __kmp_GetActiveProcessorCount(i);
          __kmp_xproc += size;
          KA_TRACE(10, ("__kmp_runtime_initialize: proc group %d size = %d\n",
                        i, size));
        }
      } else {
        KA_TRACE(10, ("__kmp_runtime_initialize: %d processor groups"
                      " detected\n",
                      __kmp_num_proc_groups));
      }
    }
  }
  if (__kmp_num_proc_groups <= 1) {
    GetSystemInfo(&info);
    __kmp_xproc = info.dwNumberOfProcessors;
  }
#else
  (void)kernel32;
  GetSystemInfo(&info);
  __kmp_xproc = info.dwNumberOfProcessors;
#endif /* KMP_GROUP_AFFINITY */

  // If the OS said there were 0 procs, take a guess and use a value of 2.
  // This is done for Linux* OS, also.  Do we need error / warning?
  if (__kmp_xproc <= 0) {
    __kmp_xproc = 2;
  }

  KA_TRACE(5,
           ("__kmp_runtime_initialize: total processors = %d\n", __kmp_xproc));

  __kmp_str_buf_free(&path);

#if USE_ITT_BUILD
  __kmp_itt_initialize();
#endif /* USE_ITT_BUILD */

  __kmp_init_runtime = TRUE;
} // __kmp_runtime_initialize

void __kmp_runtime_destroy(void) {
  if (!__kmp_init_runtime) {
    return;
  }

#if USE_ITT_BUILD
  __kmp_itt_destroy();
#endif /* USE_ITT_BUILD */

  /* we can't DeleteCriticalsection( & __kmp_win32_section ); */
  /* due to the KX_TRACE() commands */
  KA_TRACE(40, ("__kmp_runtime_destroy\n"));

  if (__kmp_gtid_threadprivate_key) {
    TlsFree(__kmp_gtid_threadprivate_key);
    __kmp_gtid_threadprivate_key = 0;
  }

  __kmp_affinity_uninitialize();
  DeleteCriticalSection(&__kmp_win32_section);

  ntdll = NULL;
  NtQuerySystemInformation = NULL;

#if KMP_ARCH_X86_64
  kernel32 = NULL;
  __kmp_GetActiveProcessorCount = NULL;
  __kmp_GetActiveProcessorGroupCount = NULL;
  __kmp_GetThreadGroupAffinity = NULL;
  __kmp_SetThreadGroupAffinity = NULL;
#endif // KMP_ARCH_X86_64

  __kmp_init_runtime = FALSE;
}

void __kmp_terminate_thread(int gtid) {
  kmp_info_t *th = __kmp_threads[gtid];

  if (!th)
    return;

  KA_TRACE(10, ("__kmp_terminate_thread: kill (%d)\n", gtid));

  if (TerminateThread(th->th.th_info.ds.ds_thread, (DWORD)-1) == FALSE) {
    /* It's OK, the thread may have exited already */
  }
  __kmp_free_handle(th->th.th_info.ds.ds_thread);
}

void __kmp_clear_system_time(void) {
  LARGE_INTEGER time;
  QueryPerformanceCounter(&time);
  __kmp_win32_time = (kmp_int64)time.QuadPart;
}

void __kmp_initialize_system_tick(void) {
  {
    BOOL status;
    LARGE_INTEGER freq;

    status = QueryPerformanceFrequency(&freq);
    if (!status) {
      DWORD error = GetLastError();
      __kmp_fatal(KMP_MSG(FunctionError, "QueryPerformanceFrequency()"),
                  KMP_ERR(error), __kmp_msg_null);

    } else {
      __kmp_win32_tick = ((double)1.0) / (double)freq.QuadPart;
    }
  }
}

/* Calculate the elapsed wall clock time for the user */

void __kmp_elapsed(double *t) {
  LARGE_INTEGER now;
  QueryPerformanceCounter(&now);
  *t = ((double)now.QuadPart) * __kmp_win32_tick;
}

/* Calculate the elapsed wall clock tick for the user */

void __kmp_elapsed_tick(double *t) { *t = __kmp_win32_tick; }

void __kmp_read_system_time(double *delta) {
  if (delta != NULL) {
    LARGE_INTEGER now;
    QueryPerformanceCounter(&now);
    *delta = ((double)(((kmp_int64)now.QuadPart) - __kmp_win32_time)) *
             __kmp_win32_tick;
  }
}

/* Return the current time stamp in nsec */
kmp_uint64 __kmp_now_nsec() {
  LARGE_INTEGER now;
  QueryPerformanceCounter(&now);
  return 1e9 * __kmp_win32_tick * now.QuadPart;
}

extern "C" void *__stdcall __kmp_launch_worker(void *arg) {
  volatile void *stack_data;
  void *exit_val;
  void *padding = 0;
  kmp_info_t *this_thr = (kmp_info_t *)arg;
  int gtid;

  gtid = this_thr->th.th_info.ds.ds_gtid;
  __kmp_gtid_set_specific(gtid);
#ifdef KMP_TDATA_GTID
#error "This define causes problems with LoadLibrary() + declspec(thread) " \
        "on Windows* OS.  See CQ50564, tests kmp_load_library*.c and this MSDN " \
        "reference: http://support.microsoft.com/kb/118816"
//__kmp_gtid = gtid;
#endif

#if USE_ITT_BUILD
  __kmp_itt_thread_name(gtid);
#endif /* USE_ITT_BUILD */

  __kmp_affinity_bind_init_mask(gtid);

#if KMP_ARCH_X86 || KMP_ARCH_X86_64
  // Set FP control regs to be a copy of the parallel initialization thread's.
  __kmp_clear_x87_fpu_status_word();
  __kmp_load_x87_fpu_control_word(&__kmp_init_x87_fpu_control_word);
  __kmp_load_mxcsr(&__kmp_init_mxcsr);
#endif /* KMP_ARCH_X86 || KMP_ARCH_X86_64 */

  if (__kmp_stkoffset > 0 && gtid > 0) {
    padding = KMP_ALLOCA(gtid * __kmp_stkoffset);
    (void)padding;
  }

  KMP_FSYNC_RELEASING(&this_thr->th.th_info.ds.ds_alive);
  this_thr->th.th_info.ds.ds_thread_id = GetCurrentThreadId();
  TCW_4(this_thr->th.th_info.ds.ds_alive, TRUE);

  if (TCR_4(__kmp_gtid_mode) <
      2) { // check stack only if it is used to get gtid
    TCW_PTR(this_thr->th.th_info.ds.ds_stackbase, &stack_data);
    KMP_ASSERT(this_thr->th.th_info.ds.ds_stackgrow == FALSE);
    __kmp_check_stack_overlap(this_thr);
  }
  KMP_MB();
  exit_val = __kmp_launch_thread(this_thr);
  KMP_FSYNC_RELEASING(&this_thr->th.th_info.ds.ds_alive);
  TCW_4(this_thr->th.th_info.ds.ds_alive, FALSE);
  KMP_MB();
  return exit_val;
}

#if KMP_USE_MONITOR
/* The monitor thread controls all of the threads in the complex */

void *__stdcall __kmp_launch_monitor(void *arg) {
  DWORD wait_status;
  kmp_thread_t monitor;
  int status;
  int interval;
  kmp_info_t *this_thr = (kmp_info_t *)arg;

  KMP_DEBUG_ASSERT(__kmp_init_monitor);
  TCW_4(__kmp_init_monitor, 2); // AC: Signal library that monitor has started
  // TODO: hide "2" in enum (like {true,false,started})
  this_thr->th.th_info.ds.ds_thread_id = GetCurrentThreadId();
  TCW_4(this_thr->th.th_info.ds.ds_alive, TRUE);

  KMP_MB(); /* Flush all pending memory write invalidates.  */
  KA_TRACE(10, ("__kmp_launch_monitor: launched\n"));

  monitor = GetCurrentThread();

  /* set thread priority */
  status = SetThreadPriority(monitor, THREAD_PRIORITY_HIGHEST);
  if (!status) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantSetThreadPriority), KMP_ERR(error), __kmp_msg_null);
  }

  /* register us as monitor */
  __kmp_gtid_set_specific(KMP_GTID_MONITOR);
#ifdef KMP_TDATA_GTID
#error "This define causes problems with LoadLibrary() + declspec(thread) " \
        "on Windows* OS.  See CQ50564, tests kmp_load_library*.c and this MSDN " \
        "reference: http://support.microsoft.com/kb/118816"
//__kmp_gtid = KMP_GTID_MONITOR;
#endif

#if USE_ITT_BUILD
  __kmp_itt_thread_ignore(); // Instruct Intel(R) Threading Tools to ignore
// monitor thread.
#endif /* USE_ITT_BUILD */

  KMP_MB(); /* Flush all pending memory write invalidates.  */

  interval = (1000 / __kmp_monitor_wakeups); /* in milliseconds */

  while (!TCR_4(__kmp_global.g.g_done)) {
    /*  This thread monitors the state of the system */

    KA_TRACE(15, ("__kmp_launch_monitor: update\n"));

    wait_status = WaitForSingleObject(__kmp_monitor_ev, interval);

    if (wait_status == WAIT_TIMEOUT) {
      TCW_4(__kmp_global.g.g_time.dt.t_value,
            TCR_4(__kmp_global.g.g_time.dt.t_value) + 1);
    }

    KMP_MB(); /* Flush all pending memory write invalidates.  */
  }

  KA_TRACE(10, ("__kmp_launch_monitor: finished\n"));

  status = SetThreadPriority(monitor, THREAD_PRIORITY_NORMAL);
  if (!status) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantSetThreadPriority), KMP_ERR(error), __kmp_msg_null);
  }

  if (__kmp_global.g.g_abort != 0) {
    /* now we need to terminate the worker threads   */
    /* the value of t_abort is the signal we caught */
    int gtid;

    KA_TRACE(10, ("__kmp_launch_monitor: terminate sig=%d\n",
                  (__kmp_global.g.g_abort)));

    /* terminate the OpenMP worker threads */
    /* TODO this is not valid for sibling threads!!
     * the uber master might not be 0 anymore.. */
    for (gtid = 1; gtid < __kmp_threads_capacity; ++gtid)
      __kmp_terminate_thread(gtid);

    __kmp_cleanup();

    Sleep(0);

    KA_TRACE(10,
             ("__kmp_launch_monitor: raise sig=%d\n", __kmp_global.g.g_abort));

    if (__kmp_global.g.g_abort > 0) {
      raise(__kmp_global.g.g_abort);
    }
  }

  TCW_4(this_thr->th.th_info.ds.ds_alive, FALSE);

  KMP_MB();
  return arg;
}
#endif

void __kmp_create_worker(int gtid, kmp_info_t *th, size_t stack_size) {
  kmp_thread_t handle;
  DWORD idThread;

  KA_TRACE(10, ("__kmp_create_worker: try to create thread (%d)\n", gtid));

  th->th.th_info.ds.ds_gtid = gtid;

  if (KMP_UBER_GTID(gtid)) {
    int stack_data;

    /* TODO: GetCurrentThread() returns a pseudo-handle that is unsuitable for
       other threads to use. Is it appropriate to just use GetCurrentThread?
       When should we close this handle?  When unregistering the root? */
    {
      BOOL rc;
      rc = DuplicateHandle(GetCurrentProcess(), GetCurrentThread(),
                           GetCurrentProcess(), &th->th.th_info.ds.ds_thread, 0,
                           FALSE, DUPLICATE_SAME_ACCESS);
      KMP_ASSERT(rc);
      KA_TRACE(10, (" __kmp_create_worker: ROOT Handle duplicated, th = %p, "
                    "handle = %" KMP_UINTPTR_SPEC "\n",
                    (LPVOID)th, th->th.th_info.ds.ds_thread));
      th->th.th_info.ds.ds_thread_id = GetCurrentThreadId();
    }
    if (TCR_4(__kmp_gtid_mode) < 2) { // check stack only if used to get gtid
      /* we will dynamically update the stack range if gtid_mode == 1 */
      TCW_PTR(th->th.th_info.ds.ds_stackbase, &stack_data);
      TCW_PTR(th->th.th_info.ds.ds_stacksize, 0);
      TCW_4(th->th.th_info.ds.ds_stackgrow, TRUE);
      __kmp_check_stack_overlap(th);
    }
  } else {
    KMP_MB(); /* Flush all pending memory write invalidates.  */

    /* Set stack size for this thread now. */
    KA_TRACE(10,
             ("__kmp_create_worker: stack_size = %" KMP_SIZE_T_SPEC " bytes\n",
              stack_size));

    stack_size += gtid * __kmp_stkoffset;

    TCW_PTR(th->th.th_info.ds.ds_stacksize, stack_size);
    TCW_4(th->th.th_info.ds.ds_stackgrow, FALSE);

    KA_TRACE(10,
             ("__kmp_create_worker: (before) stack_size = %" KMP_SIZE_T_SPEC
              " bytes, &__kmp_launch_worker = %p, th = %p, &idThread = %p\n",
              (SIZE_T)stack_size, (LPTHREAD_START_ROUTINE)&__kmp_launch_worker,
              (LPVOID)th, &idThread));

    handle = CreateThread(
        NULL, (SIZE_T)stack_size, (LPTHREAD_START_ROUTINE)__kmp_launch_worker,
        (LPVOID)th, STACK_SIZE_PARAM_IS_A_RESERVATION, &idThread);

    KA_TRACE(10,
             ("__kmp_create_worker: (after) stack_size = %" KMP_SIZE_T_SPEC
              " bytes, &__kmp_launch_worker = %p, th = %p, "
              "idThread = %u, handle = %" KMP_UINTPTR_SPEC "\n",
              (SIZE_T)stack_size, (LPTHREAD_START_ROUTINE)&__kmp_launch_worker,
              (LPVOID)th, idThread, handle));

    if (handle == 0) {
      DWORD error = GetLastError();
      __kmp_fatal(KMP_MSG(CantCreateThread), KMP_ERR(error), __kmp_msg_null);
    } else {
      th->th.th_info.ds.ds_thread = handle;
    }

    KMP_MB(); /* Flush all pending memory write invalidates.  */
  }

  KA_TRACE(10, ("__kmp_create_worker: done creating thread (%d)\n", gtid));
}

int __kmp_still_running(kmp_info_t *th) {
  return (WAIT_TIMEOUT == WaitForSingleObject(th->th.th_info.ds.ds_thread, 0));
}

#if KMP_USE_MONITOR
void __kmp_create_monitor(kmp_info_t *th) {
  kmp_thread_t handle;
  DWORD idThread;
  int ideal, new_ideal;

  if (__kmp_dflt_blocktime == KMP_MAX_BLOCKTIME) {
    // We don't need monitor thread in case of MAX_BLOCKTIME
    KA_TRACE(10, ("__kmp_create_monitor: skipping monitor thread because of "
                  "MAX blocktime\n"));
    th->th.th_info.ds.ds_tid = 0; // this makes reap_monitor no-op
    th->th.th_info.ds.ds_gtid = 0;
    TCW_4(__kmp_init_monitor, 2); // Signal to stop waiting for monitor creation
    return;
  }
  KA_TRACE(10, ("__kmp_create_monitor: try to create monitor\n"));

  KMP_MB(); /* Flush all pending memory write invalidates.  */

  __kmp_monitor_ev = CreateEvent(NULL, TRUE, FALSE, NULL);
  if (__kmp_monitor_ev == NULL) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantCreateEvent), KMP_ERR(error), __kmp_msg_null);
  }
#if USE_ITT_BUILD
  __kmp_itt_system_object_created(__kmp_monitor_ev, "Event");
#endif /* USE_ITT_BUILD */

  th->th.th_info.ds.ds_tid = KMP_GTID_MONITOR;
  th->th.th_info.ds.ds_gtid = KMP_GTID_MONITOR;

  // FIXME - on Windows* OS, if __kmp_monitor_stksize = 0, figure out how
  // to automatically expand stacksize based on CreateThread error code.
  if (__kmp_monitor_stksize == 0) {
    __kmp_monitor_stksize = KMP_DEFAULT_MONITOR_STKSIZE;
  }
  if (__kmp_monitor_stksize < __kmp_sys_min_stksize) {
    __kmp_monitor_stksize = __kmp_sys_min_stksize;
  }

  KA_TRACE(10, ("__kmp_create_monitor: requested stacksize = %d bytes\n",
                (int)__kmp_monitor_stksize));

  TCW_4(__kmp_global.g.g_time.dt.t_value, 0);

  handle =
      CreateThread(NULL, (SIZE_T)__kmp_monitor_stksize,
                   (LPTHREAD_START_ROUTINE)__kmp_launch_monitor, (LPVOID)th,
                   STACK_SIZE_PARAM_IS_A_RESERVATION, &idThread);
  if (handle == 0) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantCreateThread), KMP_ERR(error), __kmp_msg_null);
  } else
    th->th.th_info.ds.ds_thread = handle;

  KMP_MB(); /* Flush all pending memory write invalidates.  */

  KA_TRACE(10, ("__kmp_create_monitor: monitor created %p\n",
                (void *)th->th.th_info.ds.ds_thread));
}
#endif

/* Check to see if thread is still alive.
   NOTE:  The ExitProcess(code) system call causes all threads to Terminate
   with a exit_val = code.  Because of this we can not rely on exit_val having
   any particular value.  So this routine may return STILL_ALIVE in exit_val
   even after the thread is dead. */

int __kmp_is_thread_alive(kmp_info_t *th, DWORD *exit_val) {
  DWORD rc;
  rc = GetExitCodeThread(th->th.th_info.ds.ds_thread, exit_val);
  if (rc == 0) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(FunctionError, "GetExitCodeThread()"), KMP_ERR(error),
                __kmp_msg_null);
  }
  return (*exit_val == STILL_ACTIVE);
}

void __kmp_exit_thread(int exit_status) {
  ExitThread(exit_status);
} // __kmp_exit_thread

// This is a common part for both __kmp_reap_worker() and __kmp_reap_monitor().
static void __kmp_reap_common(kmp_info_t *th) {
  DWORD exit_val;

  KMP_MB(); /* Flush all pending memory write invalidates.  */

  KA_TRACE(
      10, ("__kmp_reap_common: try to reap (%d)\n", th->th.th_info.ds.ds_gtid));

  /* 2006-10-19:
     There are two opposite situations:
     1. Windows* OS keep thread alive after it resets ds_alive flag and
     exits from thread function. (For example, see C70770/Q394281 "unloading of
     dll based on OMP is very slow".)
     2. Windows* OS may kill thread before it resets ds_alive flag.

     Right solution seems to be waiting for *either* thread termination *or*
     ds_alive resetting. */
  {
    // TODO: This code is very similar to KMP_WAIT. Need to generalize
    // KMP_WAIT to cover this usage also.
    void *obj = NULL;
    kmp_uint32 spins;
    kmp_uint64 time;
#if USE_ITT_BUILD
    KMP_FSYNC_SPIN_INIT(obj, (void *)&th->th.th_info.ds.ds_alive);
#endif /* USE_ITT_BUILD */
    KMP_INIT_YIELD(spins);
    KMP_INIT_BACKOFF(time);
    do {
#if USE_ITT_BUILD
      KMP_FSYNC_SPIN_PREPARE(obj);
#endif /* USE_ITT_BUILD */
      __kmp_is_thread_alive(th, &exit_val);
      KMP_YIELD_OVERSUB_ELSE_SPIN(spins, time);
    } while (exit_val == STILL_ACTIVE && TCR_4(th->th.th_info.ds.ds_alive));
#if USE_ITT_BUILD
    if (exit_val == STILL_ACTIVE) {
      KMP_FSYNC_CANCEL(obj);
    } else {
      KMP_FSYNC_SPIN_ACQUIRED(obj);
    }
#endif /* USE_ITT_BUILD */
  }

  __kmp_free_handle(th->th.th_info.ds.ds_thread);

  /* NOTE:  The ExitProcess(code) system call causes all threads to Terminate
     with a exit_val = code.  Because of this we can not rely on exit_val having
     any particular value. */
  kmp_intptr_t e = (kmp_intptr_t)exit_val;
  if (exit_val == STILL_ACTIVE) {
    KA_TRACE(1, ("__kmp_reap_common: thread still active.\n"));
  } else if ((void *)e != (void *)th) {
    KA_TRACE(1, ("__kmp_reap_common: ExitProcess / TerminateThread used?\n"));
  }

  KA_TRACE(10,
           ("__kmp_reap_common: done reaping (%d), handle = %" KMP_UINTPTR_SPEC
            "\n",
            th->th.th_info.ds.ds_gtid, th->th.th_info.ds.ds_thread));

  th->th.th_info.ds.ds_thread = 0;
  th->th.th_info.ds.ds_tid = KMP_GTID_DNE;
  th->th.th_info.ds.ds_gtid = KMP_GTID_DNE;
  th->th.th_info.ds.ds_thread_id = 0;

  KMP_MB(); /* Flush all pending memory write invalidates.  */
}

#if KMP_USE_MONITOR
void __kmp_reap_monitor(kmp_info_t *th) {
  int status;

  KA_TRACE(10, ("__kmp_reap_monitor: try to reap %p\n",
                (void *)th->th.th_info.ds.ds_thread));

  // If monitor has been created, its tid and gtid should be KMP_GTID_MONITOR.
  // If both tid and gtid are 0, it means the monitor did not ever start.
  // If both tid and gtid are KMP_GTID_DNE, the monitor has been shut down.
  KMP_DEBUG_ASSERT(th->th.th_info.ds.ds_tid == th->th.th_info.ds.ds_gtid);
  if (th->th.th_info.ds.ds_gtid != KMP_GTID_MONITOR) {
    KA_TRACE(10, ("__kmp_reap_monitor: monitor did not start, returning\n"));
    return;
  }

  KMP_MB(); /* Flush all pending memory write invalidates.  */

  status = SetEvent(__kmp_monitor_ev);
  if (status == FALSE) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantSetEvent), KMP_ERR(error), __kmp_msg_null);
  }
  KA_TRACE(10, ("__kmp_reap_monitor: reaping thread (%d)\n",
                th->th.th_info.ds.ds_gtid));
  __kmp_reap_common(th);

  __kmp_free_handle(__kmp_monitor_ev);

  KMP_MB(); /* Flush all pending memory write invalidates.  */
}
#endif

void __kmp_reap_worker(kmp_info_t *th) {
  KA_TRACE(10, ("__kmp_reap_worker: reaping thread (%d)\n",
                th->th.th_info.ds.ds_gtid));
  __kmp_reap_common(th);
}

#if KMP_HANDLE_SIGNALS

static void __kmp_team_handler(int signo) {
  if (__kmp_global.g.g_abort == 0) {
    // Stage 1 signal handler, let's shut down all of the threads.
    if (__kmp_debug_buf) {
      __kmp_dump_debug_buffer();
    }
    KMP_MB(); // Flush all pending memory write invalidates.
    TCW_4(__kmp_global.g.g_abort, signo);
    KMP_MB(); // Flush all pending memory write invalidates.
    TCW_4(__kmp_global.g.g_done, TRUE);
    KMP_MB(); // Flush all pending memory write invalidates.
  }
} // __kmp_team_handler

static sig_func_t __kmp_signal(int signum, sig_func_t handler) {
  sig_func_t old = signal(signum, handler);
  if (old == SIG_ERR) {
    int error = errno;
    __kmp_fatal(KMP_MSG(FunctionError, "signal"), KMP_ERR(error),
                __kmp_msg_null);
  }
  return old;
}

static void __kmp_install_one_handler(int sig, sig_func_t handler,
                                      int parallel_init) {
  sig_func_t old;
  KMP_MB(); /* Flush all pending memory write invalidates.  */
  KB_TRACE(60, ("__kmp_install_one_handler: called: sig=%d\n", sig));
  if (parallel_init) {
    old = __kmp_signal(sig, handler);
    // SIG_DFL on Windows* OS in NULL or 0.
    if (old == __kmp_sighldrs[sig]) {
      __kmp_siginstalled[sig] = 1;
    } else { // Restore/keep user's handler if one previously installed.
      old = __kmp_signal(sig, old);
    }
  } else {
    // Save initial/system signal handlers to see if user handlers installed.
    // 2009-09-23: It is a dead code. On Windows* OS __kmp_install_signals
    // called once with parallel_init == TRUE.
    old = __kmp_signal(sig, SIG_DFL);
    __kmp_sighldrs[sig] = old;
    __kmp_signal(sig, old);
  }
  KMP_MB(); /* Flush all pending memory write invalidates.  */
} // __kmp_install_one_handler

static void __kmp_remove_one_handler(int sig) {
  if (__kmp_siginstalled[sig]) {
    sig_func_t old;
    KMP_MB(); // Flush all pending memory write invalidates.
    KB_TRACE(60, ("__kmp_remove_one_handler: called: sig=%d\n", sig));
    old = __kmp_signal(sig, __kmp_sighldrs[sig]);
    if (old != __kmp_team_handler) {
      KB_TRACE(10, ("__kmp_remove_one_handler: oops, not our handler, "
                    "restoring: sig=%d\n",
                    sig));
      old = __kmp_signal(sig, old);
    }
    __kmp_sighldrs[sig] = NULL;
    __kmp_siginstalled[sig] = 0;
    KMP_MB(); // Flush all pending memory write invalidates.
  }
} // __kmp_remove_one_handler

void __kmp_install_signals(int parallel_init) {
  KB_TRACE(10, ("__kmp_install_signals: called\n"));
  if (!__kmp_handle_signals) {
    KB_TRACE(10, ("__kmp_install_signals: KMP_HANDLE_SIGNALS is false - "
                  "handlers not installed\n"));
    return;
  }
  __kmp_install_one_handler(SIGINT, __kmp_team_handler, parallel_init);
  __kmp_install_one_handler(SIGILL, __kmp_team_handler, parallel_init);
  __kmp_install_one_handler(SIGABRT, __kmp_team_handler, parallel_init);
  __kmp_install_one_handler(SIGFPE, __kmp_team_handler, parallel_init);
  __kmp_install_one_handler(SIGSEGV, __kmp_team_handler, parallel_init);
  __kmp_install_one_handler(SIGTERM, __kmp_team_handler, parallel_init);
} // __kmp_install_signals

void __kmp_remove_signals(void) {
  int sig;
  KB_TRACE(10, ("__kmp_remove_signals: called\n"));
  for (sig = 1; sig < NSIG; ++sig) {
    __kmp_remove_one_handler(sig);
  }
} // __kmp_remove_signals

#endif // KMP_HANDLE_SIGNALS

/* Put the thread to sleep for a time period */
void __kmp_thread_sleep(int millis) {
  DWORD status;

  status = SleepEx((DWORD)millis, FALSE);
  if (status) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(FunctionError, "SleepEx()"), KMP_ERR(error),
                __kmp_msg_null);
  }
}

// Determine whether the given address is mapped into the current address space.
int __kmp_is_address_mapped(void *addr) {
  MEMORY_BASIC_INFORMATION lpBuffer;
  SIZE_T dwLength;

  dwLength = sizeof(MEMORY_BASIC_INFORMATION);

  VirtualQuery(addr, &lpBuffer, dwLength);

  return !(((lpBuffer.State == MEM_RESERVE) || (lpBuffer.State == MEM_FREE)) ||
           ((lpBuffer.Protect == PAGE_NOACCESS) ||
            (lpBuffer.Protect == PAGE_EXECUTE)));
}

kmp_uint64 __kmp_hardware_timestamp(void) {
  kmp_uint64 r = 0;

  QueryPerformanceCounter((LARGE_INTEGER *)&r);
  return r;
}

/* Free handle and check the error code */
void __kmp_free_handle(kmp_thread_t tHandle) {
  /* called with parameter type HANDLE also, thus suppose kmp_thread_t defined
   * as HANDLE */
  BOOL rc;
  rc = CloseHandle(tHandle);
  if (!rc) {
    DWORD error = GetLastError();
    __kmp_fatal(KMP_MSG(CantCloseHandle), KMP_ERR(error), __kmp_msg_null);
  }
}

int __kmp_get_load_balance(int max) {
  static ULONG glb_buff_size = 100 * 1024;

  // Saved count of the running threads for the thread balance algorithm
  static int glb_running_threads = 0;
  static double glb_call_time = 0; /* Thread balance algorithm call time */

  int running_threads = 0; // Number of running threads in the system.
  NTSTATUS status = 0;
  ULONG buff_size = 0;
  ULONG info_size = 0;
  void *buffer = NULL;
  PSYSTEM_PROCESS_INFORMATION spi = NULL;
  int first_time = 1;

  double call_time = 0.0; // start, finish;

  __kmp_elapsed(&call_time);

  if (glb_call_time &&
      (call_time - glb_call_time < __kmp_load_balance_interval)) {
    running_threads = glb_running_threads;
    goto finish;
  }
  glb_call_time = call_time;

  // Do not spend time on running algorithm if we have a permanent error.
  if (NtQuerySystemInformation == NULL) {
    running_threads = -1;
    goto finish;
  }

  if (max <= 0) {
    max = INT_MAX;
  }

  do {

    if (first_time) {
      buff_size = glb_buff_size;
    } else {
      buff_size = 2 * buff_size;
    }

    buffer = KMP_INTERNAL_REALLOC(buffer, buff_size);
    if (buffer == NULL) {
      running_threads = -1;
      goto finish;
    }
    status = NtQuerySystemInformation(SystemProcessInformation, buffer,
                                      buff_size, &info_size);
    first_time = 0;

  } while (status == STATUS_INFO_LENGTH_MISMATCH);
  glb_buff_size = buff_size;

#define CHECK(cond)                                                            \
  {                                                                            \
    KMP_DEBUG_ASSERT(cond);                                                    \
    if (!(cond)) {                                                             \
      running_threads = -1;                                                    \
      goto finish;                                                             \
    }                                                                          \
  }

  CHECK(buff_size >= info_size);
  spi = PSYSTEM_PROCESS_INFORMATION(buffer);
  for (;;) {
    ptrdiff_t offset = uintptr_t(spi) - uintptr_t(buffer);
    CHECK(0 <= offset &&
          offset + sizeof(SYSTEM_PROCESS_INFORMATION) < info_size);
    HANDLE pid = spi->ProcessId;
    ULONG num = spi->NumberOfThreads;
    CHECK(num >= 1);
    size_t spi_size =
        sizeof(SYSTEM_PROCESS_INFORMATION) + sizeof(SYSTEM_THREAD) * (num - 1);
    CHECK(offset + spi_size <
          info_size); // Make sure process info record fits the buffer.
    if (spi->NextEntryOffset != 0) {
      CHECK(spi_size <=
            spi->NextEntryOffset); // And do not overlap with the next record.
    }
    // pid == 0 corresponds to the System Idle Process. It always has running
    // threads on all cores. So, we don't consider the running threads of this
    // process.
    if (pid != 0) {
      for (ULONG i = 0; i < num; ++i) {
        THREAD_STATE state = spi->Threads[i].State;
        // Count threads that have Ready or Running state.
        // !!! TODO: Why comment does not match the code???
        if (state == StateRunning) {
          ++running_threads;
          // Stop counting running threads if the number is already greater than
          // the number of available cores
          if (running_threads >= max) {
            goto finish;
          }
        }
      }
    }
    if (spi->NextEntryOffset == 0) {
      break;
    }
    spi = PSYSTEM_PROCESS_INFORMATION(uintptr_t(spi) + spi->NextEntryOffset);
  }

#undef CHECK

finish: // Clean up and exit.

  if (buffer != NULL) {
    KMP_INTERNAL_FREE(buffer);
  }

  glb_running_threads = running_threads;

  return running_threads;
} //__kmp_get_load_balance()

// Find symbol from the loaded modules
void *__kmp_lookup_symbol(const char *name, bool next) {
  HANDLE process = GetCurrentProcess();
  DWORD needed;
  HMODULE *modules = nullptr;
  if (!EnumProcessModules(process, modules, 0, &needed))
    return nullptr;
  DWORD num_modules = needed / sizeof(HMODULE);
  modules = (HMODULE *)malloc(num_modules * sizeof(HMODULE));
  if (!EnumProcessModules(process, modules, needed, &needed)) {
    free(modules);
    return nullptr;
  }
  HMODULE curr_module = nullptr;
  if (next) {
    // Current module needs to be skipped if next flag is true
    if (!GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS,
                           (LPCTSTR)&__kmp_lookup_symbol, &curr_module)) {
      free(modules);
      return nullptr;
    }
  }
  void *proc = nullptr;
  for (uint32_t i = 0; i < num_modules; i++) {
    if (next && modules[i] == curr_module)
      continue;
    proc = (void *)GetProcAddress(modules[i], name);
    if (proc)
      break;
  }
  free(modules);
  return proc;
}

// Functions for hidden helper task
void __kmp_hidden_helper_worker_thread_wait() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_do_initialize_hidden_helper_threads() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_threads_initz_wait() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_initz_release() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_main_thread_wait() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_main_thread_release() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_worker_thread_signal() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_threads_deinitz_wait() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}

void __kmp_hidden_helper_threads_deinitz_release() {
  KMP_ASSERT(0 && "Hidden helper task is not supported on Windows");
}
