PpmIdleSelectStates
VOID __stdcall PpmIdleSelectStates(
_KPRCB *Prcb,
UINT64 *EnterTime,
UINT64 *InterruptTime,
UINT8 *DeepSleepEnabled,
UINT64 *SelectedProcessorState,
UINT64 *SelectedPlatformState,
UINT8 *SynchronizedTransition){
_PPM_IDLE_STATES *IdleStates;
__int64 v9;
_PPM_IDLE_STATES *v10;
unsigned __int64 TimeUpdateLock;
unsigned __int64 BaselineInterruptTimeQpc;
__int64 v13;
UINT64 PerformanceCounter;
__int64 v15;
unsigned __int64 v16;
UINT64 *v17;
unsigned __int64 v18;
_KPRCB *v19;
UINT64 *v20;
int OverrideIndex;
unsigned __int8 v22;
UINT64 v23;
unsigned __int8 ClockOwner;
_PPM_IDLE_STATES *v25;
_PPM_IDLE_STATES *v26;
unsigned __int64 v27;
unsigned __int8 PlatformIdle;
int v29;
unsigned __int64 v30;
__int16 v31;
bool v32;
unsigned __int64 v33;
_KPRCB *v34;
unsigned int v35;
unsigned int InterruptRate;
unsigned int i;
unsigned int v38;
unsigned __int8 v39;
unsigned int v40;
__int64(__fastcall *v41)(_QWORD, __int64);
__int64 v42;
unsigned int v43;
int v44;
UINT8 v45;
char v46;
__int64 v47;
__int64 v48;
unsigned int v49;
__int64 v50;
__int64 v51;
unsigned __int64 v52;
UINT64 v53;
UINT8 v54;
UINT64 v55;
unsigned __int8 v56;
int v57;
int v58;
unsigned __int64 v59;
unsigned __int64 v60;
unsigned int v61;
unsigned int v62;
unsigned int j;
unsigned int v64;
_PPM_IDLE_STATES *v65;
__int64 v66;
__int64 v67;
char *v68;
unsigned int v69;
__int64 v70;
bool v71;
int v72;
UINT8 *v73;
int VetoPresent;
unsigned int(__fastcall *IdleAvailabilityCheck)(void *, unsigned int);
unsigned int(__fastcall *v76)(_QWORD, _QWORD, __int64);
struct _KPRCB *CurrentPrcb;
_KNODE *ParentNode;
unsigned int v79;
unsigned int NextNode;
__int64 v81;
char v82;
__int64 *v83;
__int64 v84;
__int64 v85;
__int64 v86;
__int64 v87;
unsigned __int64 v88;
__int64 v89;
__int64 v90;
unsigned __int64 v91;
char v92;
__int64 *v93;
__int64 v94;
__int64 v95;
__int64 v96;
__int64 v97;
UINT64 v98;
__int64 v99;
__int64 v100;
UINT64 v101;
unsigned __int64 v102;
signed __int64 v103;
_DWORD *v104;
int v105;
__int64 v106;
unsigned int v107;
__int64 v108;
__int64 v109;
__int64 v110;
_KPRCB *v111;
UINT8 v112;
int v113;
UINT64 v114;
UINT64 v115;
UINT64 v116;
UINT64 v117;
unsigned int(__fastcall *v118)(_QWORD, _QWORD, _QWORD);
__int64 v119;
int v120;
_DWORD *v121;
_DWORD *v122;
_LIST_ENTRY *p_VetoListHead;
_LIST_ENTRY *Flink;
__int64 v125;
UINT64 *NextDueTime;
_KEXPECTED_WAKE_REASON *ExpectedWakeReason;
UINT8 v128;
UINT8 v129;
char v130;
UINT64 ProcessorState;
int v132;
int v133;
_KPRCB *Prcba;
UINT64 *v135;
int v136;
int v137;
unsigned int v138;
int v139;
int v140;
int v141;
UINT64 Flags;
unsigned int *v143;
UINT64 RemainingLatency;
unsigned __int64 v145;
__int64 v146;
_DWORD *v147;
UINT64 MaximumIdleDuration;
_KEXPECTED_WAKE_REASON v149[2];
_KEXPECTED_WAKE_REASON v150[2];
UINT64 *v151;
_PPM_IDLE_STATES *v152;
bool *v153;
_KEXPECTED_WAKE_REASON v154[2];
__int64 v155;
UINT64 LookupIndex;
__int64 v157;
_PROC_IDLE_ACCOUNTING *IdleAccounting;
UINT64 *v159;
UINT64 *v160;
UINT8 *v161;
UINT8 *v162;
UINT16 *v163[2];
__int64 v164;
UINT16 *v165[2];
__int64 v166;
__int64 v167[22];
__int64 v168[22];
_KAFFINITY_EX Result;
bool *v170;
v159 = SelectedProcessorState;
v160 = SelectedPlatformState;
v162 = SynchronizedTransition;
v151 = InterruptTime;
v135 = EnterTime;
Prcba = Prcb;
v153 = v170;
v161 = DeepSleepEnabled;
memset(&Result, 0i64, sizeof(Result));
IdleStates = Prcb->PowerState.IdleStates;
v9 = 0i64;
IdleAccounting = Prcb->PowerState.IdleAccounting;
v146 = PpmPlatformStates;
v10 = Prcb->PowerState.IdleStates;
v152 = IdleStates;
LODWORD(RemainingLatency) = PopFxSystemLatencyHint;
v128 = 0;
BYTE4(ProcessorState) = 1;
LOBYTE(v139) = 0;
v130 = 0;
v155 = 0i64;
LODWORD(ProcessorState) = 0;
v147 = 0i64;
v138 = 0;
v143 = 0i64;
v133 = 0;
v132 = 0;
MaximumIdleDuration = 0i64;
*(_QWORD *)v154 = 0i64;
LODWORD(Flags) = 0;
while( 1 )
{
TimeUpdateLock = KUSER_SHARED_DATA.TimeUpdateLock;
if( (KUSER_SHARED_DATA.TimeUpdateLock & 1) == 0 )
{
BaselineInterruptTimeQpc = KUSER_SHARED_DATA.BaselineInterruptTimeQpc;
v13 = *(_QWORD *)&KUSER_SHARED_DATA.InterruptTime.LowPart;
PerformanceCounter = KeQueryPerformanceCounter(0i64);
if( KUSER_SHARED_DATA.TimeUpdateLock == TimeUpdateLock )
break;
}
_mm_pause();
}
v15 = (__int64)v152;
v16 = PerformanceCounter;
v17 = v135;
if( PerformanceCounter > BaselineInterruptTimeQpc )
{
v157 = 0i64;
v18 = -1i64 - BaselineInterruptTimeQpc + PerformanceCounter;
if( KUSER_SHARED_DATA.QpcInterruptTimeIncrementShift )
v18 <<= KUSER_SHARED_DATA.QpcInterruptTimeIncrementShift;
v9 = (v18 * (unsigned __int128)KUSER_SHARED_DATA.QpcInterruptTimeIncrement) >> 64;
v157 = v9;
}
v19 = Prcba;
v20 = v151;
*v151 = v9 + v13;
v10->PrepareInfo.Constraints.TotalTime = v16;
v10->PrepareInfo.Constraints.IdleTime = v19->PowerState.IdleTimeTotal + v19->PowerState.PerfFeedback.StallTime;
v10->PrepareInfo.Constraints.Parked = v19->PowerState.Parked;
v10->PrepareInfo.Constraints.PromotePercent = v19->PowerState.IdlePolicy.PromotePercent;
v10->PrepareInfo.Constraints.DemotePercent = v19->PowerState.IdlePolicy.DemotePercent;
v10->PrepareInfo.Constraints.Interruptible = 1;
if( v19->ClockOwner
&& (CurrentPrcb = KeGetCurrentPrcb(),
LODWORD(LookupIndex) = 0,
ParentNode = CurrentPrcb->ParentNode,
v79 = ParentNode->Affinity.Reserved[0],
(ParentNode->DeepIdleSet & ~(1i64 << CurrentPrcb->GroupIndex)) == (ParentNode->Affinity.Mask & ~(1i64 << (KiProcessorIndexToNumberMappingTable[CurrentPrcb->Number] & 0x3F)))) )
{
while( 1 )
{
NextNode = MmGetNextNode(v79, &LookupIndex);
OverrideIndex = -1;
if( NextNode == -1 )
break;
if( *(_QWORD *)(*(_QWORD *)(v81 + 8i64 * NextNode) + 64i64) != *(_QWORD *)(*(_QWORD *)(v81 + 8i64 * NextNode)
+ 136i64) )
goto LABEL_9;
}
v10->PrepareInfo.Constraints.PlatformIdle = 1;
v10->ReasonFlags |= 0x80u;
}
else
{
LABEL_9:
v10->PrepareInfo.Constraints.PlatformIdle = 0;
OverrideIndex = -1;
}
if( v10->IdleOverride )
{
v10->ReasonFlags |= 0x100u;
OverrideIndex = v10->OverrideIndex;
}
v10->PrepareInfo.Constraints.OverrideState = OverrideIndex;
if( PpmIdleRespectIdleStateMax )
{
v22 = *(_BYTE *)(2736i64 * *(&stru_140C23628 + 441) + *(&stru_140C00F40 + 365) + 198);
v10->PrepareInfo.Constraints.IdleStateMax = v22;
if( v22 )
v10->ReasonFlags |= 0x4000u;
}
else
{
v10->PrepareInfo.Constraints.IdleStateMax = 0;
}
*v17 = v16;
*(_QWORD *)(v15 + 240) = 1310721i64;
memset((VOID *)(v15 + 248), 0i64, 0xA0u);
v23 = *v20;
ClockOwner = v19->ClockOwner;
v25 = v19->PowerState.IdleStates;
v145 = v23;
if( !ClockOwner && KiSerializeTimerExpiration )
{
v135 = 0i64;
_m_prefetchw((char *)&stru_140CF2E80 + 5032);
v102 = *(&stru_140CF2E80 + 629);
if( *(&stru_140CF2E80 + 2516) )
{
while( 1 )
{
v103 = _InterlockedCompareExchange64(
(_QWORD *)&stru_140CF2E80 + 629,
v102 ^ (unsigned __int16)(v102 ^ (v102 - 1)),
v102);
if( v102 == v103 )
break;
v102 = v103;
_mm_pause();
if( !(_WORD)v103 )
goto LABEL_172;
}
v135 = (UINT64 *)(v102 >> 16);
}
LABEL_172:
v26 = v19->PowerState.IdleStates;
ClockOwner = v19->ClockOwner;
}
else
{
v135 = 0i64;
v26 = v25;
}
v164 = 0i64;
*(_OWORD *)v163 = 0i64;
memset(v167, 0i64, 0xA8u);
v27 = -1i64;
PlatformIdle = v26->PrepareInfo.Constraints.PlatformIdle;
v29 = -(ClockOwner != 0);
v30 = KiClockTimerNextTickTime;
v31 = v29 & 8;
*(_QWORD *)v149 = 0i64;
v32 = Prcba->ClockOwner == 0;
v136 = 2;
if( v32 )
{
LOBYTE(NextDueTime) = 0;
KiGetNextTimerExpirationDueTime(Prcba, 0, v23, 0, NextDueTime, v149);
if( v30 <= *(_QWORD *)v149 )
v30 = *(_QWORD *)v149;
}
else if( PlatformIdle && !(_BYTE)KiDynamicTickDisableReason && KiClockState == ClockStatePeriodic )
{
LOBYTE(NextDueTime) = 0;
KiGetNextTimerExpirationDueTime(Prcba, 1u, v23, 0, NextDueTime, v149);
if( v23 + (unsigned int)KiLastRequestedTimeIncrement < *(_QWORD *)v149 )
v30 = *(_QWORD *)v149;
else
v136 = 2;
}
if( v30 == -1i64 )
{
v33 = -1i64;
}
else
{
v33 = 0i64;
if( v30 > v23 )
v33 = v30 - v23;
}
v34 = Prcba;
v35 = 0;
InterruptRate = Prcba->InterruptRate;
for( i = InterruptRate; i; i >>= 4 )
v35 += KeMaximumIncrement;
if( InterruptRate )
{
v38 = (unsigned int)KeMaximumIncrement / (InterruptRate + 1);
if( !v38 )
v38 = 1;
v27 = v38;
}
if( v33 <= v27 )
{
v27 = v33;
}
else
{
v31 |= 1u;
if( v33 >= v35 )
v33 = v35;
}
if( PpmIdleDurationExpirationTimeout )
{
if( Prcba->ClockOwner )
{
LODWORD(v167[0]) = 1310721;
v82 = 0;
memset((char *)v167 + 4, 0i64, 0xA4u);
if( KeNumberNodes )
{
v83 = KeNodeBlock;
v84 = (unsigned __int16)KeNumberNodes;
do
{
v85 = *v83;
v86 = *(unsigned __int16 *)(*v83 + 144);
v87 = *(_QWORD *)(*v83 + 72);
if( LOWORD(v167[0]) <= (unsigned __int16)v86 )
LOWORD(v167[0]) = v86 + 1;
v167[v86 + 1] |= v87;
if( *(_QWORD *)(v85 + 72) )
v82 = 1;
++v83;
--v84;
}
while( v84 );
if( v82 )
{
v163[1] = (UINT16 *)v167[1];
v88 = 0i64;
v163[0] = (UINT16 *)v167;
while( 1 )
{
v140 = 0;
if( KiEnumerateNextProcessorNumber((INT64)&v140, v163) < 0 )
break;
v89 = (unsigned int)KiProcessorNumberToIndexMappingTable[64 * (unsigned __int16)v140 + BYTE2(v140)];
if( (unsigned int)v89 >= (unsigned int)KeQueryActiveProcessorCountEx(0xFFFFu) )
{
v90 = 0i64;
}
else
{
_mm_lfence();
v90 = (__int64)*(&KiProcessorBlock + v89);
}
v91 = *(_QWORD *)(v90 + 32808);
if( v91 > v88 && v91 != -1i64 )
v88 = v91;
}
v15 = (__int64)v152;
if( v88 && v33 + v145 > v88 )
{
v31 |= 0x2000u;
v33 = v88 > v145 ? (unsigned int)(v88 - v145) : 1i64;
if( v33 < v27 )
v27 = v33;
}
v34 = Prcba;
}
}
}
}
if( v27 < (unsigned __int64)v135 )
{
v27 = (unsigned __int64)v135;
v33 = (unsigned __int64)v135;
v31 |= 0x1000u;
}
v25->ReasonFlags |= v31;
v39 = v136;
v25->PrepareInfo.Constraints.MaxIdleDuration = v33;
v40 = -1;
v25->PrepareInfo.Constraints.ExpectedWakeReason = v39;
v25->PrepareInfo.Constraints.ExpectedIdleDuration = v27;
v41 = *(__int64(__fastcall **)(_QWORD, __int64))(v15 + 432);
LODWORD(v135) = -1;
if( v41 )
{
v40 = v41(*(_QWORD *)(v15 + 488), v15 + 496);
LODWORD(v135) = v40;
}
if( v34->PowerState.IdlePolicy.ForceLightIdle )
{
v40 = 0;
LODWORD(v135) = 0;
}
v42 = v146;
if( v146 )
{
PoCopyDeepIdleMask((_KAFFINITY_EX *)(v15 + 576));
KeAddProcessorAffinityEx((UINT16 *)(v15 + 576), v34->Number);
v104 = *(_DWORD **)(v15 + 752);
v145 = *(_QWORD *)(v42 + 48);
v105 = *(_DWORD *)v42;
v147 = v104;
memset(v104, 0i64, 4 * v105 + 8);
v43 = ProcessorState;
v106 = 0i64;
if( *(_DWORD *)(v15 + 776) )
{
v107 = 0;
while( 1 )
{
v108 = *(_QWORD *)(v15 + 784);
v109 = v107;
if( PpmIdleVetoBias || !*(_BYTE *)(v108 + 24 * v106 + 1) )
{
LODWORD(v117) = -2;
}
else
{
v110 = *(unsigned int *)(v108 + 24 * v106 + 4);
v111 = Prcba;
if( PpmDripsStateIndex == -1
|| (unsigned int)v110 < PpmDripsStateIndex
|| !PpmCheckPreConditionsForDeepSleep(Prcba) )
{
v113 = BYTE4(ProcessorState);
if( v128 == 1 )
v113 = 1;
v112 = 0;
}
else
{
v112 = 1;
v113 = BYTE4(ProcessorState);
if( !v128 )
v113 = 1;
}
v128 = v112;
HIDWORD(ProcessorState) = v113;
if( (_BYTE)v113 )
{
BYTE4(ProcessorState) = 0;
PpmEstimateIdleDuration(v111, v112, v112, *v151, 0i64, &MaximumIdleDuration, v154, &Flags);
}
v114 = MaximumIdleDuration;
v115 = (unsigned int)RemainingLatency;
LODWORD(ProcessorState) = -1;
LODWORD(ExpectedWakeReason) = v110;
LODWORD(NextDueTime) = v110;
*(_DWORD *)(v15 + 796) = 0;
v116 = PpmIdleCheckCoordinatedStateEligibility(
v111,
v40,
v115,
v114,
(UINT64)NextDueTime,
(UINT64)ExpectedWakeReason,
&ProcessorState,
(_PPM_COORDINATED_SELECTION *)(v15 + 792));
v43 = ProcessorState;
v117 = v116;
if( !*(_BYTE *)(v146 + 12) && !v116 )
{
v118 = *(unsigned int(__fastcall **)(_QWORD, _QWORD, _QWORD))(v146 + 16);
if( v118 )
v117 = v118(*(_QWORD *)(v15 + 488), (unsigned int)ProcessorState, (unsigned int)v110);
}
PpmIdleUpdateSelectionStatistics(v117, (_PPM_SELECTION_STATISTICS *)(1008 * v110 + v145 + 72));
v119 = v146 + 384 * v110;
if( v117 != 0xFFFFFFFF )
v155 = *(_QWORD *)(v119 + 64);
if( !v117 )
{
v122 = v147;
v72 = -1;
*v153 = 1;
*v122 = v110;
if( *(_BYTE *)(v119 + 121) )
v72 = v110;
if( KeSubtractAffinityEx((WORD *)(v15 + 240), (INT8 *)(v119 + 128), (INT8 *)&Result) )
PpmUnlockProcessors((_KAFFINITY_EX *)(v15 + 240), &Result);
v34 = Prcba;
v45 = v128;
goto LABEL_92;
}
if( v117 == 2147483651 )
{
v130 = 1;
}
else
{
v120 = (unsigned __int8)v139;
if( v117 == 2147483656 )
v120 = 1;
v139 = v120;
}
PpmIdleRollbackCoordinatedSelection((_PPM_COORDINATED_SELECTION *)(v15 + 792), 0i64);
}
v121 = v147;
v107 = v109 + 1;
v106 = (unsigned int)(v106 + 1);
v138 = v109 + 1;
v147[v109 + 2] = v117;
if( (unsigned int)v106 >= *(_DWORD *)(v15 + 776) )
break;
v40 = (unsigned int)v135;
}
v34 = Prcba;
v138 = v107;
}
else
{
v121 = v147;
}
*(_DWORD *)(v15 + 796) = 0;
*v121 = -1;
PpmUnlockProcessors((_KAFFINITY_EX *)(v15 + 240), (_KAFFINITY_EX *)(v15 + 240));
}
else
{
v43 = ProcessorState;
}
v44 = *(_DWORD *)(v15 + 32);
v45 = 0;
v143 = *(unsigned int **)(v15 + 744);
v46 = 1;
memset(v143, 0i64, 4 * v44 + 8);
v47 = 0i64;
v155 = *(_QWORD *)(v15 + 40);
HIDWORD(ProcessorState) = 0;
if( !*(_DWORD *)(v15 + 760) )
goto LABEL_91;
v48 = 2147483658i64;
v49 = 0x80000000;
v50 = 0x100000000i64;
while( 1 )
{
v51 = *(_QWORD *)(v15 + 768);
v52 = (unsigned int)v47;
v145 = (unsigned int)v47;
v43 = *(_DWORD *)(v51 + 24 * v47 + 4);
LODWORD(ProcessorState) = v43;
if( !v146 && v43 == *(_DWORD *)(v15 + 32) - 1 && *(_BYTE *)(v15 + 540) && PpmCheckPreConditionsForDeepSleep(v34) )
{
v129 = 1;
if( !v45 )
v46 = 1;
}
else
{
if( v45 == 1 )
v46 = 1;
v129 = 0;
}
if( v46 )
{
LOBYTE(Prcba) = 0;
*(_OWORD *)v165 = 0i64;
v53 = *v151;
v166 = 0i64;
memset(v168, 0i64, 0xA8u);
v54 = v129;
v55 = -1i64;
v56 = v34->PowerState.IdleStates->PrepareInfo.Constraints.PlatformIdle;
v57 = 0;
if( v34->ClockOwner )
v57 = 8;
v132 = v57;
if( v129 )
v132 = v57 | 4;
v58 = 2;
v32 = v34->ClockOwner == 0;
v59 = KiClockTimerNextTickTime;
v137 = 2;
*(_QWORD *)v150 = 0i64;
if( v32 )
{
LOBYTE(NextDueTime) = 0;
KiGetNextTimerExpirationDueTime(v34, 0, v53, v129, NextDueTime, v150);
v54 = v129;
if( v59 <= *(_QWORD *)v150 )
v59 = *(_QWORD *)v150;
}
else
{
if( !v56 || (_BYTE)KiDynamicTickDisableReason || KiClockState )
goto LABEL_60;
LOBYTE(NextDueTime) = 0;
KiGetNextTimerExpirationDueTime(v34, 1u, v53, v129, NextDueTime, v150);
v54 = v129;
if( v53 + (unsigned int)KiLastRequestedTimeIncrement >= *(_QWORD *)v150 )
{
v58 = 2;
goto LABEL_60;
}
v59 = *(_QWORD *)v150;
}
v58 = v137;
LABEL_60:
if( v59 == -1i64 )
{
v60 = -1i64;
}
else
{
v60 = 0i64;
if( v59 > v53 )
v60 = v59 - v53;
}
v61 = v34->InterruptRate;
v62 = v61;
LODWORD(Flags) = v58;
for( j = 0; v62; v62 >>= 4 )
j += KeMaximumIncrement;
if( !v54 && v61 )
{
v64 = (unsigned int)KeMaximumIncrement / (v61 + 1);
if( !v64 )
v64 = 1;
v55 = v64;
}
if( v60 <= v55 )
{
v55 = v60;
}
else
{
v132 |= 1u;
if( v60 >= j )
v60 = j;
}
if( PpmIdleDurationExpirationTimeout )
{
if( v34->ClockOwner )
{
LODWORD(v168[0]) = 1310721;
v92 = 0;
memset((char *)v168 + 4, 0i64, 0xA4u);
if( KeNumberNodes )
{
v93 = KeNodeBlock;
v94 = (unsigned __int16)KeNumberNodes;
do
{
v95 = *v93;
v96 = *(unsigned __int16 *)(*v93 + 144);
v97 = *(_QWORD *)(*v93 + 72);
if( LOWORD(v168[0]) <= (unsigned __int16)v96 )
LOWORD(v168[0]) = v96 + 1;
v168[v96 + 1] |= v97;
if( *(_QWORD *)(v95 + 72) )
v92 = 1;
++v93;
--v94;
}
while( v94 );
if( v92 )
{
v165[1] = (UINT16 *)v168[1];
v98 = 0i64;
v165[0] = (UINT16 *)v168;
while( 1 )
{
v141 = 0;
if( KiEnumerateNextProcessorNumber((INT64)&v141, v165) < 0 )
break;
v99 = (unsigned int)KiProcessorNumberToIndexMappingTable[64 * (unsigned __int16)v141 + BYTE2(v141)];
if( (unsigned int)v99 >= (unsigned int)KeQueryActiveProcessorCountEx(0xFFFFu) )
{
v100 = 0i64;
}
else
{
_mm_lfence();
v100 = (__int64)*(&KiProcessorBlock + v99);
}
v101 = *(_QWORD *)(v100 + 32808);
if( v101 > v98 && v101 != -1i64 )
v98 = v101;
}
v15 = (__int64)v152;
if( v98 && v60 + v53 > v98 )
{
v132 |= 0x2000u;
v60 = v98 > v53 ? (unsigned int)(v98 - v53) : 1i64;
if( v60 < v55 )
v55 = v60;
}
LODWORD(v47) = HIDWORD(ProcessorState);
}
}
}
}
v43 = ProcessorState;
v49 = 0x80000000;
*(_QWORD *)v154 = v60;
v50 = 0x100000000i64;
v52 = v145;
v48 = 2147483658i64;
MaximumIdleDuration = v55;
v46 = (char)Prcba;
}
if( !v43 )
{
v67 = 0i64;
goto LABEL_83;
}
v65 = v34->PowerState.IdleStates;
if( v65->Type == 3 && PpmIdleVetoBias )
{
v67 = 4294967294i64;
goto LABEL_83;
}
v66 = v43;
if( v65->State[v66].NoCState )
{
v67 = v48;
goto LABEL_83;
}
if( v43 > (unsigned int)v135 && (_DWORD)v135 != -1 )
{
v67 = 2147483656i64;
goto LABEL_83;
}
if( !v65->State[v66].Interruptible && v65->PrepareInfo.Constraints.Interruptible )
{
v67 = 2147483655i64;
goto LABEL_83;
}
VetoPresent = v65->State[v66].VetoAccounting.VetoPresent;
if( VetoPresent )
{
if( VetoPresent >= 0 )
{
if( v65->State[v66].VetoAccounting.PreallocatedVetoList )
{
p_VetoListHead = &v65->State[v66].VetoAccounting.VetoListHead;
Flink = p_VetoListHead->Flink;
v32 = p_VetoListHead->Flink == p_VetoListHead;
VetoPresent = v49;
if( !v32 )
VetoPresent = (int)Flink[1].Flink;
}
else
{
VetoPresent = v49;
}
}
else
{
VetoPresent = -2147483635;
}
}
v43 = ProcessorState;
if( VetoPresent )
{
v67 = v50 | (unsigned int)VetoPresent;
}
else
{
if( v65->State[v66].Latency > (unsigned int)RemainingLatency )
{
v43 = ProcessorState;
v67 = 2147483650i64;
goto LABEL_83;
}
if( v65->State[v66].BreakEvenDuration > MaximumIdleDuration )
{
v43 = ProcessorState;
v67 = 2147483651i64;
goto LABEL_83;
}
IdleAvailabilityCheck = v65->IdleAvailabilityCheck;
v67 = IdleAvailabilityCheck ? IdleAvailabilityCheck(v65->PrepareInfo.Context, ProcessorState) : 0i64;
}
if( !v67 )
{
v76 = *(unsigned int(__fastcall **)(_QWORD, _QWORD, __int64))(v15 + 440);
if( v76 )
v67 = v76(*(_QWORD *)(v15 + 488), v43, 0xFFFFFFFFi64);
}
LABEL_83:
v68 = (char *)IdleAccounting + 1000 * v43;
if( !v67 )
{
v69 = 0;
LABEL_85:
++*(_QWORD *)&v68[8 * v69 + 80];
goto LABEL_86;
}
if( (v67 & 0x80000000) == 0 )
{
if( (v67 & 0x100000000i64) != 0 )
{
v125 = *((_QWORD *)v68 + 25);
v69 = 2;
if( v125 )
++*(_QWORD *)(((unsigned __int64)(((unsigned int)v67 & 0x7FFFFFFF) - 1) << 6) + *(_QWORD *)(v125 + 32) + 24);
}
else
{
v69 = 1;
}
goto LABEL_85;
}
if( (unsigned int)v67 <= 0x8000000C )
{
v69 = v67 - 2147483646;
goto LABEL_85;
}
LABEL_86:
if( !v67 )
break;
if( v67 == 2147483651i64 )
{
v130 = 1;
}
else if( v67 == 2147483656i64 )
{
LOBYTE(v139) = 1;
}
v47 = (unsigned int)(v47 + 1);
v45 = v129;
v49 = 0x80000000;
HIDWORD(ProcessorState) = v47;
v50 = 0x100000000i64;
v48 = 2147483658i64;
v143[v52 + 2] = v67;
if( (unsigned int)v47 >= *(_DWORD *)(v15 + 760) )
goto LABEL_91;
}
v70 = 248i64 * v43;
*v143 = v43;
v133 = v47;
v71 = !*(_BYTE *)(v70 + v15 + 1058) || v146 && (!*(_BYTE *)(v70 + v15 + 1061) || v43);
v45 = v129;
*v153 = v71;
LABEL_91:
v72 = -1;
LABEL_92:
if( *v153 )
PpmIdleSetSynchronizationState((_PPM_IDLE_SYNCHRONIZATION_STATE *)&v34->PowerState.Synchronization, 1u);
*(_WORD *)(v15 + 48) |= v132;
v73 = v162;
*(_BYTE *)(v15 + 7) = v139;
*(_BYTE *)(v15 + 6) = v130;
*(_QWORD *)(v15 + 520) = *(_QWORD *)v154;
*(_QWORD *)(v15 + 512) = MaximumIdleDuration;
*(_BYTE *)(v15 + 541) = Flags;
*(_DWORD *)v159 = v43;
*(_DWORD *)v160 = v72;
*v161 = v45;
*(_QWORD *)v73 = v155;
}Referenced by:
PoIdle