https://git.reactos.org/?p=reactos.git;a=commitdiff;h=98e62b9bcaf62883298a7…
commit 98e62b9bcaf62883298a773e545859ec624dab20
Author: Jérôme Gardou <jerome.gardou(a)reactos.org>
AuthorDate: Mon Aug 2 18:46:05 2021 +0200
Commit: Jérôme Gardou <zefklop(a)users.noreply.github.com>
CommitDate: Wed Aug 4 17:48:39 2021 +0200
[NTOS:MM] In page zeroing thread, zero more than one page at a time.
---
ntoskrnl/mm/ARM3/zeropage.c | 75 +++++++++++++++++++++++++++------------------
1 file changed, 46 insertions(+), 29 deletions(-)
diff --git a/ntoskrnl/mm/ARM3/zeropage.c b/ntoskrnl/mm/ARM3/zeropage.c
index 5ad738b53d4..407fb03e27c 100644
--- a/ntoskrnl/mm/ARM3/zeropage.c
+++ b/ntoskrnl/mm/ARM3/zeropage.c
@@ -38,10 +38,6 @@ MmZeroPageThread(VOID)
PKTHREAD Thread = KeGetCurrentThread();
PVOID StartAddress, EndAddress;
PVOID WaitObjects[2];
- KIRQL OldIrql;
- PVOID ZeroAddress;
- PFN_NUMBER PageIndex, FreePage;
- PMMPFN Pfn1;
/* Get the discardable sections to free them */
MiFindInitializationCode(&StartAddress, &EndAddress);
@@ -58,6 +54,8 @@ MmZeroPageThread(VOID)
while (TRUE)
{
+ KIRQL OldIrql;
+
KeWaitForMultipleObjects(1, // 2
WaitObjects,
WaitAny,
@@ -70,41 +68,60 @@ MmZeroPageThread(VOID)
while (TRUE)
{
- if (!MmFreePageListHead.Total)
+ ULONG PageCount = 0;
+ PMMPFN Pfn1 = (PMMPFN)LIST_HEAD;
+ PVOID ZeroAddress;
+ PFN_NUMBER PageIndex, FreePage;
+
+ while (PageCount < MI_ZERO_PTES)
{
- KeClearEvent(&MmZeroingPageEvent);
- MiReleasePfnLock(OldIrql);
- break;
+ PMMPFN Pfn2;
+
+ if (!MmFreePageListHead.Total)
+ break;
+
+ PageIndex = MmFreePageListHead.Flink;
+ ASSERT(PageIndex != LIST_HEAD);
+ MI_SET_USAGE(MI_USAGE_ZERO_LOOP);
+ MI_SET_PROCESS2("Kernel 0 Loop");
+ FreePage = MiRemoveAnyPage(MI_GET_PAGE_COLOR(PageIndex));
+
+ /* The first global free page should also be the first on its own list
*/
+ if (FreePage != PageIndex)
+ {
+ KeBugCheckEx(PFN_LIST_CORRUPT,
+ 0x8F,
+ FreePage,
+ PageIndex,
+ 0);
+ }
+
+ Pfn2 = MiGetPfnEntry(PageIndex);
+ Pfn2->u1.Flink = (PFN_NUMBER)Pfn1;
+ Pfn1 = Pfn2;
+ PageCount++;
}
+ MiReleasePfnLock(OldIrql);
- PageIndex = MmFreePageListHead.Flink;
- ASSERT(PageIndex != LIST_HEAD);
- Pfn1 = MiGetPfnEntry(PageIndex);
- MI_SET_USAGE(MI_USAGE_ZERO_LOOP);
- MI_SET_PROCESS2("Kernel 0 Loop");
- FreePage = MiRemoveAnyPage(MI_GET_PAGE_COLOR(PageIndex));
-
- /* The first global free page should also be the first on its own list */
- if (FreePage != PageIndex)
+ if (PageCount == 0)
{
- KeBugCheckEx(PFN_LIST_CORRUPT,
- 0x8F,
- FreePage,
- PageIndex,
- 0);
+ KeClearEvent(&MmZeroingPageEvent);
+ break;
}
- Pfn1->u1.Flink = LIST_HEAD;
- MiReleasePfnLock(OldIrql);
-
- ZeroAddress = MiMapPagesInZeroSpace(Pfn1, 1);
+ ZeroAddress = MiMapPagesInZeroSpace(Pfn1, PageCount);
ASSERT(ZeroAddress);
- KeZeroPages(ZeroAddress, PAGE_SIZE);
- MiUnmapPagesInZeroSpace(ZeroAddress, 1);
+ KeZeroPages(ZeroAddress, PageCount * PAGE_SIZE);
+ MiUnmapPagesInZeroSpace(ZeroAddress, PageCount);
OldIrql = MiAcquirePfnLock();
- MiInsertPageInList(&MmZeroedPageListHead, PageIndex);
+ while (Pfn1 != (PMMPFN)LIST_HEAD)
+ {
+ PageIndex = MiGetPfnEntryIndex(Pfn1);
+ Pfn1 = (PMMPFN)Pfn1->u1.Flink;
+ MiInsertPageInList(&MmZeroedPageListHead, PageIndex);
+ }
}
}
}