KiSuspendThread

UINT8 __stdcall KiSuspendThread(INT64 Thread, _KPRCB *Prcb){
  UINT8 v2; 
  $C2BDD6D5375F7E2805A991361E69A246 *v5; 
  char v6; 
  char v8; 
  __int32 v9; 
  _KWAIT_BLOCK *v10; 
  volatile unsigned __int8 *p_BlockState; 
  _KWAIT_BLOCK *v12; 
  VOID *v13; 
  volatile unsigned __int8 **v14; 
  __int64 v15; 
  _KWAIT_STATUS_REGISTER v16; 
  _ULARGE_INTEGER v17; 
  _ULARGE_INTEGER v18; 
  UINT64 SpinCount; 
  UINT64 v20; 

  v2 = 0;
  LODWORD(SpinCount) = 0;
  while( _interlockedbittestandset64((volatile signed __int32 *)(Thread + 64), 0i64) )
  {
    do
      KeYieldProcessorEx(&SpinCount);
    while( *(_QWORD *)(Thread + 64) );
  }
  if( (*(_DWORD *)(Thread + 116) & 0x4000) != 0 )
  {
    if( *(_DWORD *)(Thread + 740) )
    {
      *(_DWORD *)(Thread + 740) = 0;
      v5 = ($C2BDD6D5375F7E2805A991361E69A246 *)(Thread + 648);
      v6 = 0;
      if( !*(_BYTE *)(Thread + 730) )
      {
        *(_BYTE *)(Thread + 730) = 1;
        v6 = 1;
        KiInsertQueueApc((_KAPC *)(Thread + 648));
      }
      if( KiDisableLightWeightSuspend
        || *(_BYTE *)(Thread + 388) != 5
        || (*(_BYTE *)(Thread + 112) & 7) != 1
        || (v8 = *(_BYTE *)(Thread + 3), (v8 & 0x40) != 0)
        || v8 < 0
        || *(_DWORD *)(Thread + 484)
        || *(_BYTE *)(Thread + 390)
        || *(_BYTE *)(Thread + 192)
        || *(_BYTE *)(Thread + 586)
        || *(_BYTE *)(*(_QWORD *)(Thread + 208) + 17i64) != 5 && *(_BYTE *)(*(_QWORD *)(Thread + 208) + 16i64) != 1 )
      {
        if( v6 )
          KiSignalThreadForApc(Prcb, &v5->SchedulerApc, 2u);
      }
      else
      {
        v9 = (*(_DWORD *)(Thread + 116) ^ (*(char *)(Thread + 391) << 18)) & 0x40000;
        *(_BYTE *)(Thread + 112) = 3;
        *(_DWORD *)(Thread + 116) ^= v9;
        *(_BYTE *)(Thread + 193) = 1;
        KiReleaseThreadLockSafe(Thread);
        v10 = *(_KWAIT_BLOCK **)(Thread + 208);
        p_BlockState = &v10->BlockState;
        v12 = &v10[*(unsigned __int8 *)(Thread + 587)];
        do
        {
          if( *p_BlockState < 5u )
          {
            v13 = *(VOID **)(p_BlockState + 15);
            KiAcquireKobjectLockSafe(v13);
            if( *p_BlockState == 4 )
            {
              v14 = *(volatile unsigned __int8 ***)(p_BlockState - 9);
              v15 = *(_QWORD *)(p_BlockState - 17);
              if( *(volatile unsigned __int8 **)(v15 + 8) != p_BlockState - 17 || *v14 != p_BlockState - 17 )
                __fastfail(3u);
              *v14 = (volatile unsigned __int8 *)v15;
              *(_QWORD *)(v15 + 8) = v14;
            }
            _InterlockedAnd((volatile signed __int32 *)v13, 0xFFFFFF7F);
            *p_BlockState = 6;
          }
          p_BlockState += 48;
        }
        while( p_BlockState - 17 != (volatile unsigned __int8 *)v12 );
        if( (*(_DWORD *)(Thread + 116) & 0x200) != 0 )
        {
          v17 = *(_ULARGE_INTEGER *)&KUSER_SHARED_DATA.InterruptTime.LowPart;
          if( KiCancelTimer((_KTIMER *)(Thread + 256), 1u) )
          {
            v18 = *(_ULARGE_INTEGER *)(Thread + 280);
            if( v18.QuadPart <= v17.QuadPart )
            {
              *(_QWORD *)(Thread + 280) = 0i64;
            }
            else if( (*(_BYTE *)(Thread + 257) & 1) != 0 )
            {
              *(_QWORD *)(Thread + 280) += *(_QWORD *)&KUSER_SHARED_DATA.SystemTime.LowPart - v17.QuadPart;
            }
            else
            {
              *(_QWORD *)(Thread + 280) = v17.QuadPart - v18.QuadPart;
            }
          }
          else
          {
            *(_QWORD *)(Thread + 280) = 0i64;
            *(_BYTE *)(Thread + 481) = 4;
            *(_QWORD *)(Thread + 264) = Thread + 464;
            *(_QWORD *)(Thread + 272) = Thread + 464;
          }
        }
        if( (*(_DWORD *)(Thread + 120) & 0x4000) != 0
          && !_interlockedbittestandset((volatile signed __int32 *)(Thread + 120), 0x14u) )
        {
          KiDecrementProcessStackCount(*(_KPROCESS **)(Thread + 184));
        }
        LODWORD(v20) = 0;
        while( _interlockedbittestandset64((volatile signed __int32 *)(Thread + 64), 0i64) )
        {
          do
            KeYieldProcessorEx(&v20);
          while( *(_QWORD *)(Thread + 64) );
        }
        v16.Flags = *(_BYTE *)(Thread + 112) & 0xFC;
        *(_DWORD *)(Thread + 116) = *(_DWORD *)(Thread + 116) & 0xFFFDFDFF | ((*(_DWORD *)(Thread + 116) & 0x200) << 8);
        v16.Flags |= 4u;
        *(_KWAIT_STATUS_REGISTER *)(Thread + 112) = v16;
        if( (v16.Flags & 0x20) != 0 )
          KiSignalThread(Prcb, (_ETHREAD *)Thread, 256i64, 0i64);
      }
    }
    v2 = 1;
  }
  KiReleaseThreadLockSafe(Thread);
  return v2;
}

Referenced by:

KeSuspendThread
KiAdjustThreadTimer
KiFreezeSingleThread