1 #ifndef __INCLUDE_INTERNAL_MM_H
2 #define __INCLUDE_INTERNAL_MM_H
4 #include <internal/arch/mm.h>
6 /* TYPES *********************************************************************/
10 extern ULONG MiFreeSwapPages
;
11 extern ULONG MiUsedSwapPages
;
12 extern ULONG MmPagedPoolSize
;
13 extern ULONG MmTotalPagedPoolQuota
;
14 extern ULONG MmTotalNonPagedPoolQuota
;
15 extern PHYSICAL_ADDRESS MmSharedDataPagePhysicalAddress
;
17 extern PVOID MmPagedPoolBase
;
18 extern ULONG MmPagedPoolSize
;
22 struct _MM_RMAP_ENTRY
;
24 typedef ULONG SWAPENTRY
;
25 typedef ULONG PFN_TYPE
, *PPFN_TYPE
;
27 #define MEMORY_AREA_INVALID (0)
28 #define MEMORY_AREA_SECTION_VIEW (1)
29 #define MEMORY_AREA_CONTINUOUS_MEMORY (2)
30 #define MEMORY_AREA_NO_CACHE (3)
31 #define MEMORY_AREA_IO_MAPPING (4)
32 #define MEMORY_AREA_SYSTEM (5)
33 #define MEMORY_AREA_MDL_MAPPING (7)
34 #define MEMORY_AREA_VIRTUAL_MEMORY (8)
35 #define MEMORY_AREA_CACHE_SEGMENT (9)
36 #define MEMORY_AREA_SHARED_DATA (10)
37 #define MEMORY_AREA_KERNEL_STACK (11)
38 #define MEMORY_AREA_PAGED_POOL (12)
39 #define MEMORY_AREA_NO_ACCESS (13)
40 #define MEMORY_AREA_PEB_OR_TEB (14)
42 #define MM_PHYSICAL_PAGE_MPW_PENDING (0x8)
44 #define MM_CORE_DUMP_TYPE_NONE (0x0)
45 #define MM_CORE_DUMP_TYPE_MINIMAL (0x1)
46 #define MM_CORE_DUMP_TYPE_FULL (0x2)
48 #define MM_PAGEOP_PAGEIN (1)
49 #define MM_PAGEOP_PAGEOUT (2)
50 #define MM_PAGEOP_PAGESYNCH (3)
51 #define MM_PAGEOP_ACCESSFAULT (4)
53 #define PAGE_TO_SECTION_PAGE_DIRECTORY_OFFSET(x) \
56 #define PAGE_TO_SECTION_PAGE_TABLE_OFFSET(x) \
57 ((((x)) % (4*1024*1024)) / (4*1024))
59 #define NR_SECTION_PAGE_TABLES 1024
60 #define NR_SECTION_PAGE_ENTRIES 1024
62 #define TEB_BASE 0x7FFDE000
63 #define KPCR_BASE 0xFF000000
65 /* Although Microsoft says this isn't hardcoded anymore,
66 they won't be able to change it. Stuff depends on it */
67 #define MM_VIRTMEM_GRANULARITY (64 * 1024)
69 #define STATUS_MM_RESTART_OPERATION ((NTSTATUS)0xD0000001)
72 * Additional flags for protection attributes
74 #define PAGE_WRITETHROUGH (1024)
75 #define PAGE_SYSTEM (2048)
77 #define SEC_PHYSICALMEMORY (0x80000000)
79 #define MM_PAGEFILE_SEGMENT (0x1)
80 #define MM_DATAFILE_SEGMENT (0x2)
86 #define MC_MAXIMUM (4)
88 #define PAGED_POOL_MASK 1
89 #define MUST_SUCCEED_POOL_MASK 2
90 #define CACHE_ALIGNED_POOL_MASK 4
91 #define QUOTA_POOL_MASK 8
92 #define SESSION_POOL_MASK 32
93 #define VERIFIER_POOL_MASK 64
95 #define MM_PAGED_POOL_SIZE (100*1024*1024)
96 #define MM_NONPAGED_POOL_SIZE (100*1024*1024)
99 * Paged and non-paged pools are 8-byte aligned
101 #define MM_POOL_ALIGNMENT 8
104 * Maximum size of the kmalloc area (this is totally arbitary)
106 #define MM_KERNEL_MAP_SIZE (16*1024*1024)
107 #define MM_KERNEL_MAP_BASE (0xf0c00000)
110 * FIXME - different architectures have different cache line sizes...
112 #define MM_CACHE_LINE_SIZE 32
114 #define MM_ROUND_UP(x,s) \
115 ((PVOID)(((ULONG_PTR)(x)+(s)-1) & ~((ULONG_PTR)(s)-1)))
117 #define MM_ROUND_DOWN(x,s) \
118 ((PVOID)(((ULONG_PTR)(x)) & ~((ULONG_PTR)(s)-1)))
120 #define PAGE_FLAGS_VALID_FROM_USER_MODE \
125 PAGE_EXECUTE_READ | \
126 PAGE_EXECUTE_READWRITE | \
127 PAGE_EXECUTE_WRITECOPY | \
132 #define PAGE_IS_READABLE \
136 PAGE_EXECUTE_READ | \
137 PAGE_EXECUTE_READWRITE | \
138 PAGE_EXECUTE_WRITECOPY)
140 #define PAGE_IS_WRITABLE \
143 PAGE_EXECUTE_READWRITE | \
144 PAGE_EXECUTE_WRITECOPY)
146 #define PAGE_IS_EXECUTABLE \
148 PAGE_EXECUTE_READ | \
149 PAGE_EXECUTE_READWRITE | \
150 PAGE_EXECUTE_WRITECOPY)
152 #define PAGE_IS_WRITECOPY \
154 PAGE_EXECUTE_WRITECOPY)
158 ULONG Entry
[NR_SECTION_PAGE_ENTRIES
];
159 } SECTION_PAGE_TABLE
, *PSECTION_PAGE_TABLE
;
163 PSECTION_PAGE_TABLE PageTables
[NR_SECTION_PAGE_TABLES
];
164 } SECTION_PAGE_DIRECTORY
, *PSECTION_PAGE_DIRECTORY
;
166 typedef struct _MM_SECTION_SEGMENT
168 LONGLONG FileOffset
; /* start offset into the file for image sections */
169 ULONG_PTR VirtualAddress
; /* dtart offset into the address range for image sections */
170 ULONG RawLength
; /* length of the segment which is part of the mapped file */
171 ULONG Length
; /* absolute length of the segment */
173 FAST_MUTEX Lock
; /* lock which protects the page directory */
174 ULONG ReferenceCount
;
175 SECTION_PAGE_DIRECTORY PageDirectory
;
177 ULONG Characteristics
;
179 } MM_SECTION_SEGMENT
, *PMM_SECTION_SEGMENT
;
181 typedef struct _MM_IMAGE_SECTION_OBJECT
184 ULONG_PTR StackReserve
;
185 ULONG_PTR StackCommit
;
186 ULONG_PTR EntryPoint
;
188 ULONG ImageCharacteristics
;
189 USHORT MinorSubsystemVersion
;
190 USHORT MajorSubsystemVersion
;
194 PMM_SECTION_SEGMENT Segments
;
195 } MM_IMAGE_SECTION_OBJECT
, *PMM_IMAGE_SECTION_OBJECT
;
197 typedef struct _ROS_SECTION_OBJECT
201 LARGE_INTEGER MaximumSize
;
202 ULONG SectionPageProtection
;
203 ULONG AllocationAttributes
;
204 PFILE_OBJECT FileObject
;
207 PMM_IMAGE_SECTION_OBJECT ImageSection
;
208 PMM_SECTION_SEGMENT Segment
;
210 } ROS_SECTION_OBJECT
, *PROS_SECTION_OBJECT
;
212 typedef struct _MEMORY_AREA
214 PVOID StartingAddress
;
216 struct _MEMORY_AREA
*Parent
;
217 struct _MEMORY_AREA
*LeftChild
;
218 struct _MEMORY_AREA
*RightChild
;
222 BOOLEAN DeleteInProgress
;
228 ROS_SECTION_OBJECT
* Section
;
230 PMM_SECTION_SEGMENT Segment
;
231 BOOLEAN WriteCopyView
;
232 LIST_ENTRY RegionListHead
;
236 LIST_ENTRY RegionListHead
;
239 } MEMORY_AREA
, *PMEMORY_AREA
;
241 typedef struct _MADDRESS_SPACE
243 PMEMORY_AREA MemoryAreaRoot
;
245 struct _EPROCESS
* Process
;
246 PUSHORT PageTableRefCountTable
;
247 ULONG PageTableRefCountTableSize
;
248 } MADDRESS_SPACE
, *PMADDRESS_SPACE
;
254 ULONG NrReservedPages
;
259 ULONG PagingRequestsInLastMinute
;
260 ULONG PagingRequestsInLastFiveMinutes
;
261 ULONG PagingRequestsInLastFifteenMinutes
;
264 extern MM_STATS MmStats
;
266 typedef struct _MM_PAGEOP
268 /* Type of operation. */
270 /* Number of threads interested in this operation. */
271 ULONG ReferenceCount
;
272 /* Event that will be set when the operation is completed. */
273 KEVENT CompletionEvent
;
274 /* Status of the operation once it is completed. */
276 /* TRUE if the operation was abandoned. */
278 /* The memory area to be affected by the operation. */
281 struct _MM_PAGEOP
* Next
;
282 struct _ETHREAD
* Thread
;
284 * These fields are used to identify the operation if it is against a
285 * virtual memory area.
290 * These fields are used to identify the operation if it is against a
293 PMM_SECTION_SEGMENT Segment
;
295 } MM_PAGEOP
, *PMM_PAGEOP
;
297 typedef struct _MM_MEMORY_CONSUMER
301 NTSTATUS (*Trim
)(ULONG Target
, ULONG Priority
, PULONG NrFreed
);
302 } MM_MEMORY_CONSUMER
, *PMM_MEMORY_CONSUMER
;
304 typedef struct _MM_REGION
309 LIST_ENTRY RegionListEntry
;
310 } MM_REGION
, *PMM_REGION
;
312 extern MM_MEMORY_CONSUMER MiMemoryConsumers
[MC_MAXIMUM
];
315 (*PMM_ALTER_REGION_FUNC
)(
316 PMADDRESS_SPACE AddressSpace
,
326 (*PMM_FREE_PAGE_FUNC
)(
328 PMEMORY_AREA MemoryArea
,
338 /* aspace.c ******************************************************************/
342 MmLockAddressSpace(PMADDRESS_SPACE AddressSpace
);
346 MmUnlockAddressSpace(PMADDRESS_SPACE AddressSpace
);
350 MmInitializeKernelAddressSpace(VOID
);
354 MmGetCurrentAddressSpace(VOID
);
358 MmGetKernelAddressSpace(VOID
);
362 MmInitializeAddressSpace(
363 struct _EPROCESS
* Process
,
364 PMADDRESS_SPACE AddressSpace
);
368 MmDestroyAddressSpace(PMADDRESS_SPACE AddressSpace
);
370 /* marea.c *******************************************************************/
374 MmInitMemoryAreas(VOID
);
379 PMADDRESS_SPACE AddressSpace
,
384 PMEMORY_AREA
*Result
,
385 BOOLEAN FixedAddress
,
386 ULONG AllocationFlags
,
387 PHYSICAL_ADDRESS BoundaryAddressMultiple OPTIONAL
392 MmLocateMemoryAreaByAddress(
393 PMADDRESS_SPACE AddressSpace
,
400 PMADDRESS_SPACE AddressSpace
,
407 PMADDRESS_SPACE AddressSpace
,
408 PMEMORY_AREA MemoryArea
,
409 PMM_FREE_PAGE_FUNC FreePage
,
410 PVOID FreePageContext
415 MmFreeMemoryAreaByPtr(
416 PMADDRESS_SPACE AddressSpace
,
418 PMM_FREE_PAGE_FUNC FreePage
,
419 PVOID FreePageContext
424 MmDumpMemoryAreas(PMADDRESS_SPACE AddressSpace
);
428 MmLocateMemoryAreaByRegion(
429 PMADDRESS_SPACE AddressSpace
,
437 PMADDRESS_SPACE AddressSpace
,
439 ULONG_PTR Granularity
,
445 MmReleaseMemoryAreaIfDecommitted(
446 struct _EPROCESS
*Process
,
447 PMADDRESS_SPACE AddressSpace
,
451 /* npool.c *******************************************************************/
455 MiDebugDumpNonPagedPool(BOOLEAN NewOnly
);
459 MiDebugDumpNonPagedPoolStats(BOOLEAN NewOnly
);
463 MiInitializeNonPagedPool(VOID
);
472 /* pool.c *******************************************************************/
476 ExAllocateNonPagedPoolWithTag(
485 ExAllocatePagedPoolWithTag(
493 ExFreeNonPagedPool(PVOID block
);
497 ExFreePagedPool(IN PVOID Block
);
501 MmInitializePagedPool(VOID
);
505 MiAllocateSpecialPool(
506 IN POOL_TYPE PoolType
,
507 IN SIZE_T NumberOfBytes
,
515 IN POOL_TYPE PoolType
,
516 IN ULONG CurrentMaxQuota
,
517 OUT PULONG NewMaxQuota
520 /* mdl.c *********************************************************************/
529 /* mminit.c ******************************************************************/
533 MiShutdownMemoryManager(VOID
);
538 ULONG_PTR FirstKernelPhysAddress
,
539 ULONG_PTR LastKernelPhysAddress
,
540 ULONG_PTR LastKernelAddress
,
541 PADDRESS_RANGE BIOSMemoryMap
,
542 ULONG AddressRangeCount
,
556 MiFreeInitMemory(VOID
);
560 MmInitializeMdlImplementation(VOID
);
562 /* pagefile.c ****************************************************************/
566 MmAllocSwapPage(VOID
);
570 MmDereserveSwapPages(ULONG Nr
);
574 MmFreeSwapPage(SWAPENTRY Entry
);
578 MmInitPagingFile(VOID
);
589 MmReserveSwapPages(ULONG Nr
);
602 ULONG BugCodeParameter1
,
603 ULONG BugCodeParameter2
,
604 ULONG BugCodeParameter3
,
605 ULONG BugCodeParameter4
,
606 struct _KTRAP_FRAME
* TrapFrame
611 MmIsAvailableSwapPage(VOID
);
615 MmShowOutOfSpaceMessagePagingFile(VOID
);
617 /* process.c ****************************************************************/
621 MmCreateProcessAddressSpace(
622 IN PEPROCESS Process
,
623 IN PROS_SECTION_OBJECT Section OPTIONAL
,
624 IN POBJECT_NAME_INFORMATION
*AuditName OPTIONAL
629 MmCreatePeb(struct _EPROCESS
*Process
);
634 struct _EPROCESS
*Process
,
636 PINITIAL_TEB InitialTeb
642 struct _EPROCESS
*Process
,
648 MmCleanProcessAddressSpace(IN PEPROCESS Process
);
652 MmDeleteProcessAddressSpace(IN PEPROCESS Process
);
656 MmGetSessionLocaleId(VOID
);
660 MmSetMemoryPriorityProcess(
661 IN PEPROCESS Process
,
662 IN UCHAR MemoryPriority
665 /* i386/pfault.c *************************************************************/
677 /* mm.c **********************************************************************/
682 KPROCESSOR_MODE Mode
,
690 KPROCESSOR_MODE Mode
,
695 /* anonmem.c *****************************************************************/
699 MmNotPresentFaultVirtualMemory(
700 PMADDRESS_SPACE AddressSpace
,
701 MEMORY_AREA
* MemoryArea
,
708 MmPageOutVirtualMemory(
709 PMADDRESS_SPACE AddressSpace
,
710 PMEMORY_AREA MemoryArea
,
712 struct _MM_PAGEOP
* PageOp
718 PMEMORY_AREA MemoryArea
,
720 PMEMORY_BASIC_INFORMATION Info
,
727 struct _EPROCESS
* Process
,
728 PMEMORY_AREA MemoryArea
734 PMADDRESS_SPACE AddressSpace
,
735 PMEMORY_AREA MemoryArea
,
744 MmWritePageVirtualMemory(
745 PMADDRESS_SPACE AddressSpace
,
751 /* kmap.c ********************************************************************/
755 ExAllocatePage(VOID
);
759 ExUnmapPage(PVOID Addr
);
763 ExAllocatePageWithPhysPage(PFN_TYPE Page
);
774 MiZeroPage(PFN_TYPE Page
);
776 /* memsafe.s *****************************************************************/
780 MmSafeReadPtr(PVOID Source
);
782 /* pageop.c ******************************************************************/
786 MmReleasePageOp(PMM_PAGEOP PageOp
);
794 PMM_SECTION_SEGMENT Segment
,
806 PMM_SECTION_SEGMENT Segment
,
812 MmInitializePageOp(VOID
);
814 /* process.c *****************************************************************/
818 MmCreateKernelStack(BOOLEAN GuiStack
);
822 MmDeleteKernelStack(PVOID Stack
,
825 /* balace.c ******************************************************************/
829 MmInitializeMemoryConsumer(
831 NTSTATUS (*Trim
)(ULONG Target
, ULONG Priority
, PULONG NrFreed
)
836 MmInitializeBalancer(
837 ULONG NrAvailablePages
,
843 MmReleasePageMemoryConsumer(
850 MmRequestPageMemoryConsumer(
853 PPFN_TYPE AllocatedPage
858 MiInitBalancerThread(VOID
);
862 MmRebalanceMemoryConsumers(VOID
);
864 /* rmap.c **************************************************************/
868 MmSetRmapListHeadPage(
870 struct _MM_RMAP_ENTRY
* ListHead
873 struct _MM_RMAP_ENTRY
*
875 MmGetRmapListHeadPage(PFN_TYPE Page
);
881 struct _EPROCESS
*Process
,
890 VOID (*DeleteMapping
)(PVOID Context
, struct _EPROCESS
*Process
, PVOID Address
)
897 struct _EPROCESS
*Process
,
903 MmInitializeRmapList(VOID
);
907 MmSetCleanAllRmaps(PFN_TYPE Page
);
911 MmSetDirtyAllRmaps(PFN_TYPE Page
);
915 MmIsDirtyPageRmap(PFN_TYPE Page
);
919 MmWritePagePhysicalAddress(PFN_TYPE Page
);
923 MmPageOutPhysicalAddress(PFN_TYPE Page
);
925 /* freelist.c **********************************************************/
929 MmGetLRUNextUserPage(PFN_TYPE PreviousPage
);
933 MmGetLRUFirstUserPage(VOID
);
937 MmSetLRULastPage(PFN_TYPE Page
);
941 MmLockPage(PFN_TYPE Page
);
945 MmLockPageUnsafe(PFN_TYPE Page
);
949 MmUnlockPage(PFN_TYPE Page
);
953 MmGetLockCountPage(PFN_TYPE Page
);
957 MmInitializePageList(
958 ULONG_PTR FirstPhysKernelAddress
,
959 ULONG_PTR LastPhysKernelAddress
,
960 ULONG MemorySizeInPages
,
961 ULONG_PTR LastKernelBase
,
962 PADDRESS_RANGE BIOSMemoryMap
,
963 ULONG AddressRangeCount
968 MmGetContinuousPages(
970 PHYSICAL_ADDRESS LowestAcceptableAddress
,
971 PHYSICAL_ADDRESS HighestAcceptableAddress
,
972 PHYSICAL_ADDRESS BoundaryAddressMultiple
977 MmZeroPageThreadMain(
981 /* i386/page.c *********************************************************/
985 MmCreateHyperspaceMapping(PFN_TYPE Page
);
989 MmChangeHyperspaceMapping(
996 MmDeleteHyperspaceMapping(PVOID Address
);
1000 MmCreateVirtualMappingForKernel(
1009 MmCommitPagedPoolAddress(
1016 MmCreateVirtualMapping(
1017 struct _EPROCESS
* Process
,
1026 MmCreateVirtualMappingUnsafe(
1027 struct _EPROCESS
* Process
,
1037 struct _EPROCESS
* Process
,
1043 struct _EPROCESS
* Process
,
1051 struct _EPROCESS
* Process
,
1057 MmInitGlobalKernelPageDirectory(VOID
);
1061 MmDisableVirtualMapping(
1062 struct _EPROCESS
*Process
,
1070 MmEnableVirtualMapping(
1071 struct _EPROCESS
*Process
,
1077 MmRawDeleteVirtualMapping(PVOID Address
);
1081 MmDeletePageFileMapping(
1082 struct _EPROCESS
*Process
,
1084 SWAPENTRY
* SwapEntry
1089 MmCreatePageFileMapping(
1090 struct _EPROCESS
*Process
,
1098 struct _EPROCESS
*Process
,
1104 MmTransferOwnershipPage(
1112 struct _EPROCESS
*Process
,
1120 SWAPENTRY SavedSwapEntry
1125 MmAllocPagesSpecifyRange(
1127 PHYSICAL_ADDRESS LowestAddress
,
1128 PHYSICAL_ADDRESS HighestAddress
,
1129 ULONG NumberOfPages
,
1135 MmDereferencePage(PFN_TYPE Page
);
1139 MmReferencePage(PFN_TYPE Page
);
1143 MmReferencePageUnsafe(PFN_TYPE Page
);
1147 MmIsAccessedAndResetAccessPage(
1148 struct _EPROCESS
*Process
,
1154 MmGetReferenceCountPage(PFN_TYPE Page
);
1158 MmIsUsablePage(PFN_TYPE Page
);
1168 MmGetFlagsPage(PFN_TYPE Page
);
1172 MmSetSavedSwapEntryPage(
1174 SWAPENTRY SavedSwapEntry
);
1178 MmGetSavedSwapEntryPage(PFN_TYPE Page
);
1183 struct _EPROCESS
*Process
,
1189 MmCreatePageTable(PVOID PAddress
);
1194 struct _EPROCESS
*Process
,
1201 struct _EPROCESS
*Process
,
1208 struct _EPROCESS
*Src
,
1209 struct _EPROCESS
*Dest
,
1210 PPHYSICAL_ADDRESS DirectoryTableBase
1215 MmReleaseMmInfo(struct _EPROCESS
*Process
);
1219 Mmi386ReleaseMmInfo(struct _EPROCESS
*Process
);
1223 MmDeleteVirtualMapping(
1224 struct _EPROCESS
*Process
,
1234 struct _EPROCESS
*Process
,
1240 MmMarkPageMapped(PFN_TYPE Page
);
1244 MmMarkPageUnmapped(PFN_TYPE Page
);
1249 struct _EPROCESS
*Process
,
1256 MiInitPageDirectoryMap(VOID
);
1260 MiGetUserPageDirectoryCount(VOID
);
1262 /* wset.c ********************************************************************/
1271 /* region.c ************************************************************/
1276 PMADDRESS_SPACE AddressSpace
,
1278 PLIST_ENTRY RegionListHead
,
1283 PMM_ALTER_REGION_FUNC AlterFunc
1289 PLIST_ENTRY RegionListHead
,
1299 PLIST_ENTRY RegionListHead
,
1301 PVOID
* RegionBaseAddress
1304 /* section.c *****************************************************************/
1308 MmGetFileObjectForSection(
1309 IN PROS_SECTION_OBJECT Section
1322 PMEMORY_AREA MemoryArea
,
1324 PMEMORY_BASIC_INFORMATION Info
,
1330 MmProtectSectionView(
1331 PMADDRESS_SPACE AddressSpace
,
1332 PMEMORY_AREA MemoryArea
,
1341 MmWritePageSectionView(
1342 PMADDRESS_SPACE AddressSpace
,
1350 MmInitSectionImplementation(VOID
);
1354 MmNotPresentFaultSectionView(
1355 PMADDRESS_SPACE AddressSpace
,
1356 MEMORY_AREA
* MemoryArea
,
1363 MmPageOutSectionView(
1364 PMADDRESS_SPACE AddressSpace
,
1365 PMEMORY_AREA MemoryArea
,
1367 struct _MM_PAGEOP
*PageOp
1372 MmCreatePhysicalMemorySection(VOID
);
1376 MmAccessFaultSectionView(
1377 PMADDRESS_SPACE AddressSpace
,
1378 MEMORY_AREA
* MemoryArea
,
1385 MmFreeSectionSegments(PFILE_OBJECT FileObject
);
1387 /* mpw.c *********************************************************************/
1391 MmInitMpwThread(VOID
);
1393 /* pager.c *******************************************************************/
1397 MiIsPagerThread(VOID
);
1401 MiStartPagerThread(VOID
);
1405 MiStopPagerThread(VOID
);
1409 MiQueryVirtualMemory(
1410 IN HANDLE ProcessHandle
,
1412 IN MEMORY_INFORMATION_CLASS VirtualMemoryInformationClass
,
1413 OUT PVOID VirtualMemoryInformation
,
1415 OUT PULONG ResultLength