[NTOS]: Switch to using an ARM3, much more correct MmZeroPageThread. Stub support for discarding sections and listening to the Power Manager Idle Timer.

[NTOS]: Use a synchronization (auto-reset) instead of notification event for the zero page thread, this way we don't have to reset it manually and query its state. Instead, a boolean MmZeroingPageThreadActive is checked instead.
[NTOS]: Once we switch to colored lists, major improvements can be done for speed.

svn path=/trunk/; revision=48922
This commit is contained in:
Sir Richard 2010-09-28 16:47:25 +00:00
parent 6ef328578c
commit 05d3392da9
9 changed files with 115 additions and 86 deletions

View file

@ -1951,5 +1951,5 @@ Phase1Initialization(IN PVOID Context)
Phase1InitializationDiscard(Context);
/* Jump into zero page thread */
MmZeroPageThreadMain(NULL);
MmZeroPageThread();
}

View file

@ -1164,10 +1164,10 @@ MmGetContinuousPages(
BOOLEAN ZeroPages
);
NTSTATUS
VOID
NTAPI
MmZeroPageThreadMain(
PVOID Context
MmZeroPageThread(
VOID
);
/* hypermap.c *****************************************************************/

View file

@ -145,8 +145,6 @@ MiComputeNonPagedPoolVa(IN ULONG FreePages)
}
}
extern KEVENT ZeroPageThreadEvent;
NTSTATUS
NTAPI
MiInitMachineDependent(IN PLOADER_PARAMETER_BLOCK LoaderBlock)
@ -496,10 +494,7 @@ MiInitMachineDependent(IN PLOADER_PARAMETER_BLOCK LoaderBlock)
/* Initialize the color tables */
MiInitializeColorTables();
/* ReactOS Stuff */
KeInitializeEvent(&ZeroPageThreadEvent, NotificationEvent, TRUE);
/* Build the PFN Database */
MiInitializePfnDatabase(LoaderBlock);
MmInitializeBalancer(MmAvailablePages, 0);

View file

@ -439,6 +439,8 @@ extern PMMPDE MiHighestUserPde;
extern PFN_NUMBER MmSystemPageDirectory[PD_COUNT];
extern PMMPTE MmSharedUserDataPte;
extern LIST_ENTRY MmProcessList;
extern BOOLEAN MmZeroingPageThreadActive;
extern KEVENT MmZeroingPageEvent;
#define MI_PFN_TO_PFNENTRY(x) (&MmPfnDatabase[1][x])
#define MI_PFNENTRY_TO_PFN(x) (x - MmPfnDatabase[1])

View file

@ -1811,7 +1811,11 @@ MmArmInitSystem(IN ULONG Phase,
/* Initialize the Loader Lock */
KeInitializeMutant(&MmSystemLoadLock, FALSE);
/* Set the zero page event */
KeInitializeEvent(&MmZeroingPageEvent, SynchronizationEvent, FALSE);
MmZeroingPageThreadActive = FALSE;
//
// Count physical pages on the system
//

View file

@ -397,8 +397,6 @@ MiRemoveZeroPage(IN ULONG Color)
return PageIndex;
}
extern KEVENT ZeroPageThreadEvent;
VOID
NTAPI
MiInsertPageInFreeList(IN PFN_NUMBER PageFrameIndex)
@ -507,10 +505,11 @@ MiInsertPageInFreeList(IN PFN_NUMBER PageFrameIndex)
#endif
/* Notify zero page thread if enough pages are on the free list now */
if ((MmFreePageListHead.Total > 8) && !(KeReadStateEvent(&ZeroPageThreadEvent)))
if ((ListHead->Total >= 8) && !(MmZeroingPageThreadActive))
{
/* This is ReactOS-specific */
KeSetEvent(&ZeroPageThreadEvent, IO_NO_INCREMENT, FALSE);
/* Set the event */
MmZeroingPageThreadActive = TRUE;
KeSetEvent(&MmZeroingPageEvent, IO_NO_INCREMENT, FALSE);
}
}

View file

@ -0,0 +1,98 @@
/*
* PROJECT: ReactOS Kernel
* LICENSE: BSD - See COPYING.ARM in the top level directory
* FILE: ntoskrnl/mm/ARM3/zeropage.c
* PURPOSE: ARM Memory Manager Zero Page Thread Support
* PROGRAMMERS: ReactOS Portable Systems Group
*/
/* INCLUDES *******************************************************************/
#include <ntoskrnl.h>
#define NDEBUG
#include <debug.h>
#line 15 "ARM³::ZEROPAGE"
#define MODULE_INVOLVED_IN_ARM3
#include "../ARM3/miarm.h"
/* GLOBALS ********************************************************************/
BOOLEAN MmZeroingPageThreadActive;
KEVENT MmZeroingPageEvent;
/* PRIVATE FUNCTIONS **********************************************************/
VOID
NTAPI
MmZeroPageThread(VOID)
{
PKTHREAD Thread = KeGetCurrentThread();
//PVOID StartAddress, EndAddress;
PVOID WaitObjects[2];
NTSTATUS Status;
KIRQL OldIrql;
PVOID ZeroAddress;
PFN_NUMBER PageIndex, FreePage;
PMMPFN Pfn1;
/* FIXME: Get the discardable sections to free them */
// MiFindInitializationCode(&StartAddress, &EndAddress);
// if (StartAddress) MiFreeInitializationCode(StartAddress, EndAddress);
/* Set our priority to 0 */
Thread->BasePriority = 0;
KeSetPriorityThread(Thread, 0);
/* Setup the wait objects */
WaitObjects[0] = &MmZeroingPageEvent;
// WaitObjects[1] = &PoSystemIdleTimer; FIXME: Implement idle timer
while (TRUE)
{
Status = KeWaitForMultipleObjects(1, // 2
WaitObjects,
WaitAny,
WrFreePage,
KernelMode,
FALSE,
NULL,
NULL);
OldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
while (TRUE)
{
if (!MmFreePageListHead.Total)
{
MmZeroingPageThreadActive = FALSE;
KeReleaseQueuedSpinLock(LockQueuePfnLock, OldIrql);
break;
}
PageIndex = MmFreePageListHead.Flink;
Pfn1 = MiGetPfnEntry(PageIndex);
FreePage = MiRemoveAnyPage(0); // FIXME: Use real color
if (FreePage != PageIndex)
{
KeBugCheckEx(PFN_LIST_CORRUPT,
0x8F,
FreePage,
PageIndex,
0);
}
Pfn1->u1.Flink = LIST_HEAD;
KeReleaseQueuedSpinLock(LockQueuePfnLock, OldIrql);
ZeroAddress = MiMapPagesToZeroInHyperSpace(Pfn1, 1);
ASSERT(ZeroAddress);
RtlZeroMemory(ZeroAddress, PAGE_SIZE);
MiUnmapPagesInZeroSpace(ZeroAddress, 1);
OldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
MiInsertPageInList(&MmZeroedPageListHead, PageIndex);
}
}
}
/* EOF */

View file

@ -48,8 +48,6 @@ SIZE_T MmPagedPoolCommit;
SIZE_T MmPeakCommitment;
SIZE_T MmtotalCommitLimitMaximum;
KEVENT ZeroPageThreadEvent;
static BOOLEAN ZeroPageThreadShouldTerminate = FALSE;
static RTL_BITMAP MiUserPfnBitMap;
/* FUNCTIONS *************************************************************/
@ -625,72 +623,4 @@ MmAllocPage(ULONG Type)
return PfnOffset;
}
NTSTATUS
NTAPI
MmZeroPageThreadMain(PVOID Ignored)
{
NTSTATUS Status;
KIRQL oldIrql;
PMMPFN Pfn1;
PFN_NUMBER PageIndex, FreePage;
ULONG Count;
PVOID ZeroAddress;
/* Free initial kernel memory */
//MiFreeInitMemory();
/* Set our priority to 0 */
KeGetCurrentThread()->BasePriority = 0;
KeSetPriorityThread(KeGetCurrentThread(), 0);
while(1)
{
Status = KeWaitForSingleObject(&ZeroPageThreadEvent,
0,
KernelMode,
FALSE,
NULL);
if (ZeroPageThreadShouldTerminate)
{
DPRINT1("ZeroPageThread: Terminating\n");
return STATUS_SUCCESS;
}
Count = 0;
oldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
while (MmFreePageListHead.Total)
{
PageIndex = MmFreePageListHead.Flink;
Pfn1 = MiGetPfnEntry(PageIndex);
FreePage = MiRemoveAnyPage(0); // FIXME: Use real color
if (FreePage != PageIndex)
{
KeBugCheckEx(PFN_LIST_CORRUPT,
0x8F,
FreePage,
PageIndex,
0);
}
Pfn1->u1.Flink = LIST_HEAD;
KeReleaseQueuedSpinLock(LockQueuePfnLock, oldIrql);
ZeroAddress = MiMapPagesToZeroInHyperSpace(Pfn1, 1);
ASSERT(ZeroAddress);
RtlZeroMemory(ZeroAddress, PAGE_SIZE);
MiUnmapPagesInZeroSpace(ZeroAddress, 1);
oldIrql = KeAcquireQueuedSpinLock(LockQueuePfnLock);
MiInsertPageInList(&MmZeroedPageListHead, PageIndex);
Count++;
}
DPRINT("Zeroed %d pages.\n", Count);
KeResetEvent(&ZeroPageThreadEvent);
KeReleaseQueuedSpinLock(LockQueuePfnLock, oldIrql);
}
return STATUS_SUCCESS;
}
/* EOF */

View file

@ -463,6 +463,7 @@
<file>syspte.c</file>
<file>vadnode.c</file>
<file>virtual.c</file>
<file>zeropage.c</file>
</directory>
<file>anonmem.c</file>
<file>balance.c</file>