1702{
1707#if (_MI_PAGING_LEVELS >= 3)
1709#if (_MI_PAGING_LEVELS == 4)
1711#endif
1712#endif
1718 ULONG ProtectionCode;
1725
1726
1728 {
1729#if (_MI_PAGING_LEVELS < 3)
1730
1733#endif
1734
1735 if (
1738#endif
1741#endif
1744 {
1745
1746 DbgPrint(
"MM:***PAGE FAULT AT IRQL > 1 Va %p, IRQL %lx\n",
1749 if (TrapInformation)
1750 {
1752#ifdef _M_IX86
1754 DbgPrint(
"MM:***EAX %p, ECX %p EDX %p\n", TrapFrame->
Eax, TrapFrame->
Ecx, TrapFrame->
Edx);
1755 DbgPrint(
"MM:***EBX %p, ESI %p EDI %p\n", TrapFrame->
Ebx, TrapFrame->
Esi, TrapFrame->
Edi);
1756#elif defined(_M_AMD64)
1758 DbgPrint(
"MM:***RAX %p, RCX %p RDX %p\n", TrapFrame->
Rax, TrapFrame->
Rcx, TrapFrame->
Rdx);
1759 DbgPrint(
"MM:***RBX %p, RSI %p RDI %p\n", TrapFrame->
Rbx, TrapFrame->
Rsi, TrapFrame->
Rdi);
1760#elif defined(_M_ARM)
1762 DbgPrint(
"MM:***R0 %p, R1 %p R2 %p, R3 %p\n", TrapFrame->
R0, TrapFrame->
R1, TrapFrame->
R2, TrapFrame->
R3);
1763 DbgPrint(
"MM:***R11 %p, R12 %p SP %p, LR %p\n", TrapFrame->
R11, TrapFrame->
R12, TrapFrame->
Sp, TrapFrame->
Lr);
1764#endif
1765 }
1766
1767
1769 }
1770
1771
1774
1775
1777 {
1778
1780 if (!(PointerPte->
u.
Long & PTE_READWRITE) &&
1782 {
1783
1788 10);
1789 }
1790 }
1791
1792
1795 }
1796
1797
1799 {
1800
1802
1803#if (_MI_PAGING_LEVELS == 2)
1806#endif
1807
1808
1809 if (
1811
1813#endif
1815
1817#endif
1818
1820 {
1821
1824 FaultCode,
1826 2);
1827 }
1828
1829
1831
1832
1835 {
1836
1837 if (!IsSessionAddress)
1838 {
1839
1843 {
1844
1846 {
1847
1849 if (!(PointerPte->
u.
Long & PTE_READWRITE) &&
1851 {
1852
1857 11);
1858 }
1859 }
1860
1861
1864 {
1869 1);
1870 }
1871 }
1872
1873
1876 }
1877 }
1878#if (_MI_PAGING_LEVELS == 2)
1879
1881 {
1882
1885 {
1886
1889 FaultCode,
1891 6);
1892 }
1893 }
1894#else
1895
1896_WARN(
"Session space stuff is not implemented yet!")
1897
1898#endif
1899
1900
1902 {
1903#if (_MI_PAGING_LEVELS < 3)
1904
1906#endif
1907
1908 goto UserFault;
1909 }
1910
1911
1913
1914
1915 if (!IsSessionAddress)
1916 {
1917
1919 CurrentProcess =
NULL;
1920
1921
1928 {
1929
1931 }
1932 }
1933 else
1934 {
1935
1938
1939
1942 {
1943
1945 }
1946 }
1947RetryKernel:
1948
1951
1952
1955 {
1956
1958 {
1959
1961 if (!(
TempPte.u.Long & PTE_READWRITE) &&
1964 {
1965
1966 ASSERT(!IsSessionAddress);
1967
1968
1973 12);
1974 }
1975 }
1976
1977
1980 {
1985 2);
1986 }
1987
1988
1989 if ((IsSessionAddress) &&
1992 {
1993
1995
1996
1998 {
1999
2004 13);
2005 }
2006
2007
2009 }
2010
2011
2014
2015
2017 }
2018
2019
2021 {
2022
2029 {
2030
2033 FaultCode,
2035 4);
2036 }
2037
2038
2040
2041
2042 if ((IsSessionAddress) &&
2044 {
2045
2047 &ProtectionCode,
2048 &Vad);
2050 }
2051 }
2052 else
2053 {
2054
2056
2057
2059 {
2060
2063 FaultCode,
2065 1);
2066 }
2067
2068
2070 {
2071
2074 FaultCode,
2076 0);
2077 }
2078 }
2079
2080
2082 !(ProtoPte) &&
2083 !(IsSessionAddress) &&
2085 {
2086
2089 {
2090
2095 14);
2096 }
2097 }
2098
2099
2102 PointerPte,
2103 ProtoPte,
2105 CurrentProcess,
2106 TrapInformation,
2108
2109
2113
2115 {
2117 goto RetryKernel;
2118 }
2119
2120
2123 }
2124
2125
2126UserFault:
2129
2130
2132
2134
2135#if (_MI_PAGING_LEVELS == 4)
2136
2138 {
2139
2141
2142
2144
2145
2148 {
2151 }
2152
2153
2155 PointerPxe,
2157 CurrentProcess,
2160 {
2161 goto ExitUser;
2162 }
2163
2164
2166 }
2167#endif
2168
2169#if (_MI_PAGING_LEVELS >= 3)
2170
2172 {
2173
2175
2176
2178
2179
2181 {
2183 }
2184
2186 {
2189 }
2190
2191
2193 PointerPpe,
2195 CurrentProcess,
2198 {
2199 goto ExitUser;
2200 }
2201
2202
2205 }
2206#endif
2207
2208
2210 {
2211
2213
2214
2215#if MI_TRACE_PFNS
2216 UserPdeFault =
TRUE;
2217#endif
2218
2220 {
2222 }
2223
2225 {
2226#if (_MI_PAGING_LEVELS == 2)
2227
2229#endif
2230
2232
2233
2236 }
2237
2238
2240 PointerPde,
2242 CurrentProcess,
2245 {
2246 goto ExitUser;
2247 }
2248
2249#if _MI_PAGING_LEVELS >= 3
2251#endif
2252
2253#if MI_TRACE_PFNS
2254 UserPdeFault =
FALSE;
2255
2256 if (TrapInformation)
2258 else
2260#endif
2261
2264 }
2265 else
2266 {
2267
2269 }
2270
2271
2273
2274
2276 {
2277
2279 {
2280
2282 {
2283 PFN_NUMBER PageFrameIndex, OldPageFrameIndex;
2285
2286 LockIrql = MiAcquirePfnLock();
2287
2289
2292
2293
2295 if (PageFrameIndex == 0)
2296 {
2297 MiReleasePfnLock(LockIrql);
2299 goto ExitUser;
2300 }
2302
2303 MiCopyPfn(PageFrameIndex, OldPageFrameIndex);
2304
2305
2311
2312
2316 TempPte.u.Hard.CopyOnWrite = 0;
2317
2319
2320 MiReleasePfnLock(LockIrql);
2321
2322
2325 }
2326
2327
2329 {
2330
2333 }
2334 }
2335
2336#if _MI_HAS_NO_EXECUTE
2337
2340 {
2341
2343 {
2344
2349 }
2350
2351
2354 }
2355#endif
2356
2357
2360 }
2361
2362
2365 {
2366
2368 PointerPte,
2370 CurrentProcess,
2373 {
2374 goto ExitUser;
2375 }
2376
2377#if MI_TRACE_PFNS
2378
2379 if (TrapInformation)
2381 else
2383#endif
2384
2385
2388 }
2389
2390
2392 {
2393
2396 {
2397#if (_MI_PAGING_LEVELS == 2)
2398
2400#endif
2401
2403
2404
2407 }
2408
2409
2410
2411
2412
2418#endif
2419#endif
2420 )
2421 {
2422
2424 }
2425
2426
2428 {
2429
2431
2432
2433 TempPte.u.Soft.Protection = ProtectionCode & ~MM_GUARDPAGE;
2435
2436
2438 ASSERT(CurrentThread->ApcNeeded == 0);
2439
2440
2443
2444
2446 }
2447
2448
2449 if (!ProtoPte)
2450 {
2451
2453 {
2454
2455#ifdef _M_ARM
2456 _WARN(
"This is probably completely broken!");
2458#else
2460#endif
2461 }
2462 else
2463 {
2464
2465 TempPte.u.Soft.Protection = ProtectionCode;
2467 }
2468
2469
2471
2472
2473
2474
2475
2480 if (!PageFrameIndex)
2481 {
2482
2484
2485
2487
2488 if (PageFrameIndex == 0)
2489 {
2491 goto ExitUser;
2492 }
2493
2494
2496
2497
2499 }
2500
2501
2503
2504
2506
2507
2509
2510
2512
2513
2515 {
2516
2518 PointerPte,
2520 PageFrameIndex);
2521 }
2522 else
2523 {
2524
2526 PointerPte,
2528 PageFrameIndex);
2529 }
2530
2531
2533
2534
2538
2539
2543 }
2544
2545
2546 ASSERT(ProtectionCode != 0x100);
2547
2548
2550 TempPte.u.Soft.Protection = ProtectionCode;
2553 }
2554 else
2555 {
2556
2559 {
2560
2562 {
2563
2565 &ProtectionCode,
2566 &Vad);
2567 if (!ProtoPte)
2568 {
2572 }
2573 }
2574 else
2575 {
2576
2578
2579
2581 {
2582
2584 }
2585 else
2586 {
2587
2588 ProtectionCode = 0x100;
2590 }
2591 }
2592 }
2593 }
2594
2595
2596 if (ProtectionCode != 0x100)
2597 {
2598
2602 ProtectionCode,
2603 TrapInformation,
2606 {
2607
2608 ASSERT(CurrentThread->ApcNeeded == 0);
2609
2610
2613
2614
2616 {
2617
2619 }
2620
2621
2623 }
2624 }
2625
2626
2629 PointerPte,
2630 ProtoPte,
2632 CurrentProcess,
2633 TrapInformation,
2634 Vad);
2635
2636ExitUser:
2637
2638
2641
2643 {
2645 goto UserFault;
2646 }
2647
2649}
#define KeRaiseIrql(irql, oldIrql)
#define KeLowerIrql(oldIrql)
#define MI_IS_SYSTEM_PAGE_TABLE_ADDRESS(Address)
FORCEINLINE VOID MiLockWorkingSet(IN PETHREAD Thread, IN PMMSUPPORT WorkingSet)
BOOLEAN MmProtectFreedNonPagedPool
FORCEINLINE BOOLEAN MiIsUserPte(PVOID Address)
#define MI_IS_SESSION_PTE(Pte)
#define MM_INVALID_PROTECTION
FORCEINLINE VOID MiUnlockProcessWorkingSet(IN PEPROCESS Process, IN PETHREAD Thread)
FORCEINLINE VOID MiUnlockWorkingSet(IN PETHREAD Thread, IN PMMSUPPORT WorkingSet)
FORCEINLINE VOID MI_WRITE_INVALID_PDE(IN PMMPDE PointerPde, IN MMPDE InvalidPde)
FORCEINLINE BOOLEAN MiIsUserPde(PVOID Address)
FORCEINLINE VOID MI_UPDATE_VALID_PTE(IN PMMPTE PointerPte, IN MMPTE TempPte)
#define MI_IS_PFN_DELETED(x)
#define MI_IS_PAGE_TABLE_OR_HYPER_ADDRESS(Address)
FORCEINLINE USHORT MiIncrementPageTableReferences(IN PVOID Address)
FORCEINLINE VOID MiLockProcessWorkingSet(IN PEPROCESS Process, IN PETHREAD Thread)
#define MiAddressToPde(x)
struct _EPROCESS * PEPROCESS
#define MI_IS_PAGE_EXECUTABLE(x)
#define MI_IS_WRITE_ACCESS(FaultCode)
#define MM_PTE_SOFTWARE_PROTECTION_BITS
#define MI_IS_INSTRUCTION_FETCH(FaultCode)
#define _MI_PAGING_LEVELS
FORCEINLINE PMMPTE MiAddressToPpe(PVOID Address)
#define MiProtoPteToPte(x)
FORCEINLINE PMMPTE MiAddressToPxe(PVOID Address)
#define MI_IS_PAGE_LARGE(x)
ULONG MmSizeOfNonPagedPoolInBytes
PVOID MmNonPagedPoolExpansionStart
MMSUPPORT MmSystemCacheWs
PVOID MmNonPagedPoolStart
#define STATUS_PAGE_FAULT_COPY_ON_WRITE
#define STATUS_IN_PAGE_ERROR
static PMMPTE NTAPI MiCheckVirtualAddress(IN PVOID VirtualAddress, OUT PULONG ProtectCode, OUT PMMVAD *ProtoVad)
VOID NTAPI MmRebalanceMemoryConsumersAndWait(VOID)
NTSTATUS FASTCALL MiCheckPdeForPagedPool(IN PVOID Address)
static NTSTATUS NTAPI MiCheckForUserStackOverflow(IN PVOID Address, IN PVOID TrapInformation)
NTSTATUS NTAPI MiDispatchFault(IN ULONG FaultCode, IN PVOID Address, IN PMMPTE PointerPte, IN PMMPTE PointerProtoPte, IN BOOLEAN Recursive, IN PEPROCESS Process, IN PVOID TrapInformation, IN PMMVAD Vad)
VOID NTAPI KeBugCheckEx(_In_ ULONG BugCheckCode, _In_ ULONG_PTR BugCheckParameter1, _In_ ULONG_PTR BugCheckParameter2, _In_ ULONG_PTR BugCheckParameter3, _In_ ULONG_PTR BugCheckParameter4)
PFN_NUMBER NumberOfPrivatePages
ULONG OwnsSessionWorkingSetExclusive
ULONG OwnsSessionWorkingSetShared
ULONG OwnsSystemWorkingSetShared
ULONG OwnsProcessWorkingSetShared
ULONG OwnsProcessWorkingSetExclusive
ULONG OwnsSystemWorkingSetExclusive
struct _MM_SESSION_SPACE * GlobalVirtualAddress