KiTimer2Expiration

UINT8 __fastcall KiTimer2Expiration(struct KPRCB *a1, UINT64 a2, CHAR a3, CHAR a4, INT64 a5){
  UINT8 result; 
  __int64 v10; 
  __int64 v11; 
  unsigned __int64 v12; 
  __int64 v13; 
  __int64 v14; 
  __int64 v15; 
  __int64 ***v16; 
  __int64 *v17; 
  _DWORD *v18; 
  char v19; 
  _KTIMER2 *v20; 
  unsigned __int8 Signalling; 
  signed __int32 v22; 
  signed __int32 v23; 
  __int64 **v24; 
  __int64 v25; 
  UINT64 v26; 
  _KTIMER2 *v27; 
  UINT64 v28; 
  signed __int32 v29; 
  char v30[8]; 
  __int64 *v31; 
  __int64 **v32; 
  INT64 v33; 
  __int128 v34; 
  v33 = a5;
  result = KiNextTimer2DueTime;
  v30[0] = 0;
  v34 = 0i64;
  if( a2 < KiNextTimer2DueTime )
    return result;
  v32 = &v31;
  v31 = (__int64 *)&v31;
  KxAcquireSpinLock(&KiTimer2CollectionLock);
  v10 = 0i64;
  v11 = 5i64;
  if( !a4 )
  {
    v10 = 1i64;
    v11 = 2i64;
    if( a3 )
      v11 = 3i64;
  }
  v12 = (unsigned __int64)&KiTimer2Collections[3 * v10];
  do
  {
    v13 = *(_QWORD *)(v12 + 8);
    if( (v13 & 1) != 0 )
    {
      if( v13 == 1 )
        goto LABEL_10;
      v14 = v13 ^ (v12 | 1);
    }
    else
    {
      v14 = *(_QWORD *)(v12 + 8);
    }
    if( v14 )
    {
      v15 = 0i64;
      if( v10 >= 2 )
        v15 = 24i64;
      do
      {
        v16 = (__int64 ***)(v14 - v15);
        if( a2 < (unsigned __int64)v16[6] )
          break;
        KiRemoveTimer2((_KTIMER2 *)(v16 - 3));
        v22 = *((_DWORD *)v16 - 6);
        v23 = _InterlockedCompareExchange((volatile signed __int32 *)v16 - 6, v22 & 0xFFFFF0FF | 0x200, v22);
        if( v22 != v23 )
        {
          do
          {
            v29 = v23;
            v23 = _InterlockedCompareExchange((volatile signed __int32 *)v16 - 6, v23 & 0xFFFFF0FF | 0x200, v23);
          }
          while( v29 != v23 );
        }
        v24 = v32;
        if( *v32 != (__int64 *)&v31 )
          __fastfail(3u);
        v16[1] = v32;
        *v16 = &v31;
        *v24 = (__int64 *)v16;
        v25 = *(_QWORD *)(v12 + 8);
        v32 = (__int64 **)v16;
        if( (v25 & 1) != 0 )
        {
          if( v25 == 1 )
            break;
          v14 = v25 ^ (v12 | 1);
        }
        else
        {
          v14 = v25;
        }
      }
      while( v14 );
    }
LABEL_10:
    ++v10;
    v12 += 24i64;
  }
  while( v10 < v11 );
  KxReleaseSpinLock(&KiTimer2CollectionLock);
  v17 = v31;
  if( v31 == (__int64 *)&v31 )
    goto LABEL_20;
  v18 = (_DWORD *)v33;
  v19 = 0;
  while( 2 )
  {
    v20 = (_KTIMER2 *)(v17 - 3);
    v17 = (__int64 *)*v17;
    KiAcquireKobjectLockSafe(v20);
    Signalling = v20->Header.Signalling;
    if( (Signalling & 2) != 0 )
    {
      if( (v20->TypeFlags & 2) != 0 )
        v19 = 1;
      goto LABEL_16;
    }
    v26 = 0i64;
    v27 = v20;
    if( (Signalling & 8) != 0 )
    {
      if( KiInsertTimer2((__int64)v20, 0, v30) )
      {
        v28 = 0i64;
        v27 = v20;
        v26 = 1i64;
        goto LABEL_40;
      }
      if( (v20->TypeFlags & 2) != 0 )
        v19 = 1;
LABEL_16:
      KiExpireTimer2((__int64)v20, (__int64)a1, a2, v18);
    }
    else
    {
      v28 = 4i64;
LABEL_40:
      KiUpdateTimer2Flags(v27, v26, v28);
    }
    if( v17 != (__int64 *)&v31 )
      continue;
    break;
  }
  if( v19 )
    KiCheckAndRearmForceIdle();
LABEL_20:
  if( *((_QWORD *)a1 + 1441) )
    KiProcessThreadWaitList(a1, 1, 0);
  result = KiShouldActivateHRTimerClock(*(UINT64 *)&KUSER_SHARED_DATA.InterruptTime.LowPart, DueTime);
  if( result )
    KiSendClockInterruptToClockOwner();
  return result;
}

Referenced by:

KiRetireDpcList
KiTimerExpirationDpc