- Get rid of the concept and tracking of "mapped pages". The MapCount was never checked anywhere in terms of page accounting -- only the reference count is.

- Fix the issue with the system attempting to map page 0 into hyperspace.

svn path=/trunk/; revision=42226
This commit is contained in:
ReactOS Portable Systems Group 2009-07-26 08:20:29 +00:00
parent 698ff57ea6
commit c417ef7e62
4 changed files with 20 additions and 102 deletions

View file

@ -96,6 +96,9 @@ KiAttachProcess(IN PKTHREAD Thread,
/* Release lock */
KiReleaseApcLockFromDpcLevel(ApcLock);
/* Make sure that we are in the right page directory (ReactOS Mm Hack) */
MiSyncForProcessAttach(Thread, (PEPROCESS)Process);
/* Swap Processes */
KiSwapProcess(Process, SavedApcState->Process);
@ -573,9 +576,6 @@ KeStackAttachProcess(IN PKPROCESS Process,
ASSERT_PROCESS(Process);
ASSERT_IRQL_LESS_OR_EQUAL(DISPATCH_LEVEL);
/* Make sure that we are in the right page directory (ReactOS Mm Hack) */
MiSyncForProcessAttach(Thread, (PEPROCESS)Process);
/* Crash system if DPC is being executed! */
if (KeIsExecutingDpc())
{

View file

@ -37,9 +37,10 @@ MiMapPageInHyperSpace(IN PEPROCESS Process,
PFN_NUMBER Offset;
//
// Never accept page 0
// Never accept page 0 or non-physical pages
//
ASSERT(Page != 0);
ASSERT(MiGetPfnEntry(Page) != NULL);
//
// Build the PTE

View file

@ -38,7 +38,6 @@
#define Type CacheAttribute
#define Zero PrototypePte
#define LockCount u3.e1.PageColor
#define MapCount u2.ShareCount
#define RmapListHead AweReferenceCount
#define SavedSwapEntry u4.EntireFrame
#define Flags u3.e1
@ -264,7 +263,6 @@ MiFindContiguousPages(IN PFN_NUMBER LowestPfn,
Pfn1->Flags.Consumer = MC_NPPOOL;
Pfn1->ReferenceCount = 1;
Pfn1->LockCount = 0;
Pfn1->MapCount = 0;
Pfn1->SavedSwapEntry = 0;
//
@ -452,7 +450,6 @@ MiAllocatePagesForMdl(IN PHYSICAL_ADDRESS LowAddress,
// Make sure it's really free
//
ASSERT(Pfn1->Flags.Type == MM_PHYSICAL_PAGE_FREE);
ASSERT(Pfn1->MapCount == 0);
ASSERT(Pfn1->ReferenceCount == 0);
//
@ -464,7 +461,6 @@ MiAllocatePagesForMdl(IN PHYSICAL_ADDRESS LowAddress,
Pfn1->Flags.EndOfAllocation = 1;
Pfn1->ReferenceCount = 1;
Pfn1->LockCount = 0;
Pfn1->MapCount = 0;
Pfn1->SavedSwapEntry = 0;
//
@ -507,7 +503,6 @@ MiAllocatePagesForMdl(IN PHYSICAL_ADDRESS LowAddress,
//
// Sanity checks
//
ASSERT(Pfn1->MapCount == 0);
ASSERT(Pfn1->ReferenceCount == 0);
//
@ -519,7 +514,6 @@ MiAllocatePagesForMdl(IN PHYSICAL_ADDRESS LowAddress,
Pfn1->Flags.StartOfAllocation = 1;
Pfn1->Flags.EndOfAllocation = 1;
Pfn1->LockCount = 0;
Pfn1->MapCount = 0;
Pfn1->SavedSwapEntry = 0;
//
@ -678,12 +672,11 @@ MmDumpPfnDatabase(VOID)
//
// Pretty-print the page
//
DbgPrint("0x%08p:\t%04s\t%20s\t(%02d.%02d.%02d) [%08p])\n",
DbgPrint("0x%08p:\t%04s\t%20s\t(%02d.%02d) [%08p])\n",
i << PAGE_SHIFT,
State,
Consumer,
Pfn1->ReferenceCount,
Pfn1->MapCount,
Pfn1->LockCount,
Pfn1->RmapListHead);
}
@ -716,8 +709,7 @@ MmInitializePageList(VOID)
RtlZeroMemory(&UsedPage, sizeof(UsedPage));
UsedPage.Flags.Type = MM_PHYSICAL_PAGE_USED;
UsedPage.Flags.Consumer = MC_NPPOOL;
UsedPage.ReferenceCount = 2;
UsedPage.MapCount = 1;
UsedPage.ReferenceCount = 1;
/* Loop the memory descriptors */
for (NextEntry = KeLoaderBlock->MemoryDescriptorListHead.Flink;
@ -812,61 +804,6 @@ MmGetRmapListHeadPage(PFN_TYPE Pfn)
return(ListHead);
}
VOID
NTAPI
MmMarkPageMapped(PFN_TYPE Pfn)
{
KIRQL oldIrql;
PPHYSICAL_PAGE Page;
if (Pfn <= MmHighestPhysicalPage)
{
oldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
Page = MiGetPfnEntry(Pfn);
if (Page)
{
if (Page->Flags.Type == MM_PHYSICAL_PAGE_FREE)
{
DPRINT1("Mapping non-used page\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
Page->MapCount++;
Page->ReferenceCount++;
}
KeReleaseQueuedSpinLock(LockQueuePfnLock, oldIrql);
}
}
VOID
NTAPI
MmMarkPageUnmapped(PFN_TYPE Pfn)
{
KIRQL oldIrql;
PPHYSICAL_PAGE Page;
if (Pfn <= MmHighestPhysicalPage)
{
oldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
Page = MiGetPfnEntry(Pfn);
if (Page)
{
if (Page->Flags.Type == MM_PHYSICAL_PAGE_FREE)
{
DPRINT1("Unmapping non-used page\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
if (Page->MapCount == 0)
{
DPRINT1("Unmapping not mapped page\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
Page->MapCount--;
Page->ReferenceCount--;
}
KeReleaseQueuedSpinLock(LockQueuePfnLock, oldIrql);
}
}
VOID
NTAPI
MmSetSavedSwapEntryPage(PFN_TYPE Pfn, SWAPENTRY SwapEntry)
@ -1000,12 +937,6 @@ MmDereferencePage(PFN_TYPE Pfn)
DPRINT1("Freeing page with rmap entries.\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
if (Page->MapCount != 0)
{
DPRINT1("Freeing mapped page (0x%x count %d)\n",
Pfn << PAGE_SHIFT, Page->MapCount);
KeBugCheck(MEMORY_MANAGEMENT);
}
if (Page->LockCount > 0)
{
DPRINT1("Freeing locked page\n");
@ -1162,11 +1093,6 @@ MmAllocPage(ULONG Consumer, SWAPENTRY SwapEntry)
DPRINT1("Got non-free page from freelist\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
if (PageDescriptor->MapCount != 0)
{
DPRINT1("Got mapped page from freelist\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
if (PageDescriptor->ReferenceCount != 0)
{
DPRINT1("%d\n", PageDescriptor->ReferenceCount);
@ -1176,7 +1102,6 @@ MmAllocPage(ULONG Consumer, SWAPENTRY SwapEntry)
PageDescriptor->Flags.Consumer = Consumer;
PageDescriptor->ReferenceCount = 1;
PageDescriptor->LockCount = 0;
PageDescriptor->MapCount = 0;
PageDescriptor->SavedSwapEntry = SwapEntry;
MmStats.NrSystemPages++;
@ -1189,11 +1114,6 @@ MmAllocPage(ULONG Consumer, SWAPENTRY SwapEntry)
{
MiZeroPage(PfnOffset);
}
if (PageDescriptor->MapCount != 0)
{
DPRINT1("Returning mapped page.\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
return PfnOffset;
}
@ -1247,12 +1167,7 @@ MmZeroPageThreadMain(PVOID Ignored)
Status = MiZeroPage(Pfn);
oldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
if (PageDescriptor->MapCount != 0)
{
DPRINT1("Mapped page on freelist.\n");
KeBugCheck(MEMORY_MANAGEMENT);
}
PageDescriptor->Flags.Zero = 1;
PageDescriptor->Flags.Zero = 1;
PageDescriptor->Flags.Type = MM_PHYSICAL_PAGE_FREE;
if (NT_SUCCESS(Status))
{

View file

@ -465,7 +465,6 @@ MmDeleteVirtualMapping(PEPROCESS Process, PVOID Address, BOOLEAN FreePage,
if (WasValid)
{
Pfn = PTE_TO_PFN(Pte);
MmMarkPageUnmapped(Pfn);
}
else
{
@ -768,10 +767,6 @@ MmCreatePageFileMapping(PEPROCESS Process,
KeBugCheck(MEMORY_MANAGEMENT);
}
Pte = *Pt;
if (PAGE_MASK((Pte)) != 0)
{
MmMarkPageUnmapped(PTE_TO_PFN((Pte)));
}
InterlockedExchangePte(Pt, SwapEntry << 1);
if (Pte != 0)
{
@ -882,16 +877,11 @@ MmCreateVirtualMappingUnsafe(PEPROCESS Process,
oldPdeOffset = PdeOffset;
Pte = *Pt;
MmMarkPageMapped(Pages[i]);
if (PAGE_MASK(Pte) != 0 && !(Pte & PA_PRESENT) && (Pte & 0x800))
{
DPRINT1("Bad PTE %lx\n", Pte);
KeBugCheck(MEMORY_MANAGEMENT);
}
if (PAGE_MASK(Pte) != 0)
{
MmMarkPageUnmapped(PTE_TO_PFN(Pte));
}
InterlockedExchangePte(Pt, PFN_TO_PTE(Pages[i]) | Attributes);
if (Pte != 0)
{
@ -1049,6 +1039,18 @@ MmUpdatePageDir(PEPROCESS Process, PVOID Address, ULONG Size)
{
ULONG StartOffset, EndOffset, Offset;
PULONG Pde;
//
// Check if the process isn't there anymore
// This is probably a bad sign, since it means the caller is setting cr3 to
// 0 or something...
//
if ((PTE_TO_PFN(Process->Pcb.DirectoryTableBase[0]) == 0) && (Process != PsGetCurrentProcess()))
{
DPRINT1("Process: %16s is dead: %p\n", Process->ImageFileName, Process->Pcb.DirectoryTableBase[0]);
ASSERT(FALSE);
return;
}
if (Address < MmSystemRangeStart)
{