KiProcessExpiredTimerList

VOID __stdcall KiProcessExpiredTimerList(
        _KPRCB *Prcb,
        _KDPC_TRACKER_TABLE *DpcTracker,
        _KTIMER **ExpiredTimers,
        UINT64 TimerCount){
  _ETHREAD *CurrentThread; 
  int v5; 
  unsigned int v8; 
  __int64 v9; 
  volatile signed __int32 *v10; 
  _KDPC *v11; 
  _KDPC_TRACKER_TABLE v12; 
  void(__fastcall *v13)(_KDPC *, void *, void *, void *); 
  __int64 v14; 
  void **DpcWatchdogProfile; 
  void(__fastcall *v16)(_KDPC *, void *, void *, void *); 
  void *v17; 
  _SINGLE_LIST_ENTRY *Next; 
  __int64 v19; 
  _SINGLE_LIST_ENTRY *v20; 
  _SINGLE_LIST_ENTRY *v21; 
  _SINGLE_LIST_ENTRY *v22; 
  _SINGLE_LIST_ENTRY *v23; 
  _SINGLE_LIST_ENTRY *v24; 
  _SINGLE_LIST_ENTRY *v25; 
  size_t v26; 
  UINT64 Flag; 
  void(__fastcall *Data)(_KDPC *, void *, void *, void *); 
  UINT64 SpinCount; 
  unsigned int v30; 
  _ETHREAD *v31; 
  _KTIMER **v32; 
  __int128 v33; 
  __int128 v34; 
  _LARGE_INTEGER TimeStamp[2]; 
  __int128 v36; 

  CurrentThread = Prcb->CurrentThread;
  v30 = TimerCount;
  v5 = *(_BYTE *)(&PerfGlobalGroupMask + 1) & 0x80;
  v31 = CurrentThread;
  Data = 0i64;
  v33 = 0i64;
  v32 = ExpiredTimers;
  v8 = 0;
  v34 = 0i64;
  *(_OWORD *)&TimeStamp[0].anonymous_0.LowPart = 0i64;
  v36 = 0i64;
  HIDWORD(SpinCount) = CurrentThread->Tcb.WaitBlock[3].SpareLong;
  while( 1 )
  {
    v9 = v8++;
    v10 = (volatile signed __int32 *)_InterlockedExchange64((volatile __int64 *)&ExpiredTimers[v9], 0i64);
    if( v10 )
    {
      LODWORD(SpinCount) = 0;
      while( _interlockedbittestandset(v10, 7u) )
      {
        do
          KeYieldProcessorEx(&SpinCount);
        while( (*v10 & 0x80u) != 0 );
      }
      v11 = KiTimerWaitTest(Prcb, (_KTIMER *)v10, (_ULARGE_INTEGER *)DpcTracker + 1);
      if( v11 )
      {
        if( Prcb->DeferredReadyListHead.Next )
          KiProcessThreadWaitList(Prcb, AdjustUnwait, 0i64, 2ui64);
        if( v5 )
          EtwGetKernelTraceTimestamp(TimeStamp, 0x20000080ui64);
        v12 = *DpcTracker;
        Data = v11->DeferredRoutine;
        v13 = Data;
        *DpcTracker = v12 + 1;
        v14 = 2 * ((v12 & 0xF) + 1i64);
        *(_QWORD *)&DpcTracker[2 * v14] = v13;
        DpcTracker[2 * v14 + 2] = KUSER_SHARED_DATA.TickCount.LowPart;
        DpcWatchdogProfile = Prcb->DpcWatchdogProfile;
        Prcb->DpcTimeCount = 0;
        if( DpcWatchdogProfile
          && Prcb->DpcWatchdogProfileCurrentEmptyCapture != DpcWatchdogProfile
          && Prcb->DpcWatchdogCount < (signed int)Prcb->DpcWatchdogProfileCumulativeDpcThreshold )
        {
          v26 = 8 * dword_140C50A78;
          Prcb->DpcWatchdogProfileCurrentEmptyCapture = DpcWatchdogProfile;
          memset(DpcWatchdogProfile, 0i64, v26);
        }
        v16 = Data;
        Prcb->DpcRoutineActive = 1;
        v16(v11, v11->DeferredContext, (void *)(unsigned int)DpcTracker[2], (void *)(unsigned int)DpcTracker[3]);
        v17 = (void *)HIDWORD(SpinCount);
        Prcb->DpcRoutineActive = 0;
        DpcTracker[2 * v14 + 3] = KUSER_SHARED_DATA.TickCount.LowPart;
        if( (_DWORD)v17 != v31->Tcb.WaitBlock[3].SpareLong )
          KeBugCheckEx(0xC7u, (PVOID)5, Data, v17, (PVOID)v31->Tcb.CombinedApcDisable);
        if( v5 )
        {
          LODWORD(Flag) = 4196866;
          EtwTraceTimedEvent(0xF45u, 0x20000080ui64, &Data, 8ui64, Flag, (_ETW_KERNEL_TRACE_TIMESTAMP *)TimeStamp);
        }
      }
    }
    if( v8 >= v30 )
      break;
    ExpiredTimers = v32;
  }
  Next = Prcb->DeferredReadyListHead.Next;
  if( Next )
  {
    Prcb->DeferredReadyListHead.Next = 0i64;
    do
    {
      v19 = BYTE3(Next[46].Next);
      v20 = Next - 27;
      v21 = Next[-1].Next;
      Next = Next->Next;
      v22 = &v21[6 * v19];
      do
      {
        if( BYTE1(v21[2].Next) < 5u )
        {
          v23 = v21[4].Next;
          KiAcquireKobjectLockSafe(v23);
          if( BYTE1(v21[2].Next) == 4 )
          {
            v24 = v21->Next;
            if( v21->Next[1].Next != v21 || (v25 = v21[1].Next, v25->Next != v21) )
              __fastfail(3u);
            v25->Next = v24;
            v24[1].Next = v25;
          }
          _InterlockedAnd((volatile signed __int32 *)v23, 0xFFFFFF7F);
        }
        v21 += 6;
      }
      while( v21 != v22 );
      HIWORD(v20[70].Next) = 1;
      KiReadyThread(Prcb, (_KTHREAD *)v20);
    }
    while( Next );
  }
}

Referenced by:

KiExpireTimerTable
KiRetireDpcList