NtAssociateWaitCompletionPacket
NTSTATUS __stdcall NtAssociateWaitCompletionPacket(
PVOID WaitCompletionPacketHandle,
PVOID IoCompletionHandle,
PVOID TargetObjectHandle,
PVOID KeyContext,
PVOID ApcContext,
INT64 IoStatus,
UINT64 IoStatusInformation,
UINT8 *AlreadySignaled){
KPROCESSOR_MODE v10;
NTSTATUS result;
int v12;
int v13;
PVOID v14;
KMUTANT *WaitObject;
UINT64 *v16;
unsigned __int8 CurrentIrql;
_QWORD *v18;
PVOID v19;
UINT8 v20;
_LIST_ENTRY *Blink;
_LIST_ENTRY *v22;
UINT8 v23;
__int64 v24;
__int64 v25;
unsigned __int64 v26;
_KQUEUE *v27;
UINT8 v28;
int SignalState;
_LIST_ENTRY *v30;
_LIST_ENTRY *v31;
volatile unsigned int CurrentCount;
PVOID v33;
PVOID Object;
PVOID v35;
PVOID v36;
UINT64 SpinCount;
_QWORD *v38;
_KPRCB *Prcb;
__int64 v40;
v10 = *((_BYTE *)KeGetCurrentThread() + 562);
Object = 0i64;
result = ObReferenceObjectByHandle(
WaitCompletionPacketHandle,
1u,
IopWaitCompletionPacketObjectType,
v10,
&Object,
0i64);
if( result >= 0 )
{
v35 = 0i64;
v12 = ObReferenceObjectByHandle(IoCompletionHandle, 2u, IoCompletionObjectType, v10, &v35, 0i64);
if( v12 < 0 )
{
ObfDereferenceObjectWithTag(Object, 0x746C6644ui64);
return v12;
}
v36 = 0i64;
v13 = ObReferenceObjectByHandle(TargetObjectHandle, 0x100000u, 0i64, v10, &v36, 0i64);
HIDWORD(SpinCount) = v13;
if( v13 < 0 )
{
ObfDereferenceObjectWithTag(Object, 0x746C6644ui64);
v33 = v35;
}
else
{
v14 = v36;
WaitObject = (KMUTANT *)ObpGetWaitObject((INT64)v36 - 48);
if( WaitObject != (KMUTANT *)&ObpDefaultObject
&& WaitObject
&& (((WaitObject->Header.Type & 0x7F) - 2) & 0xFD) != 0 )
{
v16 = (UINT64 *)((char *)Object + 96);
CurrentIrql = KeGetCurrentIrql();
__writecr8(2ui64);
if( _interlockedbittestandset64((volatile signed __int32 *)v16, 0i64) )
KxWaitForSpinLockAndAcquire(v16);
if( !*((_BYTE *)Object + 104) )
{
*((_BYTE *)Object + 104) = 1;
v18 = Object;
*((_QWORD *)Object + 6) = KeyContext;
v18[7] = ApcContext;
*((_DWORD *)v18 + 18) = IoStatus;
v18[8] = IoStatusInformation;
v18[10] = v36;
v19 = v35;
v18[11] = v35;
*((_WORD *)v18 + 8) = 1026;
v18[3] = v19;
v18[4] = WaitObject;
v20 = KeGetCurrentIrql();
__writecr8(2ui64);
LODWORD(SpinCount) = 0;
while( _interlockedbittestandset(&WaitObject->Header.Lock, 7u) )
{
do
KeYieldProcessorEx(&SpinCount);
while( (WaitObject->Header.LockNV & 0x80u) != 0 );
}
if( WaitObject->Header.SignalState <= 0 )
{
Blink = WaitObject->Header.WaitListHead.Blink;
if( Blink->Flink == &WaitObject->Header.WaitListHead )
{
v22 = (_LIST_ENTRY *)Object;
*(_QWORD *)Object = &WaitObject->Header.WaitListHead;
v22->Blink = Blink;
Blink->Flink = v22;
WaitObject->Header.WaitListHead.Blink = v22;
_InterlockedAnd(&WaitObject->Header.Lock, 0xFFFFFF7F);
__writecr8(v20);
v23 = 0;
goto LABEL_14;
}
LABEL_34:
__fastfail(3u);
}
KiWaitSatisfyOther(WaitObject);
*((_BYTE *)v18 + 17) = 5;
*(_QWORD *)Object = v25;
v38 = (char *)v35 + 8;
KeGetCurrentIrql();
__writecr8(v26);
Prcb = KeGetCurrentPrcb();
v40 = *((_QWORD *)Prcb + 1);
v27 = (_KQUEUE *)v35;
KiAcquireKobjectLockSafe(v35);
if( (_QWORD *)*v38 == v38
|| (CurrentCount = v27->CurrentCount, v27 = (_KQUEUE *)v35, CurrentCount >= *((_DWORD *)v35 + 11))
|| (v27 = (_KQUEUE *)v35, *(PVOID *)(v40 + 232) == v35) && *(_BYTE *)(v40 + 643) == 15 )
{
v28 = 0;
}
else
{
v28 = KiWakeQueueWaiter(Prcb, (_KQUEUE *)v35, (INT64)Object);
}
if( !v28 )
{
SignalState = v27->Header.SignalState;
v27->Header.SignalState = SignalState + 1;
v30 = v27->EntryListHead.Blink;
if( v30->Flink != &v27->EntryListHead )
goto LABEL_34;
v31 = (_LIST_ENTRY *)Object;
*(_QWORD *)Object = &v27->EntryListHead;
v31->Blink = v30;
v30->Flink = v31;
v27->EntryListHead.Blink = v31;
if( !SignalState && (_QWORD *)*v38 != v38 )
KiWakeOtherQueueWaiters(Prcb, v27);
}
_InterlockedAnd(&v27->Header.Lock, 0xFFFFFF7F);
_InterlockedAnd(&WaitObject->Header.Lock, 0xFFFFFF7F);
KiExitDispatcher(KeGetCurrentPrcb(), 0i64, AdjustUnwait, 0i64, v20);
v23 = 1;
LABEL_14:
_InterlockedAnd64((volatile signed __int64 *)v16, 0i64);
__writecr8(CurrentIrql);
if( AlreadySignaled )
{
if( v10 )
{
v24 = (__int64)AlreadySignaled;
if( (unsigned __int64)AlreadySignaled >= 0x7FFFFFFF0000i64 )
v24 = 0x7FFFFFFF0000i64;
*(_BYTE *)v24 = *(_BYTE *)v24;
}
*AlreadySignaled = v23;
}
return v13;
}
KxReleaseSpinLock(v16);
__writecr8(CurrentIrql);
v13 = -1073741585;
v14 = v36;
}
else
{
v13 = -1073741583;
}
ObfDereferenceObjectWithTag(v35, 0x746C6644ui64);
ObfDereferenceObjectWithTag(v14, 0x746C6644ui64);
v33 = Object;
}
ObfDereferenceObjectWithTag(v33, 0x746C6644ui64);
return v13;
}
return result;
}Referenced by:
No references.