KeTerminateThread
VOID __stdcall KeTerminateThread(_ETHREAD *Thread){
bool v1;
__int64 v3;
INT64 *v4;
WORK_QUEUE_TYPE v5;
void *v6;
char *v7;
__int64 v8;
char **v9;
_DISPATCHER_HEADER *v10;
struct _KPRCB *CurrentPrcb;
_KWAIT_BLOCK *v12;
_KWAIT_BLOCK *Flink;
signed __int64 *v14;
signed __int64 v15;
signed __int64 v16;
UINT64 v17;
_KWAIT_BLOCK *v18;
unsigned __int8 WaitType;
INT64 WaitKey;
INT64 v21;
INT64 **v22;
_KQUEUE *NotificationQueue;
_LIST_ENTRY *p_WaitListHead;
__int64 v25;
_KPRCB *v26;
int SignalState;
_LIST_ENTRY *Blink;
int v29[8];
struct _IO_WORKITEM LockHandle;
UINT64 SpinCount;
_KPRCB *Prcb;
struct _KPRCB *v33;
v1 = (*((_DWORD *)Thread + 29) & 0x1000) == 0;
memset(&LockHandle, 0, 24);
if( !v1 )
KeBugCheckEx(0x107u, (ULONG_PTR)Thread, 0i64, 0i64, 0i64);
v3 = *((_QWORD *)Thread + 45);
if( v3 )
KeDisableProfiling((_KTHREAD *)Thread, *(_THREAD_PERFORMANCE_DATA **)(v3 + 8));
v4 = (INT64 *)*((_QWORD *)Thread + 68);
*((_BYTE *)Thread + 643) = 22;
KeGetCurrentIrql();
__writecr8(2ui64);
ExAcquireSpinLockExclusiveAtDpcLevel(v4 + 8);
v7 = (char *)Thread + 760;
if( *((_QWORD *)Thread + 95) == *((_QWORD *)Thread + 96) )
{
LockHandle.WorkItem.List.Flink = 0i64;
LockHandle.WorkItem.List.Blink = (_LIST_ENTRY *)KiProcessListLock;
KxAcquireQueuedSpinLock(&LockHandle, KiProcessListLock, v5, v6);
v21 = v4[106];
v22 = (INT64 **)v4[107];
if( *(INT64 **)(v21 + 8) != v4 + 106 || *v22 != v4 + 106 )
LABEL_39:
__fastfail(3u);
*v22 = (INT64 *)v21;
*(_QWORD *)(v21 + 8) = v22;
KeReleaseInStackQueuedSpinLockFromDpcLevel((_KLOCK_QUEUE_HANDLE *)&LockHandle);
}
KiAcquireKobjectLockSafe(v4);
v8 = *(_QWORD *)v7;
v9 = (char **)*((_QWORD *)Thread + 96);
if( *(char **)(*(_QWORD *)v7 + 8i64) != v7 || *v9 != v7 )
goto LABEL_39;
*v9 = (char *)v8;
*(_QWORD *)(v8 + 8) = v9;
_InterlockedAnd((volatile signed __int32 *)v4, 0xFFFFFF7F);
if( *((_QWORD *)Thread + 13) )
KiRemoveThreadFromSchedulingGroup((__int64)Thread);
ExReleaseSpinLockExclusiveFromDpcLevel(v4 + 8);
v10 = (_DISPATCHER_HEADER *)*((_QWORD *)Thread + 29);
if( v10 )
KiActivateWaiterQueueWithNoLocks(Thread, v10, (_LIST_ENTRY *)((char *)Thread + 520));
CurrentPrcb = KeGetCurrentPrcb();
v33 = CurrentPrcb;
KiAcquireKobjectLockSafe(Thread);
v12 = (_KWAIT_BLOCK *)((char *)Thread + 8);
*((_DWORD *)Thread + 1) = 1;
Flink = (_KWAIT_BLOCK *)*((_QWORD *)Thread + 1);
while( Flink != v12 )
{
v18 = Flink;
Flink = (_KWAIT_BLOCK *)Flink->WaitListEntry.Flink;
WaitType = v18->WaitType;
if( WaitType == 1 )
{
WaitKey = v18->WaitKey;
goto LABEL_27;
}
if( WaitType == 2 )
{
v18->BlockState = 5;
NotificationQueue = v18->NotificationQueue;
v18->WaitListEntry.Flink = 0i64;
p_WaitListHead = &NotificationQueue->Header.WaitListHead;
KeGetCurrentIrql();
__writecr8(2ui64);
Prcb = KeGetCurrentPrcb();
v25 = *((_QWORD *)Prcb + 1);
KiAcquireKobjectLockSafe(NotificationQueue);
if( p_WaitListHead->Flink == p_WaitListHead
|| NotificationQueue->CurrentCount >= NotificationQueue->MaximumCount
|| *(_KQUEUE **)(v25 + 232) == NotificationQueue && *(_BYTE *)(v25 + 643) == 15 )
{
v26 = Prcb;
}
else
{
v26 = Prcb;
if( KiWakeQueueWaiter(Prcb, NotificationQueue, (INT64)v18) )
goto LABEL_41;
}
SignalState = NotificationQueue->Header.SignalState;
NotificationQueue->Header.SignalState = SignalState + 1;
Blink = NotificationQueue->EntryListHead.Blink;
if( Blink->Flink != &NotificationQueue->EntryListHead )
goto LABEL_39;
v18->WaitListEntry.Flink = &NotificationQueue->EntryListHead;
v18->WaitListEntry.Blink = Blink;
Blink->Flink = &v18->WaitListEntry;
NotificationQueue->EntryListHead.Blink = &v18->WaitListEntry;
if( !SignalState && p_WaitListHead->Flink != p_WaitListHead )
KiWakeOtherQueueWaiters(v26, NotificationQueue);
LABEL_41:
_InterlockedAnd(&NotificationQueue->Header.Lock, 0xFFFFFF7F);
CurrentPrcb = v33;
}
else
{
WaitKey = 256i64;
LABEL_27:
KiTryUnwaitThread(CurrentPrcb, v18, WaitKey, 0i64);
}
}
*((_QWORD *)Thread + 2) = (char *)Thread + 8;
v12->WaitListEntry.Flink = &v12->WaitListEntry;
_InterlockedAnd((volatile signed __int32 *)Thread, 0xFFFFFF7F);
*((_BYTE *)Thread + 388) = 4;
if( *((_QWORD *)CurrentPrcb + 1441) )
KiProcessThreadWaitList((struct KPRCB *)CurrentPrcb, 1, 0);
v14 = (signed __int64 *)((char *)Thread + 1112);
_m_prefetchw(&PsReaperListHead);
v15 = PsReaperListHead;
do
{
*v14 = v15;
v16 = v15;
v15 = _InterlockedCompareExchange64(&PsReaperListHead, (signed __int64)v14, v15);
}
while( v15 != v16 );
if( v15 )
{
if( PsReaperWorkItem.Parameter
&& _interlockedbittestandreset((volatile signed __int32 *)&PsReaperWorkItem.Parameter, 0) )
{
v17 = 0xFFFFi64;
goto LABEL_19;
}
}
else
{
v17 = 0xFFFFFFFFi64;
LABEL_19:
if( !ExQueueWorkItemEx(&PsReaperWorkItem, HyperCriticalWorkQueue, v17) )
_interlockedbittestandset((volatile signed __int32 *)&PsReaperWorkItem.Parameter, 0);
}
_InterlockedOr(v29, 0);
if( *((_QWORD *)Thread + 8) )
{
LODWORD(SpinCount) = 0;
while( _interlockedbittestandset64((volatile signed __int32 *)Thread + 16, 0i64) )
{
do
KeYieldProcessorEx(&SpinCount);
while( *((_QWORD *)Thread + 8) );
}
KiReleaseThreadLockSafe((INT64)Thread);
}
KiSwapThread(Thread, CurrentPrcb);
}Referenced by:
PspExitThread