https://git.reactos.org/?p=reactos.git;a=commitdiff;h=a662bedab8310ac4c15e1337e584e5f5835d14f5

commit a662bedab8310ac4c15e1337e584e5f5835d14f5
Author:     Timo Kreuzer <timo.kreu...@reactos.org>
AuthorDate: Tue Oct 10 02:10:52 2023 +0300
Commit:     Timo Kreuzer <timo.kreu...@reactos.org>
CommitDate: Tue Oct 24 21:45:27 2023 +0300

    [NTOS:MM] Fix bugs in MmAccessFault
    
    - Acquire the appropriate working set lock when calling 
MmLocateMemoryAreaByAddress
    - Do not access MemoryArea without holding the lock (otherwise it can be 
pulled away under our feet)
    - Fix range check for paged pool
---
 ntoskrnl/mm/mmfault.c | 34 ++++++++++++++++++++++++++++------
 1 file changed, 28 insertions(+), 6 deletions(-)

diff --git a/ntoskrnl/mm/mmfault.c b/ntoskrnl/mm/mmfault.c
index 68e31ba1281..cfd6d756d15 100644
--- a/ntoskrnl/mm/mmfault.c
+++ b/ntoskrnl/mm/mmfault.c
@@ -213,6 +213,7 @@ MmAccessFault(IN ULONG FaultCode,
 {
     PMEMORY_AREA MemoryArea = NULL;
     NTSTATUS Status;
+    BOOLEAN IsArm3Fault = FALSE;
 
     /* Cute little hack for ROS */
     if ((ULONG_PTR)Address >= (ULONG_PTR)MmSystemRangeStart)
@@ -239,19 +240,40 @@ MmAccessFault(IN ULONG FaultCode,
     /* Is there a ReactOS address space yet? */
     if (MmGetKernelAddressSpace())
     {
-        /* Check if this is an ARM3 memory area */
-        MemoryArea = MmLocateMemoryAreaByAddress(MmGetKernelAddressSpace(), 
Address);
-        if (!(MemoryArea) && (Address <= MM_HIGHEST_USER_ADDRESS))
+        if (Address > MM_HIGHEST_USER_ADDRESS)
+        {
+            /* Check if this is an ARM3 memory area */
+            MiLockWorkingSetShared(PsGetCurrentThread(), &MmSystemCacheWs);
+            MemoryArea = 
MmLocateMemoryAreaByAddress(MmGetKernelAddressSpace(), Address);
+
+            if ((MemoryArea != NULL) && (MemoryArea->Type == 
MEMORY_AREA_OWNED_BY_ARM3))
+            {
+                IsArm3Fault = TRUE;
+            }
+
+            MiUnlockWorkingSetShared(PsGetCurrentThread(), &MmSystemCacheWs);
+        }
+        else
         {
             /* Could this be a VAD fault from user-mode? */
+            MiLockProcessWorkingSetShared(PsGetCurrentProcess(), 
PsGetCurrentThread());
             MemoryArea = 
MmLocateMemoryAreaByAddress(MmGetCurrentAddressSpace(), Address);
+
+            if ((MemoryArea != NULL) && (MemoryArea->Type == 
MEMORY_AREA_OWNED_BY_ARM3))
+            {
+                IsArm3Fault = TRUE;
+            }
+
+            MiUnlockProcessWorkingSetShared(PsGetCurrentProcess(), 
PsGetCurrentThread());
         }
     }
 
     /* Is this an ARM3 memory area, or is there no address space yet? */
-    if (((MemoryArea) && (MemoryArea->Type == MEMORY_AREA_OWNED_BY_ARM3)) ||
-            (!(MemoryArea) && ((ULONG_PTR)Address >= 
(ULONG_PTR)MmPagedPoolStart)) ||
-            (!MmGetKernelAddressSpace()))
+    if (IsArm3Fault ||
+        ((MemoryArea == NULL) &&
+         ((ULONG_PTR)Address >= (ULONG_PTR)MmPagedPoolStart) &&
+         ((ULONG_PTR)Address < (ULONG_PTR)MmPagedPoolEnd)) ||
+        (!MmGetKernelAddressSpace()))
     {
         /* This is an ARM3 fault */
         DPRINT("ARM3 fault %p\n", MemoryArea);

Reply via email to