NtInitiatePowerAction
NTSTATUS __stdcall NtInitiatePowerAction(
POWER_ACTION SystemAction,
_SYSTEM_POWER_STATE LightestSystemState,
UINT64 Flags,
UINT8 Asynchronous){
_ETHREAD *CurrentThread;
int v5;
UINT64 v6;
unsigned int v8;
char PreviousMode;
VOID **PoolWithTag;
UINT64 v13;
__int64 v14;
_QWORD *v15;
INT64 SubstitutionPolicy;
_LARGE_INTEGER Timeout;
POWER_ACTION_POLICY ActionPolicy;
_POP_ACTION_TRIGGER Trigger;
*(_OWORD *)&Trigger.Wait = 0i64;
CurrentThread = (_ETHREAD *)KeGetCurrentThread();
v5 = 0;
v6 = 0i64;
Timeout.QuadPart = -1500000000i64;
v8 = Flags;
PreviousMode = CurrentThread->Tcb.PreviousMode;
if( PreviousMode )
{
if( SystemAction == PowerActionWarmEject )
return -1073741811;
if( !SeSinglePrivilegeCheck(*(_QWORD *)&SeShutdownPrivilege, CurrentThread->Tcb.PreviousMode) )
return -1073741727;
}
if( LightestSystemState > PowerSystemMaximum
|| SystemAction > PowerActionWarmEject
|| (v8 & 0x10000000) != 0
|| SystemAction == PowerActionSleep && LightestSystemState >= PowerSystemHibernate
|| (v8 & 0xCFFFFC0) != 0 )
{
return -1073741811;
}
if( (unsigned int)(SystemAction - 4) > 2 && PsIsCurrentThreadInServerSilo() )
return -1073741637;
ActionPolicy.EventCode = 0;
ActionPolicy.Action = SystemAction;
ActionPolicy.Flags = v8;
Trigger.Flags = 128;
*(_OWORD *)&Trigger.Wait = 0i64;
if( !PreviousMode && SystemAction == PowerActionShutdownOff && (v8 & 0x3000000) != 0 )
{
Trigger.Type = PolicySystemInitiatedShutdown;
}
else
{
Trigger.Type = PolicyInitiatePowerActionAPI;
PopDiagTracePolicyInitiatePowerActionApiCall(
(_RTL_RUN_ONCE *)(unsigned int)SystemAction,
LightestSystemState,
Flags,
(WCHAR *)Asynchronous,
SubstitutionPolicy);
}
if( !Asynchronous )
{
PoolWithTag = ExAllocatePoolWithTag(0x200ui64, 0x38ui64, 1466122576i64);
v6 = (UINT64)PoolWithTag;
if( !PoolWithTag )
return -1073741670;
*(_OWORD *)PoolWithTag = 0i64;
*((_OWORD *)PoolWithTag + 1) = 0i64;
*((_OWORD *)PoolWithTag + 2) = 0i64;
PoolWithTag[6] = &Trigger;
KeInitializeEvent((INT64)PoolWithTag, 0, 0);
Trigger.Flags |= 0x20u;
Trigger.Wait = (_POP_TRIGGER_WAIT *)v6;
}
if( (unsigned int)(SystemAction - 4) <= 2 && (BYTE8(xmmword_140C502C8) & 8) == 0 )
{
PopAcquireRwLockExclusive((_POP_RW_LOCK *)((char *)&stru_140C23628 + 6312));
BYTE8(xmmword_140C502C8) |= 8u;
LOBYTE(xmmword_140C50488) = SleepReason;
PopBsdHandleRequest(8i64);
PopReleaseRwLock((_POP_RW_LOCK *)((char *)&stru_140C23628 + 6312));
}
PopAcquirePolicyLock();
PopExecutePowerAction(&Trigger, 0i64, &ActionPolicy, LightestSystemState, SubstituteLightestOverallDownwardBounded);
PopReleasePolicyLock();
if( v6 )
{
v13 = v6 + 32;
if( !*(_QWORD *)(v6 + 32) )
goto LABEL_23;
v5 = KeWaitForSingleObject(v6, 5, 0, 1, (INT64)&Timeout);
if( v5 == 258 && (byte_140C23261 & 3) != 0 )
v5 = KeWaitForSingleObject(v6, 5, 0, 1, 0i64);
PopAcquirePolicyLock();
v14 = *(_QWORD *)v13;
if( *(_QWORD *)(*(_QWORD *)v13 + 8i64) != v13 || (v15 = *(_QWORD **)(v6 + 40), *v15 != v13) )
__fastfail(3u);
*v15 = v14;
*(_QWORD *)(v14 + 8) = v15;
PopReleasePolicyLock();
if( v5 >= 0 )
{
LABEL_23:
v5 = *(_DWORD *)(v6 + 24);
if( v5 >= 0 )
v5 = 0;
}
ExFreePoolWithTag((PVOID)v6, 0);
}
return v5;
}Referenced by:
IopWarmEjectDevice
PopCheckPowerSourceAfterRtcWakeTimerWorker