KiSuspendThread

UINT8 __stdcall KiSuspendThread(_ETHREAD *Thread, _KPRCB *Prcb){
  UINT8 v2; 
  _KAPC *v5; 
  char v6; 
  char v8; 
  int v9; 
  __int64 v10; 
  __int64 v11; 
  __int64 v12; 
  void *v13; 
  _QWORD *v14; 
  __int64 v15; 
  char v16; 
  unsigned __int64 v17; 
  unsigned __int64 v18; 
  UINT64 SpinCount; 
  UINT64 v20; 
  v2 = 0;
  LODWORD(SpinCount) = 0;
  while( _interlockedbittestandset64((volatile signed __int32 *)Thread + 16, 0i64) )
  {
    do
      KeYieldProcessorEx(&SpinCount);
    while( *((_QWORD *)Thread + 8) );
  }
  if( (*((_DWORD *)Thread + 29) & 0x4000) != 0 )
  {
    if( *((_DWORD *)Thread + 185) )
    {
      *((_DWORD *)Thread + 185) = 0;
      v5 = (_KAPC *)((char *)Thread + 648);
      v6 = 0;
      if( !*((_BYTE *)Thread + 730) )
      {
        *((_BYTE *)Thread + 730) = 1;
        v6 = 1;
        KiInsertQueueApc((_KAPC *)((char *)Thread + 648));
      }
      if( KiDisableLightWeightSuspend
        || *((_BYTE *)Thread + 388) != 5
        || (*((_BYTE *)Thread + 112) & 7) != 1
        || (v8 = *((_BYTE *)Thread + 3), (v8 & 0x40) != 0)
        || v8 < 0
        || *((_DWORD *)Thread + 121)
        || *((_BYTE *)Thread + 390)
        || *((_BYTE *)Thread + 192)
        || *((_BYTE *)Thread + 586)
        || *(_BYTE *)(*((_QWORD *)Thread + 26) + 17i64) != 5 && *(_BYTE *)(*((_QWORD *)Thread + 26) + 16i64) != 1 )
      {
        if( v6 )
          KiSignalThreadForApc(Prcb, v5, 2u);
      }
      else
      {
        v9 = (*((_DWORD *)Thread + 29) ^ (*((char *)Thread + 391) << 18)) & 0x40000;
        *((_BYTE *)Thread + 112) = 3;
        *((_DWORD *)Thread + 29) ^= v9;
        *((_BYTE *)Thread + 193) = 1;
        KiReleaseThreadLockSafe((INT64)Thread);
        v10 = *((_QWORD *)Thread + 26);
        v11 = v10 + 17;
        v12 = v10 + 48i64 * *((unsigned __int8 *)Thread + 587);
        do
        {
          if( *(_BYTE *)v11 < 5u )
          {
            v13 = *(void **)(v11 + 15);
            KiAcquireKobjectLockSafe(v13);
            if( *(_BYTE *)v11 == 4 )
            {
              v14 = *(_QWORD **)(v11 - 9);
              v15 = *(_QWORD *)(v11 - 17);
              if( *(_QWORD *)(v15 + 8) != v11 - 17 || *v14 != v11 - 17 )
                __fastfail(3u);
              *v14 = v15;
              *(_QWORD *)(v15 + 8) = v14;
            }
            _InterlockedAnd((volatile signed __int32 *)v13, 0xFFFFFF7F);
            *(_BYTE *)v11 = 6;
          }
          v11 += 48i64;
        }
        while( v11 - 17 != v12 );
        if( (*((_DWORD *)Thread + 29) & 0x200) != 0 )
        {
          v17 = *(_QWORD *)&KUSER_SHARED_DATA.InterruptTime.LowPart;
          if( KiCancelTimer((_KTIMER *)((char *)Thread + 256), 1u) )
          {
            v18 = *((_QWORD *)Thread + 35);
            if( v18 <= v17 )
            {
              *((_QWORD *)Thread + 35) = 0i64;
            }
            else if( (*((_BYTE *)Thread + 257) & 1) != 0 )
            {
              *((_QWORD *)Thread + 35) += *(_QWORD *)&KUSER_SHARED_DATA.SystemTime.LowPart - v17;
            }
            else
            {
              *((_QWORD *)Thread + 35) = v17 - v18;
            }
          }
          else
          {
            *((_QWORD *)Thread + 35) = 0i64;
            *((_BYTE *)Thread + 481) = 4;
            *((_QWORD *)Thread + 33) = (char *)Thread + 464;
            *((_QWORD *)Thread + 34) = (char *)Thread + 464;
          }
        }
        if( (*((_DWORD *)Thread + 30) & 0x4000) != 0
          && !_interlockedbittestandset((volatile signed __int32 *)Thread + 30, 0x14u) )
        {
          KiDecrementProcessStackCount(*((_KPROCESS **)Thread + 23));
        }
        LODWORD(v20) = 0;
        while( _interlockedbittestandset64((volatile signed __int32 *)Thread + 16, 0i64) )
        {
          do
            KeYieldProcessorEx(&v20);
          while( *((_QWORD *)Thread + 8) );
        }
        v16 = *((_BYTE *)Thread + 112) & 0xFC;
        *((_DWORD *)Thread + 29) = *((_DWORD *)Thread + 29) & 0xFFFDFDFF | ((*((_DWORD *)Thread + 29) & 0x200) << 8);
        v16 |= 4u;
        *((_BYTE *)Thread + 112) = v16;
        if( (v16 & 0x20) != 0 )
          KiSignalThread(Prcb, Thread, 256i64, 0i64);
      }
    }
    v2 = 1;
  }
  KiReleaseThreadLockSafe((INT64)Thread);
  return v2;
}

Referenced by:

KeSuspendThread
KiAdjustThreadTimer
KiFreezeSingleThread