#define NDEBUG
#include <debug.h>
+#define MODULE_INVOLVED_IN_ARM3
+#include "ARM3/miarm.h"
+
/* GLOBALS *******************************************************************/
PCHAR
"LoaderXIPRom "
};
-PBOOLEAN Mm64BitPhysicalAddress = FALSE;
+BOOLEAN Mm64BitPhysicalAddress = FALSE;
ULONG MmReadClusterSize;
-MM_STATS MmStats;
+//
+// 0 | 1 is on/off paging, 2 is undocumented
+//
+UCHAR MmDisablePagingExecutive = 1; // Forced to off
PMMPTE MmSharedUserDataPte;
PMMSUPPORT MmKernelAddressSpace;
-extern KMUTANT MmSystemLoadLock;
-extern ULONG MmBootImageSize;
BOOLEAN MiDbgEnableMdDump =
#ifdef _ARM_
TRUE;
PVOID BaseAddress;
PHYSICAL_ADDRESS BoundaryAddressMultiple;
PMEMORY_AREA MArea;
+ NTSTATUS Status;
BoundaryAddressMultiple.QuadPart = 0;
//
- // First initialize the page table and hyperspace memory areas
+ // Create the memory area to define the PTE base
+ //
+ BaseAddress = (PVOID)PTE_BASE;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ 4 * 1024 * 1024,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // Create the memory area to define Hyperspace
+ //
+ BaseAddress = (PVOID)HYPER_SPACE;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ 4 * 1024 * 1024,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // Protect the PFN database
+ //
+ BaseAddress = MmPfnDatabase;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ (MxPfnAllocation << PAGE_SHIFT),
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // ReactOS requires a memory area to keep the initial NP area off-bounds
+ //
+ BaseAddress = MmNonPagedPoolStart;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ MmSizeOfNonPagedPoolInBytes,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // And we need one more for the system NP
+ //
+ BaseAddress = MmNonPagedSystemStart;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ (ULONG_PTR)MmNonPagedPoolEnd -
+ (ULONG_PTR)MmNonPagedSystemStart,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // We also need one for system view space
+ //
+ BaseAddress = MiSystemViewStart;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ MmSystemViewSize,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // And another for session space
//
- MiInitPageDirectoryMap();
+ BaseAddress = MmSessionBase;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ (ULONG_PTR)MiSessionSpaceEnd -
+ (ULONG_PTR)MmSessionBase,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // One more for ARM paged pool
+ //
+ BaseAddress = MmPagedPoolStart;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ MmSizeOfPagedPoolInBytes,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // And now, ReactOS paged pool
+ //
+ BaseAddress = MmPagedPoolBase;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_PAGED_POOL | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ MmPagedPoolSize,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
//
// Next, the KPCR
//
BaseAddress = (PVOID)PCR;
- MmCreateMemoryArea(MmGetKernelAddressSpace(),
- MEMORY_AREA_SYSTEM | MEMORY_AREA_STATIC,
- &BaseAddress,
- PAGE_SIZE * KeNumberProcessors,
- PAGE_READWRITE,
- &MArea,
- TRUE,
- 0,
- BoundaryAddressMultiple);
-
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ PAGE_SIZE * KeNumberProcessors,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
//
// Now the KUSER_SHARED_DATA
//
BaseAddress = (PVOID)KI_USER_SHARED_DATA;
- MmCreateMemoryArea(MmGetKernelAddressSpace(),
- MEMORY_AREA_SYSTEM | MEMORY_AREA_STATIC,
- &BaseAddress,
- PAGE_SIZE,
- PAGE_READWRITE,
- &MArea,
- TRUE,
- 0,
- BoundaryAddressMultiple);
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ PAGE_SIZE,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+ //
+ // And the debugger mapping
+ //
+ BaseAddress = MI_DEBUG_MAPPING;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ PAGE_SIZE,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+
+#if defined(_X86_)
+ //
+ // Finally, reserve the 2 pages we currently make use of for HAL mappings
+ //
+ BaseAddress = (PVOID)0xFFC00000;
+ Status = MmCreateMemoryArea(MmGetKernelAddressSpace(),
+ MEMORY_AREA_OWNED_BY_ARM3 | MEMORY_AREA_STATIC,
+ &BaseAddress,
+ PAGE_SIZE * 2,
+ PAGE_READWRITE,
+ &MArea,
+ TRUE,
+ 0,
+ BoundaryAddressMultiple);
+ ASSERT(Status == STATUS_SUCCESS);
+#endif
+}
+
+VOID
+NTAPI
+MiDbgDumpAddressSpace(VOID)
+{
+ //
+ // Print the memory layout
+ //
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmSystemRangeStart,
+ (ULONG_PTR)MmSystemRangeStart + MmBootImageSize,
+ "Boot Loaded Image");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmPagedPoolBase,
+ (ULONG_PTR)MmPagedPoolBase + MmPagedPoolSize,
+ "Paged Pool");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmPfnDatabase,
+ (ULONG_PTR)MmPfnDatabase + (MxPfnAllocation << PAGE_SHIFT),
+ "PFN Database");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmNonPagedPoolStart,
+ (ULONG_PTR)MmNonPagedPoolStart + MmSizeOfNonPagedPoolInBytes,
+ "ARM³ Non Paged Pool");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MiSystemViewStart,
+ (ULONG_PTR)MiSystemViewStart + MmSystemViewSize,
+ "System View Space");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmSessionBase,
+ MiSessionSpaceEnd,
+ "Session Space");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ PTE_BASE, PDE_BASE,
+ "Page Tables");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ PDE_BASE, HYPER_SPACE,
+ "Page Directories");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ HYPER_SPACE, HYPER_SPACE + (4 * 1024 * 1024),
+ "Hyperspace");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmPagedPoolStart,
+ (ULONG_PTR)MmPagedPoolStart + MmSizeOfPagedPoolInBytes,
+ "ARM³ Paged Pool");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmNonPagedSystemStart, MmNonPagedPoolExpansionStart,
+ "System PTE Space");
+ DPRINT1(" 0x%p - 0x%p\t%s\n",
+ MmNonPagedPoolExpansionStart, MmNonPagedPoolEnd,
+ "Non Paged Pool Expansion PTE Space");
}
VOID
DPRINT1("Total: %08lX (%d MB)\n", TotalPages, (TotalPages * PAGE_SIZE) / 1024 / 1024);
}
-NTSTATUS
-NTAPI
-MmArmInitSystem(IN ULONG Phase,
- IN PLOADER_PARAMETER_BLOCK LoaderBlock);
-
-VOID
-INIT_FUNCTION
-NTAPI
-MmInit1(VOID)
-{
- /* Initialize the kernel address space */
- KeInitializeGuardedMutex(&PsGetCurrentProcess()->AddressCreationLock);
- MmKernelAddressSpace = MmGetCurrentAddressSpace();
- MmInitGlobalKernelPageDirectory();
-
- /* Dump memory descriptors */
- if (MiDbgEnableMdDump) MiDbgDumpMemoryDescriptors();
-
- //
- // Initialize ARM³ in phase 0
- //
- MmArmInitSystem(0, KeLoaderBlock);
-
- /* Intialize system memory areas */
- MiInitSystemMemoryAreas();
-
- /* Initialize the page list */
- MmInitializePageList();
-
- //
- // Initialize ARM³ in phase 1
- //
- MmArmInitSystem(1, KeLoaderBlock);
-
- /* Put the paged pool after the loaded modules */
- MmPagedPoolBase = (PVOID)PAGE_ROUND_UP((ULONG_PTR)MmSystemRangeStart +
- MmBootImageSize);
- MmPagedPoolSize = MM_PAGED_POOL_SIZE;
-
- //
- // Initialize ARM³ in phase 2
- //
- MmArmInitSystem(2, KeLoaderBlock);
-
- /* Initialize paged pool */
- MmInitializePagedPool();
-
- /* Initialize working sets */
- MmInitializeMemoryConsumer(MC_USER, MmTrimUserMemory);
-}
+VOID NTAPI MiInitializeUserPfnBitmap(VOID);
BOOLEAN
NTAPI
MmInitSystem(IN ULONG Phase,
IN PLOADER_PARAMETER_BLOCK LoaderBlock)
{
- extern MMPTE HyperTemplatePte;
+ extern MMPTE ValidKernelPte;
PMMPTE PointerPte;
- MMPTE TempPte = HyperTemplatePte;
+ MMPTE TempPte = ValidKernelPte;
PFN_NUMBER PageFrameNumber;
if (Phase == 0)
{
- /* Initialize Mm bootstrap */
- MmInit1();
-
- /* Initialize the Loader Lock */
- KeInitializeMutant(&MmSystemLoadLock, FALSE);
-
- /* Reload boot drivers */
- MiReloadBootLoadedDrivers(LoaderBlock);
-
- /* Initialize the loaded module list */
- MiInitializeLoadedModuleList(LoaderBlock);
-
- /* Setup shared user data settings that NT does as well */
- ASSERT(SharedUserData->NumberOfPhysicalPages == 0);
- SharedUserData->NumberOfPhysicalPages = MmStats.NrTotalPages;
- SharedUserData->LargePageMinimum = 0;
+ /* Initialize the kernel address space */
+ KeInitializeGuardedMutex(&PsGetCurrentProcess()->AddressCreationLock);
+ MmKernelAddressSpace = MmGetCurrentAddressSpace();
+ MmInitGlobalKernelPageDirectory();
+
+ /* Dump memory descriptors */
+ if (MiDbgEnableMdDump) MiDbgDumpMemoryDescriptors();
+
+ /* Initialize ARM³ in phase 0 */
+ MmArmInitSystem(0, KeLoaderBlock);
- /* For now, we assume that we're always Server */
- SharedUserData->NtProductType = NtProductServer;
+ /* Put the paged pool after the loaded modules */
+ MmPagedPoolBase = (PVOID)PAGE_ROUND_UP((ULONG_PTR)MmSystemRangeStart +
+ MmBootImageSize);
+ MmPagedPoolSize = MM_PAGED_POOL_SIZE;
+
+ /* Intialize system memory areas */
+ MiInitSystemMemoryAreas();
+
+ /* Dump the address space */
+ MiDbgDumpAddressSpace();
}
else if (Phase == 1)
{
+ MmInitializePagedPool();
+ MiInitializeUserPfnBitmap();
+ MmInitializeMemoryConsumer(MC_USER, MmTrimUserMemory);
MmInitializeRmapList();
MmInitializePageOp();
MmInitSectionImplementation();
//
// Now write a copy of it
//
- TempPte.u.Hard.Owner = 1;
+ MI_MAKE_OWNER_PAGE(&TempPte);
TempPte.u.Hard.PageFrameNumber = PageFrameNumber;
*MmSharedUserDataPte = TempPte;
+ /* Setup the memory threshold events */
+ if (!MiInitializeMemoryEvents()) return FALSE;
+
/*
* Unmap low memory
*/
}
else if (Phase == 2)
{
-
+ /* Enough fun for now */
+ extern BOOLEAN AllowPagedPool;
+ AllowPagedPool = FALSE;
}
return TRUE;