[RSHELL]
[reactos.git] / ntoskrnl / mm / mmfault.c
index c4a8173..602d708 100644 (file)
@@ -9,6 +9,7 @@
 /* INCLUDES *******************************************************************/
 
 #include <ntoskrnl.h>
+#include "../cache/section/newmm.h"
 #define NDEBUG
 #include <debug.h>
 
 
 /* PRIVATE FUNCTIONS **********************************************************/
 
-VOID
-FASTCALL
-MiSyncForProcessAttach(IN PKTHREAD Thread,
-                       IN PEPROCESS Process)
-{
-    PETHREAD Ethread = CONTAINING_RECORD(Thread, ETHREAD, Tcb);
-
-    /* Hack Sync because Mm is broken */
-    MmUpdatePageDir(Process, Ethread, sizeof(ETHREAD));
-    MmUpdatePageDir(Process, Ethread->ThreadsProcess, sizeof(EPROCESS));
-    MmUpdatePageDir(Process,
-                    (PVOID)Thread->StackLimit,
-                    Thread->LargeStack ?
-                    KERNEL_LARGE_STACK_SIZE : KERNEL_STACK_SIZE);
-}
-
-VOID
-FASTCALL
-MiSyncForContextSwitch(IN PKTHREAD Thread)
-{
-    PVOID Process = PsGetCurrentProcess();
-    PETHREAD Ethread = CONTAINING_RECORD(Thread, ETHREAD, Tcb);
-
-    /* Hack Sync because Mm is broken */
-    MmUpdatePageDir(Process, Ethread->ThreadsProcess, sizeof(EPROCESS));
-    MmUpdatePageDir(Process,
-                    (PVOID)Thread->StackLimit,
-                    Thread->LargeStack ?
-                    KERNEL_LARGE_STACK_SIZE : KERNEL_STACK_SIZE);
-}
-
 NTSTATUS
 NTAPI
 MmpAccessFault(KPROCESSOR_MODE Mode,
@@ -57,13 +27,12 @@ MmpAccessFault(KPROCESSOR_MODE Mode,
    PMMSUPPORT AddressSpace;
    MEMORY_AREA* MemoryArea;
    NTSTATUS Status;
-   BOOLEAN Locked = FromMdl;
 
    DPRINT("MmAccessFault(Mode %d, Address %x)\n", Mode, Address);
 
    if (KeGetCurrentIrql() >= DISPATCH_LEVEL)
    {
-      DPRINT1("Page fault at high IRQL was %d\n", KeGetCurrentIrql());
+      DPRINT1("Page fault at high IRQL was %u\n", KeGetCurrentIrql());
       return(STATUS_UNSUCCESSFUL);
    }
 
@@ -105,27 +74,20 @@ MmpAccessFault(KPROCESSOR_MODE Mode,
 
       switch (MemoryArea->Type)
       {
-         case MEMORY_AREA_SYSTEM:
-            Status = STATUS_ACCESS_VIOLATION;
-            break;
-
-         case MEMORY_AREA_PAGED_POOL:
-            Status = STATUS_SUCCESS;
-            break;
-
          case MEMORY_AREA_SECTION_VIEW:
             Status = MmAccessFaultSectionView(AddressSpace,
                                               MemoryArea,
-                                              (PVOID)Address,
-                                              Locked);
-            break;
-
-         case MEMORY_AREA_VIRTUAL_MEMORY:
-            Status = STATUS_ACCESS_VIOLATION;
+                                              (PVOID)Address);
             break;
 
-         case MEMORY_AREA_SHARED_DATA:
-            Status = STATUS_ACCESS_VIOLATION;
+         case MEMORY_AREA_CACHE:
+            // This code locks for itself to keep from having to break a lock
+            // passed in.
+            if (!FromMdl)
+               MmUnlockAddressSpace(AddressSpace);
+            Status = MmAccessFaultCacheSection(Mode, Address, FromMdl);
+            if (!FromMdl)
+               MmLockAddressSpace(AddressSpace);
             break;
 
          default:
@@ -152,14 +114,12 @@ MmNotPresentFault(KPROCESSOR_MODE Mode,
    PMMSUPPORT AddressSpace;
    MEMORY_AREA* MemoryArea;
    NTSTATUS Status;
-   BOOLEAN Locked = FromMdl;
-   extern PMMPTE MmSharedUserDataPte;
 
    DPRINT("MmNotPresentFault(Mode %d, Address %x)\n", Mode, Address);
 
    if (KeGetCurrentIrql() >= DISPATCH_LEVEL)
    {
-      DPRINT1("Page fault at high IRQL was %d, address %x\n", KeGetCurrentIrql(), Address);
+      DPRINT1("Page fault at high IRQL was %u, address %x\n", KeGetCurrentIrql(), Address);
       return(STATUS_UNSUCCESSFUL);
    }
 
@@ -173,7 +133,7 @@ MmNotPresentFault(KPROCESSOR_MODE Mode,
        */
       if (Mode != KernelMode)
       {
-        DPRINT1("Address: %x\n", Address);
+         DPRINT1("Address: %x\n", Address);
          return(STATUS_ACCESS_VIOLATION);
       }
       AddressSpace = MmGetKernelAddressSpace();
@@ -205,34 +165,21 @@ MmNotPresentFault(KPROCESSOR_MODE Mode,
 
       switch (MemoryArea->Type)
       {
-         case MEMORY_AREA_PAGED_POOL:
-            {
-               Status = MmCommitPagedPoolAddress((PVOID)Address, Locked);
-               break;
-            }
-
-         case MEMORY_AREA_SYSTEM:
-            Status = STATUS_ACCESS_VIOLATION;
-            break;
-
          case MEMORY_AREA_SECTION_VIEW:
             Status = MmNotPresentFaultSectionView(AddressSpace,
                                                   MemoryArea,
                                                   (PVOID)Address,
-                                                  Locked);
-            break;
-
-         case MEMORY_AREA_VIRTUAL_MEMORY:
-         case MEMORY_AREA_PEB_OR_TEB:
-            Status = MmNotPresentFaultVirtualMemory(AddressSpace,
-                                                    MemoryArea,
-                                                    (PVOID)Address,
-                                                    Locked);
+                                                  FromMdl);
             break;
 
-         case MEMORY_AREA_SHARED_DATA:
-              *MiAddressToPte(USER_SHARED_DATA) = *MmSharedUserDataPte;
-              Status = STATUS_SUCCESS;
+         case MEMORY_AREA_CACHE:
+            // This code locks for itself to keep from having to break a lock
+            // passed in.
+            if (!FromMdl)
+               MmUnlockAddressSpace(AddressSpace);
+            Status = MmNotPresentFaultCacheSection(Mode, Address, FromMdl);
+            if (!FromMdl)
+               MmLockAddressSpace(AddressSpace);
             break;
 
          default:
@@ -259,7 +206,7 @@ MmAccessFault(IN BOOLEAN StoreInstruction,
               IN KPROCESSOR_MODE Mode,
               IN PVOID TrapInformation)
 {
-    PMEMORY_AREA MemoryArea;
+    PMEMORY_AREA MemoryArea = NULL;
 
     /* Cute little hack for ROS */
     if ((ULONG_PTR)Address >= (ULONG_PTR)MmSystemRangeStart)
@@ -273,26 +220,28 @@ MmAccessFault(IN BOOLEAN StoreInstruction,
         }
 #endif
     }
-    
-    /* 
-     * Check if this is an ARM3 memory area or if there's no memory area at all.
-     * The latter can happen early in the boot cycle when ARM3 paged pool is in
-     * use before having defined the memory areas proper.
-     * A proper fix would be to define memory areas in the ARM3 code, but we want
-     * to avoid adding this ReactOS-specific construct to ARM3 code.
-     * Either way, in the future, as ReactOS-paged pool is eliminated, this hack
-     * can go away.
-     */
-    MemoryArea = MmLocateMemoryAreaByAddress(MmGetKernelAddressSpace(), Address);
-    if ((!(MemoryArea) && ((ULONG_PTR)Address >= (ULONG_PTR)MmPagedPoolStart)) ||
-        ((MemoryArea) && (MemoryArea->Type == MEMORY_AREA_OWNED_BY_ARM3)))
+
+    /* 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))
+        {
+            /* Could this be a VAD fault from user-mode? */
+            MemoryArea = MmLocateMemoryAreaByAddress(MmGetCurrentAddressSpace(), Address);
+        }
+    }
+
+    /* 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()))
     {
-        //
-        // Hand it off to more competent hands...
-        //
+        /* This is an ARM3 fault */
         DPRINT("ARM3 fault %p\n", MemoryArea);
         return MmArmAccessFault(StoreInstruction, Address, Mode, TrapInformation);
-    }   
+    }
 
     /* Keep same old ReactOS Behaviour */
     if (StoreInstruction)
@@ -307,25 +256,3 @@ MmAccessFault(IN BOOLEAN StoreInstruction,
     }
 }
 
-NTSTATUS
-NTAPI
-MmCommitPagedPoolAddress(PVOID Address, BOOLEAN Locked)
-{
-   NTSTATUS Status;
-   PFN_TYPE AllocatedPage;
-
-   Status = MmRequestPageMemoryConsumer(MC_PPOOL, FALSE, &AllocatedPage);
-   if (!NT_SUCCESS(Status))
-   {
-      MmUnlockAddressSpace(MmGetKernelAddressSpace());
-      Status = MmRequestPageMemoryConsumer(MC_PPOOL, TRUE, &AllocatedPage);
-      MmLockAddressSpace(MmGetKernelAddressSpace());
-   }
-   Status =
-      MmCreateVirtualMapping(NULL,
-                             (PVOID)PAGE_ROUND_DOWN(Address),
-                             PAGE_READWRITE,
-                             &AllocatedPage,
-                             1);
-   return(Status);
-}