KiSelectReadyThread
_KTHREAD *__stdcall KiSelectReadyThread(INT64 LowPriority, _KPRCB *Prcb){
__int64 v2;
unsigned int v4;
UINT8 *ShareRankNonZero;
int v6;
__int64 v7;
char v8;
_ETHREAD *v9;
unsigned int v10;
__int64 v11;
__int64 v12;
int v13;
struct _KPRCB *CurrentPrcb;
unsigned int v16;
__int64 v17;
_QWORD **v18;
_QWORD *v19;
_KHETERO_CPU_POLICY v20;
__int64 v21;
_ETHREAD **v22;
_ETHREAD **v23;
struct _KPRCB *v24;
__int64 v25;
_KSCB *v26;
_KSCB *v27;
int v28;
__int64 v29;
int v30;
__int64 v31;
__int64 v32;
int v33;
unsigned int v34;
UINT64 SpinCount;
_QWORD *v36;
v2 = *((_QWORD *)Prcb + 4233);
v4 = 1 << LowPriority;
ShareRankNonZero = 0i64;
v6 = LowPriority;
v7 = *(_QWORD *)(*((_QWORD *)Prcb + 24) + 80i64);
v8 = *((_BYTE *)Prcb + 35);
v32 = v7;
if( (v8 & 2) != 0 && (v7 & *((_QWORD *)Prcb + 4232)) != 0 && v8 != 7 )
v2 = 0i64;
while( 1 )
{
v9 = 0i64;
if( !KiForceIdleDisabled && (_DWORD)KiForceIdleState == 4 )
return(_KTHREAD *)v9;
v10 = *((_DWORD *)Prcb + 7942);
v33 = -2;
v11 = 0xFFFFFFFFi64;
v34 = -1;
if( v10 >= v4 )
{
_BitScanReverse((unsigned int *)&v11, v10);
v34 = v11;
v10 = 1 << v11;
}
if( v2 )
{
LODWORD(v12) = *(_DWORD *)(v2 + 8);
if( (unsigned int)v12 >= v4 )
{
_BitScanReverse((unsigned int *)&v13, v12);
v33 = v13;
}
else
{
v13 = -2;
}
v11 = v34;
if( v13 > (int)v34 || v13 == v34 && !_bittest((const signed __int32 *)Prcb + 7943, v34) )
{
CurrentPrcb = KeGetCurrentPrcb();
LODWORD(SpinCount) = 0;
while( _interlockedbittestandset64((volatile signed __int32 *)v2, 0i64) )
{
do
{
KeYieldProcessorEx(&SpinCount);
v12 = *(_QWORD *)v2;
}
while( *(_QWORD *)v2 );
v31 = *((_QWORD *)CurrentPrcb + 4247);
if( v31 && *((_BYTE *)CurrentPrcb + 32) <= 1u )
{
LODWORD(v12) = *(_DWORD *)(v31 + 24) + 1;
*(_DWORD *)(v31 + 24) = v12;
}
}
v16 = *(_DWORD *)(v2 + 8);
v17 = v32;
LABEL_18:
ShareRankNonZero = 0i64;
v9 = 0i64;
if( v16 >= v4 && v16 >= v10 )
{
_BitScanReverse((unsigned int *)&v11, v16);
v33 = v11;
v18 = (_QWORD **)(v2 + 16 * ((int)v11 + 1i64));
v16 ^= 1 << v11;
v19 = *v18;
v36 = *v18;
while( 1 )
{
v20 = *((unsigned __int8 *)v19 - 91);
v9 = (_ETHREAD *)(v19 - 27);
if( (unsigned int)v20 >= KHeteroCpuPolicyDynamic )
{
v20 = KiConvertDynamicHeteroPolicy((_KTHREAD *)(v19 - 27), (_KHETERO_CPU_POLICY)v19, Prcb);
v19 = v36;
v17 = v32;
}
v21 = -1i64;
if( v20 )
{
v21 = *(_QWORD *)(*((_QWORD *)Prcb + 24) + 24i64 * (int)v20 + 200);
v19 = v36;
}
if( (v21 & *((_QWORD *)Prcb + 25)) != 0 )
break;
v12 = v21 & *((_QWORD *)Prcb + 4232);
if( (v12 & v17) == 0 )
break;
v19 = (_QWORD *)*v19;
v36 = v19;
if( v19 == v18 )
goto LABEL_18;
}
if( (*((_DWORD *)v9 + 30) & 0x400000) != 0 )
_InterlockedAnd(*((volatile signed __int32 **)v9 + 121), 0xFFFBFFFF);
v22 = (_ETHREAD **)*((_QWORD *)v9 + 27);
v23 = (_ETHREAD **)*((_QWORD *)v9 + 28);
if( v22[1] != (_ETHREAD *)((char *)v9 + 216) || *v23 != (_ETHREAD *)((char *)v9 + 216) )
__fastfail(3u);
*v23 = (_ETHREAD *)v22;
v22[1] = (_ETHREAD *)v23;
if( v23 == v22 )
*(_DWORD *)(v2 + 8) ^= 1 << v33;
--*(_DWORD *)(v2 + 608);
*(_QWORD *)(v2 + 616) -= *((unsigned int *)v9 + 392);
LODWORD(v12) = *((_DWORD *)Prcb + 9);
ShareRankNonZero = 0i64;
*((_DWORD *)v9 + 134) = v12;
}
_InterlockedAnd64((volatile signed __int64 *)v2, 0i64);
v24 = KeGetCurrentPrcb();
if( *((_QWORD *)v24 + 4247) && *((_BYTE *)v24 + 32) <= 1u && !(_DWORD)v12 )
ShareRankNonZero = 0i64;
if( v9 )
{
if( v33 == v34 )
_bittestandset((signed __int32 *)Prcb + 7943, v34);
goto LABEL_37;
}
v11 = v34;
}
}
if( (int)v11 >= v6 )
{
v29 = *((_QWORD *)Prcb + 2 * (int)v11 + 3984);
v9 = (_ETHREAD *)(v29 - 216);
KiRemoveThreadFromReadyQueue((__int64)Prcb, v29, v11);
if( (_DWORD)v11 == v30 )
_bittestandreset((signed __int32 *)Prcb + 7943, v11);
}
if( !v9 )
return(_KTHREAD *)v9;
LABEL_37:
v25 = *((_QWORD *)v9 + 13);
if( !v25 )
return(_KTHREAD *)v9;
v26 = (_KSCB *)(*((unsigned int *)Prcb + 54) + v25);
if( !v26 )
return(_KTHREAD *)v9;
KiGetThreadEffectiveRankNonZero(v9, v26, (_KPRCB *)v11, 1u, ShareRankNonZero);
if( !v28 )
return(_KTHREAD *)v9;
KiAddThreadToScbQueue(Prcb, v27, (_KTHREAD *)v9, 0i64);
ShareRankNonZero = 0i64;
}
}Referenced by:
KiChooseLowestRankedThread
KiGroupSchedulingGenerationEnd
KiGroupSchedulingQuantumEnd
KiQuantumEnd
KiRemoveBoostThread
KiSearchForNewThread
KiSelectNextThread
KiSelectReadyThreadEx
KiSwapThread