27#define POOL_TYPE_GLOBAL 9999
28#define POOL_TYPE_PAGED 1234
65 size_t blockSize = (base << i) +
sizeof(
POOL_HEADER);
107 uintptr_t PageVa = 0;
108 size_t HeaderBlockSize = 0;
109 size_t Iterations = 0;
116 localList.
Next = NULL;
121 if (list == NULL)
break;
136 if (Desc->
BlockSize > header->Metadata.BlockSize) {
138 header->Metadata.FreeListEntry.Next = localList.
Next;
139 localList.
Next = &header->Metadata.FreeListEntry;
145 PageVa = (uintptr_t)header;
146 HeaderBlockSize = header->Metadata.BlockSize;
151 while (Iterations--) {
153 if (entryToPushBack == NULL) {
158 localList.
Next = entryToPushBack->
Next;
160 GlobalPool.FreeListHead.Next = entryToPushBack;
172 if (!PageVa)
return false;
201 for (
size_t offset = 0; (offset + Desc->
BlockSize) <= HeaderBlockSize; offset += Desc->
BlockSize) {
225 size_t NumberOfBytes,
252 size_t RequiredSize = NumberOfBytes +
sizeof(
POOL_HEADER);
271 if (header->Metadata.BlockSize >= RequiredSize) {
273 foundHeader = header;
276 *PtrToPrevNext = list->
Next;
282 PtrToPrevNext = &list->
Next;
293 return (
void*)((uint8_t*)foundHeader +
sizeof(
POOL_HEADER));
308 bool failure =
false;
309 size_t Iterations = 0;
311 for (
size_t i = 0; i < neededPages; i++) {
341 for (
size_t j = 0; j < Iterations; j++) {
358 void* UserAddress = (
void*)((uint8_t*)newHeader +
sizeof(
POOL_HEADER));
360 kmemset(UserAddress, 0, NumberOfBytes);
368 IN size_t NumberOfBytes,
394 size_t ActualSize = NumberOfBytes +
sizeof(
POOL_HEADER);
396 if (!PagedVa)
return NULL;
402 size_t currVa = PagedVa;
403 for (
size_t i = 0; i < NumberOfPages; i++) {
405 if (!tmpPte)
continue;
406 MMPTE TempPte = *tmpPte;
423 return (
void*)((uint8_t*)PagedVa +
sizeof(
POOL_HEADER));
429 IN size_t NumberOfBytes,
471 if (NumberOfBytes == 0) {
493 (
void*)__builtin_return_address(0)
504 (
void*)__builtin_return_address(0)
510 return MiAllocatePagedPool(NumberOfBytes, Tag);
521 if (ActualSize <= currentSlab->BlockSize) {
530 return MiAllocateLargePool(NumberOfBytes, Tag);
540 if (!MiRefillPool(Desc, Index)) {
551 assert((list) != NULL,
"Pool is nullptr even though freecount isn't zero.");
578 void* UserAddress = (
void*)((uint8_t*)header +
sizeof(
POOL_HEADER));
580 kmemset(UserAddress, 0, NumberOfBytes);
656 uintptr_t CurrentVA = (uintptr_t)header;
658 for (
size_t i = 0; i < NumberOfPages; i++) {
660 if (!pte)
goto advance;
674 MMPTE TempPte = *pte;
NORETURN void MeBugCheckEx(IN enum _BUGCHECK_CODES BugCheckCode, IN void *BugCheckParameter1, IN void *BugCheckParameter2, IN void *BugCheckParameter3, IN void *BugCheckParameter4)
struct _SINGLE_LINKED_LIST SINGLE_LINKED_LIST
struct _SINGLE_LINKED_LIST * PSINGLE_LINKED_LIST
void gop_printf(uint32_t color, const char *fmt,...)
FORCEINLINE uint64_t __read_rip(void)
#define CONTAINING_RECORD(ptr, type, member)
PAGE_INDEX MiTranslatePteToPfn(IN PMMPTE pte)
PMMPTE MiGetPtePointer(IN uintptr_t va)
void MiInvalidateTlbForVa(IN void *VirtualAddress)
void MiUnmapPte(IN PMMPTE pte)
FORCEINLINE IRQL MeGetCurrentIrql(void)
FORCEINLINE PPROCESSOR MeGetCurrentProcessor(void)
FORCEINLINE void MiAtomicExchangePte(PMMPTE PtePtr, uint64_t NewPteValue)
#define MAX_POOL_DESCRIPTORS
#define MM_SET_DEMAND_ZERO_PTE(pte, prot_flags, nx)
#define PROT_KERNEL_WRITE
struct _POOL_DESCRIPTOR POOL_DESCRIPTOR
#define MI_PAGED_POOL_BASE
#define PPFN_TO_PHYSICAL_ADDRESS(PPFN)
FORCEINLINE void * kmemset(void *dest, int64_t val, uint64_t len)
struct _POOL_DESCRIPTOR * PPOOL_DESCRIPTOR
#define MI_NONPAGED_POOL_BASE
#define BYTES_TO_PAGES(Bytes)
#define MI_NONPAGED_POOL_END
struct _POOL_HEADER POOL_HEADER
#define MI_PAGED_POOL_END
#define MM_UNSET_DEMAND_ZERO_PTE(pte)
#define INDEX_TO_PPFN(Index)
#define MI_WRITE_PTE(_PtePointer, _Va, _Pa, _Flags)
struct _PFN_ENTRY * PPFN_ENTRY
#define MM_IS_DEMAND_ZERO_PTE(pte)
struct _POOL_HEADER * PPOOL_HEADER
PAGE_INDEX MiRequestPhysicalPage(IN PFN_STATE ListType)
void MiReleasePhysicalPage(IN PAGE_INDEX PfnIndex)
uintptr_t MmNonPagedPoolEnd
uintptr_t MmNonPagedPoolStart
MTSTATUS MiInitializePoolSystem(void)
POOL_DESCRIPTOR GlobalPool
uintptr_t MmPagedPoolStart
void MmFreePool(IN void *buf)
void * MmAllocatePoolWithTag(IN enum _POOL_TYPE PoolType, IN size_t NumberOfBytes, IN uint32_t Tag)
void MsAcquireSpinlock(IN PSPINLOCK lock, IN PIRQL OldIrql)
void MsReleaseSpinlock(IN PSPINLOCK lock, IN IRQL OldIrql)
struct _MMPTE::@172372265215056352375070220246156106027174106113::@200357034104227323320222006243127050212100105247 Hard
union _PFN_ENTRY::@217024126340164016372152071216274230164113211246 Descriptor
struct _PFN_ENTRY::@217024126340164016372152071216274230164113211246::@301110335271023021153236134322146064331241142124 Mapping
volatile uint64_t FreeCount
volatile uint64_t TotalBlocks
SINGLE_LINKED_LIST FreeListHead
SINGLE_LINKED_LIST FreeListEntry
union _POOL_HEADER::@321115223011072362277073135231015025151337071364 Metadata
POOL_DESCRIPTOR LookasidePools[MAX_POOL_DESCRIPTORS]
struct _SINGLE_LINKED_LIST * Next
uintptr_t MiAllocatePoolVa(IN POOL_TYPE PoolType, IN size_t NumberOfBytes)
void MiFreePoolVaContiguous(IN uintptr_t va, IN size_t NumberOfBytes, IN POOL_TYPE PoolType)