ExAllocateHeapSpecialPool
UINT64 __stdcall ExAllocateHeapSpecialPool(UINT64 a1, _XSTATE_CONFIGURATION *NumberOfBytes, _XSTATE_CONFIGURATION *Key){
unsigned int v3;
__int64 v4;
int v6;
unsigned __int8 CurrentIrql;
__int64 v8;
UINT64 v9;
UINT64 v10;
unsigned __int64 v11;
char LowPart;
_XSTATE_CONFIGURATION *v13;
NTSTATUS v14;
POOL_TYPE v15;
__int64 v16;
__int64 v17;
int v18;
int v19;
__int64 v20;
char *v21;
unsigned int v22;
unsigned int v23;
__int64 v24;
volatile signed __int32 *v25;
int v26;
volatile signed __int32 v27;
__int64 v28;
PVOID BugCheckParameter4;
int v31;
__int64 v32;
char *v33;
_KLOCK_QUEUE_HANDLE LockHandle;
unsigned int v35;
v3 = a1;
v4 = (unsigned int)Key;
v6 = a1 & 1;
if( !v6 && (_bittest(&ExpPoolFlags, 0xAu) & ((v3 & 0x200) == 0)) != 0 )
v3 |= 0x200u;
CurrentIrql = KeGetCurrentIrql();
if( CurrentIrql > (unsigned __int8)(2 - (v6 != 0)) )
KeBugCheckEx(0xC1u, (PVOID)CurrentIrql, (PVOID)(int)v3, NumberOfBytes, (PVOID)0x30);
LODWORD(v8) = ExGetHeapFromType(v3, 0x80000000ui64, 1i64);
LODWORD(BugCheckParameter4) = 4;
v9 = RtlpHpSegAlloc((UINT16 *)(v8 + 256), 0x1000u, 4096i64, 4096i64, (UINT64)BugCheckParameter4);
v10 = v9;
if( !v9 )
return 0i64;
LowPart = KUSER_SHARED_DATA.TickCount.LowPart;
memset((VOID *)(v9 + 16), LOBYTE(KUSER_SHARED_DATA.TickCountQuad) | 1u, 0xFF0u);
v13 = (_XSTATE_CONFIGURATION *)((char *)NumberOfBytes - 8);
if( (v3 & 0x40) == 0 )
v13 = NumberOfBytes;
*(_QWORD *)(v10 + 8) = 0i64;
*(_DWORD *)v10 = (_DWORD)v13;
*(_BYTE *)(v10 + 2) = LowPart | 1;
*(_DWORD *)(v10 + 4) = v4;
if( (v3 & 0x40) != 0 )
*(_DWORD *)v10 |= 0x4000u;
v11 = (v10 - (_QWORD)v13 + 4096) & 0xFFFFFFFFFFFFFFF0ui64;
if( (v3 & 0x400) != 0 )
memset((VOID *)((v10 - (_QWORD)v13 + 4096) & 0xFFFFFFFFFFFFFFF0ui64), 0i64, (size_t)v13);
v14 = MiDeterminePoolType(v10);
v15 = NonPagedPool;
LockHandle.LockQueue = 0i64;
v16 = 8i64;
if( v14 != 32 )
v15 = v14;
*(_QWORD *)&LockHandle.OldIrql = 0i64;
if( (_DWORD)v4 == PoolHitTag )
__debugbreak();
v17 = (unsigned int)*(&PerfGlobalGroupMask + 1);
v18 = v15 & 0x20;
if( (v15 & 0x20) != 0 )
{
v21 = (char *)ExpSessionPoolTrackTable;
v19 = ExpSessionPoolTrackTableMask;
v20 = ExpSessionPoolTrackTableSize;
}
else
{
LODWORD(v17) = KeGetPcr()->Prcb.Number;
v19 = PoolTrackTableMask;
v20 = PoolTrackTableSize;
v21 = (char *)*((_QWORD *)&WheapDeferredInternalLogsEventLock + v17 + 372);
}
v32 = v20;
v31 = v19;
v33 = v21;
v22 = v19 & ((40543 * v4) ^ ((unsigned __int64)(40543 * v4) >> 32));
v23 = v22;
v35 = v22;
while( 1 )
{
v24 = 56i64 * v22;
v25 = (volatile signed __int32 *)&v21[v24];
v26 = *(_DWORD *)&v21[v24];
if( v26 == (_DWORD)v4 )
break;
if( v26 )
goto LABEL_35;
if( !v18 )
{
v27 = *(_DWORD *)(v24 + *(&WheapDeferredInternalLogsEventLock + 371));
if( v27 )
{
*v25 = v27;
goto LABEL_27;
}
v23 = v35;
}
if( v22 == v20 - 1 )
{
LABEL_35:
v22 = v19 & (v22 + 1);
if( v22 == v23 )
{
ExpInsertPoolTrackerExpansion((unsigned int)v4, (UINT64)v13, v15);
return v11;
}
}
else if( v18 )
{
_InterlockedCompareExchange(v25, v4, 0);
}
else
{
KeAcquireInStackQueuedSpinLock((PKSPIN_LOCK)&ExpTaggedPoolLock, &LockHandle);
if( !*(_DWORD *)(v24 + *(&WheapDeferredInternalLogsEventLock + 371)) )
{
*(_DWORD *)(v24 + *(&WheapDeferredInternalLogsEventLock + 371)) = v4;
*v25 = v4;
}
KeReleaseInStackQueuedSpinLockFromDpcLevel(&LockHandle);
__writecr8(LockHandle.OldIrql);
v18 = v15 & 0x20;
v19 = v31;
v20 = v32;
v21 = v33;
LABEL_27:
v23 = v35;
}
}
if( (v15 & 1) != 0 )
{
v28 = 10i64;
}
else
{
v28 = 4i64;
v16 = 2i64;
}
_InterlockedIncrement64((volatile signed __int64 *)&v25[v28]);
_InterlockedExchangeAdd64((volatile signed __int64 *)&v25[v16], (unsigned __int64)v13);
return v11;
}Referenced by:
ExAllocateHeapPool