2009-10-15 17:01:31 +00:00
|
|
|
/*
|
|
|
|
* PROJECT: ReactOS Kernel
|
|
|
|
* LICENSE: BSD - See COPYING.ARM in the top level directory
|
|
|
|
* FILE: ntoskrnl/mm/ARM3/mmsup.c
|
|
|
|
* PURPOSE: ARM Memory Manager Support Routines
|
|
|
|
* PROGRAMMERS: ReactOS Portable Systems Group
|
|
|
|
*/
|
|
|
|
|
|
|
|
/* INCLUDES *******************************************************************/
|
|
|
|
|
|
|
|
#include <ntoskrnl.h>
|
|
|
|
#define NDEBUG
|
|
|
|
#include <debug.h>
|
|
|
|
|
|
|
|
#define MODULE_INVOLVED_IN_ARM3
|
2014-11-10 16:26:55 +00:00
|
|
|
#include <mm/ARM3/miarm.h>
|
2009-10-15 17:01:31 +00:00
|
|
|
|
2014-02-20 23:03:04 +00:00
|
|
|
/* GLOBALS ********************************************************************/
|
|
|
|
|
|
|
|
SIZE_T MmMinimumWorkingSetSize;
|
|
|
|
SIZE_T MmMaximumWorkingSetSize;
|
|
|
|
SIZE_T MmPagesAboveWsMinimum;
|
|
|
|
|
2009-10-15 17:01:31 +00:00
|
|
|
/* PUBLIC FUNCTIONS ***********************************************************/
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @unimplemented
|
|
|
|
*/
|
|
|
|
NTSTATUS
|
|
|
|
NTAPI
|
|
|
|
MmMapUserAddressesToPage(IN PVOID BaseAddress,
|
|
|
|
IN SIZE_T NumberOfBytes,
|
|
|
|
IN PVOID PageAddress)
|
|
|
|
{
|
|
|
|
UNIMPLEMENTED;
|
|
|
|
return STATUS_NOT_IMPLEMENTED;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @unimplemented
|
|
|
|
*/
|
|
|
|
NTSTATUS
|
|
|
|
NTAPI
|
|
|
|
MmAdjustWorkingSetSize(IN SIZE_T WorkingSetMinimumInBytes,
|
|
|
|
IN SIZE_T WorkingSetMaximumInBytes,
|
|
|
|
IN ULONG SystemCache,
|
|
|
|
IN BOOLEAN IncreaseOkay)
|
|
|
|
{
|
2014-02-20 23:03:04 +00:00
|
|
|
SIZE_T MinimumWorkingSetSize, MaximumWorkingSetSize;
|
|
|
|
SSIZE_T Delta;
|
|
|
|
PMMSUPPORT Ws;
|
|
|
|
NTSTATUS Status;
|
|
|
|
|
|
|
|
/* Check for special case: empty the working set */
|
|
|
|
if ((WorkingSetMinimumInBytes == -1) &&
|
|
|
|
(WorkingSetMaximumInBytes == -1))
|
|
|
|
{
|
|
|
|
UNIMPLEMENTED;
|
|
|
|
return STATUS_NOT_IMPLEMENTED;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Assume success */
|
|
|
|
Status = STATUS_SUCCESS;
|
|
|
|
|
|
|
|
/* Get the working set and lock it */
|
|
|
|
Ws = &PsGetCurrentProcess()->Vm;
|
|
|
|
MiLockWorkingSet(PsGetCurrentThread(), Ws);
|
|
|
|
|
|
|
|
/* Calculate the actual minimum and maximum working set size to set */
|
|
|
|
MinimumWorkingSetSize = (WorkingSetMinimumInBytes != 0) ?
|
|
|
|
(WorkingSetMinimumInBytes / PAGE_SIZE) : Ws->MinimumWorkingSetSize;
|
|
|
|
MaximumWorkingSetSize = (WorkingSetMaximumInBytes != 0) ?
|
|
|
|
(WorkingSetMaximumInBytes / PAGE_SIZE) : Ws->MaximumWorkingSetSize;
|
|
|
|
|
|
|
|
/* Check if the new maximum exceeds the global maximum */
|
|
|
|
if (MaximumWorkingSetSize > MmMaximumWorkingSetSize)
|
|
|
|
{
|
|
|
|
MaximumWorkingSetSize = MmMaximumWorkingSetSize;
|
|
|
|
Status = STATUS_WORKING_SET_LIMIT_RANGE;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Check if the new minimum is below the global minimum */
|
|
|
|
if (MinimumWorkingSetSize < MmMinimumWorkingSetSize)
|
|
|
|
{
|
|
|
|
MinimumWorkingSetSize = MmMinimumWorkingSetSize;
|
|
|
|
Status = STATUS_WORKING_SET_LIMIT_RANGE;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Check if the new minimum exceeds the new maximum */
|
|
|
|
if (MinimumWorkingSetSize > MaximumWorkingSetSize)
|
|
|
|
{
|
2014-04-16 12:30:47 +00:00
|
|
|
DPRINT1("MinimumWorkingSetSize (%lu) > MaximumWorkingSetSize (%lu)\n",
|
|
|
|
MinimumWorkingSetSize, MaximumWorkingSetSize);
|
2014-02-20 23:03:04 +00:00
|
|
|
Status = STATUS_BAD_WORKING_SET_LIMIT;
|
|
|
|
goto Cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Calculate the minimum WS size adjustment and check if we increase */
|
|
|
|
Delta = MinimumWorkingSetSize - Ws->MinimumWorkingSetSize;
|
|
|
|
if (Delta > 0)
|
|
|
|
{
|
|
|
|
/* Is increasing ok? */
|
|
|
|
if (!IncreaseOkay)
|
|
|
|
{
|
|
|
|
DPRINT1("Privilege for WS size increase not held\n");
|
|
|
|
Status = STATUS_PRIVILEGE_NOT_HELD;
|
|
|
|
goto Cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Check if the number of available pages is large enough */
|
|
|
|
if (((SIZE_T)Delta / 1024) > (MmAvailablePages - 128))
|
|
|
|
{
|
|
|
|
DPRINT1("Not enough available pages\n");
|
|
|
|
Status = STATUS_INSUFFICIENT_RESOURCES;
|
|
|
|
goto Cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Check if there are enough resident available pages */
|
|
|
|
if ((SIZE_T)Delta >
|
|
|
|
(MmResidentAvailablePages - MmSystemLockPagesCount - 256))
|
|
|
|
{
|
|
|
|
DPRINT1("Not enough resident pages\n");
|
|
|
|
Status = STATUS_INSUFFICIENT_RESOURCES;
|
|
|
|
goto Cleanup;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Update resident available pages */
|
|
|
|
if (Delta != 0)
|
|
|
|
{
|
|
|
|
InterlockedExchangeAddSizeT(&MmResidentAvailablePages, -Delta);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Calculate new pages above minimum WS size */
|
|
|
|
Delta += max((SSIZE_T)Ws->WorkingSetSize - MinimumWorkingSetSize, 0);
|
|
|
|
|
|
|
|
/* Subtract old pages above minimum WS size */
|
|
|
|
Delta -= max((SSIZE_T)Ws->WorkingSetSize - Ws->MinimumWorkingSetSize, 0);
|
|
|
|
|
|
|
|
/* If it changed, add it to the global variable */
|
|
|
|
if (Delta != 0)
|
|
|
|
{
|
|
|
|
InterlockedExchangeAddSizeT(&MmPagesAboveWsMinimum, Delta);
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Set the new working set size */
|
|
|
|
Ws->MinimumWorkingSetSize = MinimumWorkingSetSize;
|
|
|
|
Ws->MaximumWorkingSetSize = MaximumWorkingSetSize;
|
|
|
|
|
|
|
|
Cleanup:
|
|
|
|
|
|
|
|
/* Unlock the working set and return the status */
|
|
|
|
MiUnlockWorkingSet(PsGetCurrentThread(), Ws);
|
|
|
|
return Status;
|
2009-10-15 17:01:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @unimplemented
|
|
|
|
*/
|
|
|
|
BOOLEAN
|
|
|
|
NTAPI
|
|
|
|
MmSetAddressRangeModified(IN PVOID Address,
|
|
|
|
IN SIZE_T Length)
|
|
|
|
{
|
|
|
|
UNIMPLEMENTED;
|
|
|
|
return FALSE;
|
|
|
|
}
|
|
|
|
|
2009-11-04 22:40:18 +00:00
|
|
|
/*
|
|
|
|
* @implemented
|
|
|
|
*/
|
|
|
|
BOOLEAN
|
|
|
|
NTAPI
|
|
|
|
MmIsAddressValid(IN PVOID VirtualAddress)
|
|
|
|
{
|
2010-07-25 00:50:03 +00:00
|
|
|
#if _MI_PAGING_LEVELS >= 4
|
|
|
|
/* Check if the PXE is valid */
|
|
|
|
if (MiAddressToPxe(VirtualAddress)->u.Hard.Valid == 0) return FALSE;
|
|
|
|
#endif
|
2009-11-04 22:40:18 +00:00
|
|
|
|
2010-07-25 00:50:03 +00:00
|
|
|
#if _MI_PAGING_LEVELS >= 3
|
|
|
|
/* Check if the PPE is valid */
|
|
|
|
if (MiAddressToPpe(VirtualAddress)->u.Hard.Valid == 0) return FALSE;
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#if _MI_PAGING_LEVELS >= 2
|
|
|
|
/* Check if the PDE is valid */
|
|
|
|
if (MiAddressToPde(VirtualAddress)->u.Hard.Valid == 0) return FALSE;
|
|
|
|
#endif
|
|
|
|
|
|
|
|
/* Check if the PTE is valid */
|
|
|
|
if (MiAddressToPte(VirtualAddress)->u.Hard.Valid == 0) return FALSE;
|
|
|
|
|
|
|
|
/* This address is valid now, but it will only stay so if the caller holds
|
|
|
|
* the PFN lock */
|
2009-11-04 22:40:18 +00:00
|
|
|
return TRUE;
|
|
|
|
}
|
|
|
|
|
2009-10-15 17:01:31 +00:00
|
|
|
/*
|
|
|
|
* @unimplemented
|
|
|
|
*/
|
|
|
|
BOOLEAN
|
|
|
|
NTAPI
|
|
|
|
MmIsNonPagedSystemAddressValid(IN PVOID VirtualAddress)
|
|
|
|
{
|
|
|
|
DPRINT1("WARNING: %s returns bogus result\n", __FUNCTION__);
|
|
|
|
return MmIsAddressValid(VirtualAddress);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @unimplemented
|
|
|
|
*/
|
|
|
|
NTSTATUS
|
|
|
|
NTAPI
|
|
|
|
MmSetBankedSection(IN HANDLE ProcessHandle,
|
|
|
|
IN PVOID VirtualAddress,
|
|
|
|
IN ULONG BankLength,
|
|
|
|
IN BOOLEAN ReadWriteBank,
|
|
|
|
IN PVOID BankRoutine,
|
|
|
|
IN PVOID Context)
|
|
|
|
{
|
|
|
|
UNIMPLEMENTED;
|
|
|
|
return STATUS_NOT_IMPLEMENTED;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @implemented
|
|
|
|
*/
|
|
|
|
BOOLEAN
|
|
|
|
NTAPI
|
|
|
|
MmIsRecursiveIoFault(VOID)
|
|
|
|
{
|
|
|
|
PETHREAD Thread = PsGetCurrentThread();
|
2010-12-26 15:23:03 +00:00
|
|
|
|
2009-10-15 17:01:31 +00:00
|
|
|
//
|
|
|
|
// If any of these is true, this is a recursive fault
|
|
|
|
//
|
|
|
|
return ((Thread->DisablePageFaultClustering) | (Thread->ForwardClusterOnly));
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @implemented
|
|
|
|
*/
|
|
|
|
BOOLEAN
|
|
|
|
NTAPI
|
|
|
|
MmIsThisAnNtAsSystem(VOID)
|
|
|
|
{
|
[NTOS]: Make MM init read MmProductType to determine what SKU of ReactOS this is, instead of assuming Server. If you want to go back to the old behavior, you need to change "WinNT" to "ServerNT" in the hivesys under Product Type.
[NTOS]: Configure the MmSystemSize variable properly based on SKU and RAM. Previously, ReactOS told all drivers and applications you were running on a system with < 13MB RAM.
[NTOS]: Initialize thresholds for low and high memory (in pages), low and high paged pool memory, and low and high nonpaged pool memory. These are described in the source.
[NTOS]: Initialize events for each of those thresholds, and populate the \KernelObject\xxxCondition events that are documented in MSDN for driver and app developers.
[NTOS]: Define some internal thresholds to use later, representing the minimum number of free pages under we go berserk, and the minimum number of free pages that we consider "plenty".
[NTOS]: Rename MiRemoveFromList to MiUnlinkFreeOrZeroedPage (Windows name). Make the function handle MmAvailablePages decrement, instead of having the caller do it.
[NTOS]: Remove run-time initialization of the PFN lists, just initialize them statically (also fixes the fact we forgot to initialize their names).
[NTOS]: Move some more initialization code to ARM3 instead of mm.
[NTOS]: Read ProductType from registry into MmProductType instead of dummy value. Remove duplicate "Mirroring" variable read.
svn path=/trunk/; revision=45638
2010-02-20 21:48:36 +00:00
|
|
|
/* Return if this is a server system */
|
[HAL/NDK]
- Make Vector parameter in HalEnableSystemInterrupt, HalDisableSystemInterrupt and HalBeginSystemInterrupt an ULONG, not an UCHAR
[NDK]
- 64bit fixes for HANDLE_TABLE, KPROCESS, SECTION_IMAGE_INFORMATION, MMADDRESS_LIST, MMVAD_FLAGS, MMVAD, MMVAD_LONG, MMVAD_SHORT, MEMORY_DESCRIPTOR, MEMORY_ALLOCATION_DESCRIPTOR, LdrVerifyMappedImageMatchesChecksum
- KDPC_DATA::DpcQueueDepth is signed on amd64, unsigned on x86
[NTOSKRNL]
- Fix hundreds of MSVC and amd64 warnings
- add a pragma message to FstubFixupEfiPartition, since it looks broken
- Move portable Ke constants from <arch>/cpu.c to krnlinit.c
- Fixed a bug in amd64 KiGeneralProtectionFaultHandler
svn path=/trunk/; revision=53734
2011-09-18 13:11:45 +00:00
|
|
|
return MmProductType & 0xFF;
|
2009-10-15 17:01:31 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* @implemented
|
|
|
|
*/
|
|
|
|
MM_SYSTEMSIZE
|
|
|
|
NTAPI
|
|
|
|
MmQuerySystemSize(VOID)
|
|
|
|
{
|
[NTOS]: Make MM init read MmProductType to determine what SKU of ReactOS this is, instead of assuming Server. If you want to go back to the old behavior, you need to change "WinNT" to "ServerNT" in the hivesys under Product Type.
[NTOS]: Configure the MmSystemSize variable properly based on SKU and RAM. Previously, ReactOS told all drivers and applications you were running on a system with < 13MB RAM.
[NTOS]: Initialize thresholds for low and high memory (in pages), low and high paged pool memory, and low and high nonpaged pool memory. These are described in the source.
[NTOS]: Initialize events for each of those thresholds, and populate the \KernelObject\xxxCondition events that are documented in MSDN for driver and app developers.
[NTOS]: Define some internal thresholds to use later, representing the minimum number of free pages under we go berserk, and the minimum number of free pages that we consider "plenty".
[NTOS]: Rename MiRemoveFromList to MiUnlinkFreeOrZeroedPage (Windows name). Make the function handle MmAvailablePages decrement, instead of having the caller do it.
[NTOS]: Remove run-time initialization of the PFN lists, just initialize them statically (also fixes the fact we forgot to initialize their names).
[NTOS]: Move some more initialization code to ARM3 instead of mm.
[NTOS]: Read ProductType from registry into MmProductType instead of dummy value. Remove duplicate "Mirroring" variable read.
svn path=/trunk/; revision=45638
2010-02-20 21:48:36 +00:00
|
|
|
/* Return the low, medium or high memory system type */
|
2009-10-15 17:01:31 +00:00
|
|
|
return MmSystemSize;
|
|
|
|
}
|
|
|
|
|
2015-09-08 20:14:39 +00:00
|
|
|
NTSTATUS
|
|
|
|
NTAPI
|
|
|
|
MmCreateMirror(VOID)
|
|
|
|
{
|
|
|
|
UNIMPLEMENTED;
|
2021-06-11 12:29:21 +00:00
|
|
|
return STATUS_NOT_IMPLEMENTED;
|
2015-09-08 20:14:39 +00:00
|
|
|
}
|
|
|
|
|
2009-10-15 17:01:31 +00:00
|
|
|
/* EOF */
|