Track valid physical memory pages using a PFN bitmap
All checks were successful
Builds / ExectOS (i686, debug) (push) Successful in 28s
Builds / ExectOS (amd64, debug) (push) Successful in 29s
Builds / ExectOS (amd64, release) (push) Successful in 47s
Builds / ExectOS (i686, release) (push) Successful in 44s

This commit is contained in:
2026-03-17 00:05:33 +01:00
parent 3d7fe25471
commit 876923e107
7 changed files with 228 additions and 2 deletions

View File

@@ -423,6 +423,13 @@ MM::Pfn::GetPfnEntry(IN PFN_NUMBER Pfn)
return NULLPTR;
}
/* Make sure this page has a PFN entry set */
if(PfnBitMap.Buffer && !RTL::BitMap::TestBit(&PfnBitMap, Pfn))
{
/* The requested page number is not set in the bitmap, return NULLPTR */
return NULLPTR;
}
/* Get the memory layout */
MemoryLayout = MM::Manager::GetMemoryLayout();
@@ -445,6 +452,60 @@ MM::Pfn::IncrementAvailablePages(VOID)
AvailablePages++;
}
/**
* Initializes the PFN bitmap to track available physical memory.
*
* @return This routine does not return any value.
*
* @since XT 1.0
*/
XTAPI
VOID
MM::Pfn::InitializePfnBitmap(VOID)
{
PPHYSICAL_MEMORY_DESCRIPTOR PhysicalMemoryBlock;
XTSTATUS Status;
PVOID BitMap;
ULONG Index;
/* Retrieve the global physical memory descriptor block */
PhysicalMemoryBlock = MM::Manager::GetPhysicalMemoryBlock();
if(!PhysicalMemoryBlock)
{
/* Physical memory layout unavailable, kernel panic */
KE::Crash::Panic(0x7D, NumberOfPhysicalPages, LowestPhysicalPage, HighestPhysicalPage, 0x100);
}
/* Calculate the required bitmap size and allocate memory */
Status = MM::Allocator::AllocatePool(NonPagedPool,
(((HighestPhysicalPage + 1) + 31) / 32) * 4,
(PVOID *)&BitMap,
SIGNATURE32('M', 'M', 'g', 'r'));
if(Status != STATUS_SUCCESS || !BitMap)
{
/* Memory allocation failed, kernel panic */
DebugPrint(L"Insufficient physical pages! Install additional memory\n");
KE::Crash::Panic(0x7D, NumberOfPhysicalPages, LowestPhysicalPage, HighestPhysicalPage, 0x101);
}
/* Initialize the PFN bitmap structure and clear all bits by default */
RTL::BitMap::InitializeBitMap(&PfnBitMap, (PULONG_PTR)BitMap, (ULONG)HighestPhysicalPage + 1);
RTL::BitMap::ClearAllBits(&PfnBitMap);
/* Iterate through all contiguous physical memory runs to populate the availability map */
for(Index = 0; Index < PhysicalMemoryBlock->NumberOfRuns; Index++)
{
/* Ensure the current memory run contains at least one valid page frame */
if((&PhysicalMemoryBlock->Run[Index])->PageCount)
{
/* Set the corresponding bits to mark these physical pages as available for allocation */
RtlSetBits(&PfnBitMap,
(ULONG)(&PhysicalMemoryBlock->Run[Index])->BasePage,
(ULONG)(&PhysicalMemoryBlock->Run[Index])->PageCount);
}
}
}
/**
* Links a physical page to the appropriate free lists.
*