PspUmsUnInitThread

NTSTATUS __stdcall PspUmsUnInitThread(_ETHREAD *Thread){
  _ETHREAD *CurrentThread; 
  INT64 *Object; 
  INT64 v4; 
  bool v5; 
  NTSTATUS v6; 
  int updated; 
  _ADAPTER_OBJECT *v8; 
  INT64 v10; 

  LODWORD(v10) = 0;
  CurrentThread = Thread;
  if( !Thread )
    CurrentThread = (_ETHREAD *)KeGetCurrentThread();
  if( (CurrentThread->Tcb.gap0[3] & 0x40) != 0 )
  {
    Object = (INT64 *)Thread->Tcb.WaitBlock[3].Object;
    v4 = *Object;
    if( (Object[10] & 4) != 0 )
    {
      v5 = 1;
      v6 = PspRundownUmsThreadForApcDelivery(Thread, &v10, v4, 1);
      if( (Thread->CrossThreadFlags & 0x10000) != 0 )
        v6 = 0;
      if( v6 < 0 || (v10 & 8) == 0 && (v10 & 1) == 0 )
        v5 = (Thread->CrossThreadFlags & 0x10000) != 0;
    }
    else
    {
      KeSetUmsThreadKernelLock(v4, 0i64);
      v5 = 1;
    }
    updated = KeUpdateUmsThreadState(v4, 2i64, v5);
  }
  else
  {
    --Thread->Tcb.SpecialApcDisable;
    updated = PspDisassociateUmsThreadFromPrimary(Thread, 0i64, &v10);
    KiLeaveGuardedRegionUnsafe((__int64)Thread);
  }
  v8 = (_ADAPTER_OBJECT *)*((_QWORD *)Thread->Tcb.WaitBlock[3].Object + 2);
  KeUnInitializeUmsThread((INT64)Thread);
  if( v8 )
    HalPutDmaAdapter(v8);
  if( updated < 0 && (KeGetCurrentThread()->ApcState.Process->Flags & 0x40000008) == 0 )
    PsTerminateProcess((ULONG_PTR)KeGetCurrentThread()->ApcState.Process, (unsigned int)updated);
  return updated;
}

Referenced by:

PspExitThread