1718{
1723#if (_MI_PAGING_LEVELS >= 3)
1725#if (_MI_PAGING_LEVELS == 4)
1727#endif
1728#endif
1734 ULONG ProtectionCode;
1741
1742
1744 {
1745#if (_MI_PAGING_LEVELS < 3)
1746
1749#endif
1750
1751 if (
1754#endif
1757#endif
1760 {
1761
1762 DbgPrint(
"MM:***PAGE FAULT AT IRQL > 1 Va %p, IRQL %lx\n",
1765 if (TrapInformation)
1766 {
1768#ifdef _M_IX86
1770 DbgPrint(
"MM:***EAX %p, ECX %p EDX %p\n", TrapFrame->
Eax, TrapFrame->
Ecx, TrapFrame->
Edx);
1771 DbgPrint(
"MM:***EBX %p, ESI %p EDI %p\n", TrapFrame->
Ebx, TrapFrame->
Esi, TrapFrame->
Edi);
1772#elif defined(_M_AMD64)
1774 DbgPrint(
"MM:***RAX %p, RCX %p RDX %p\n", TrapFrame->
Rax, TrapFrame->
Rcx, TrapFrame->
Rdx);
1775 DbgPrint(
"MM:***RBX %p, RSI %p RDI %p\n", TrapFrame->
Rbx, TrapFrame->
Rsi, TrapFrame->
Rdi);
1776#elif defined(_M_ARM)
1778 DbgPrint(
"MM:***R0 %p, R1 %p R2 %p, R3 %p\n", TrapFrame->
R0, TrapFrame->
R1, TrapFrame->
R2, TrapFrame->
R3);
1779 DbgPrint(
"MM:***R11 %p, R12 %p SP %p, LR %p\n", TrapFrame->
R11, TrapFrame->
R12, TrapFrame->
Sp, TrapFrame->
Lr);
1780#endif
1781 }
1782
1783
1785 }
1786
1787
1790
1791
1793 {
1794
1796 if (!(PointerPte->
u.
Long & PTE_READWRITE) &&
1798 {
1799
1804 10);
1805 }
1806 }
1807
1808
1811 }
1812
1813
1815 {
1816
1818
1819#if (_MI_PAGING_LEVELS == 2)
1822#endif
1823
1824
1825 if (
1827
1829#endif
1831
1833#endif
1834
1836 {
1837
1840 FaultCode,
1842 2);
1843 }
1844
1845
1847
1848
1851 {
1852
1853 if (!IsSessionAddress)
1854 {
1855
1859 {
1860
1862 {
1863
1865 if (!(PointerPte->
u.
Long & PTE_READWRITE) &&
1867 {
1868
1873 11);
1874 }
1875 }
1876
1877
1880 {
1885 1);
1886 }
1887 }
1888
1889
1892 }
1893 }
1894#if (_MI_PAGING_LEVELS == 2)
1895
1897 {
1898
1901 {
1902
1905 FaultCode,
1907 6);
1908 }
1909 }
1910#else
1911
1912_WARN(
"Session space stuff is not implemented yet!")
1913
1914#endif
1915
1916
1918 {
1919#if (_MI_PAGING_LEVELS < 3)
1920
1922#endif
1923
1924 goto UserFault;
1925 }
1926
1927
1929
1930
1931 if (!IsSessionAddress)
1932 {
1933
1935 CurrentProcess =
NULL;
1936
1937
1944 {
1945
1947 }
1948 }
1949 else
1950 {
1951
1954
1955
1958 {
1959
1961 }
1962 }
1963RetryKernel:
1964
1967
1968
1971 {
1972
1974 {
1975
1977 if (!(
TempPte.u.Long & PTE_READWRITE) &&
1980 {
1981
1982 ASSERT(!IsSessionAddress);
1983
1984
1989 12);
1990 }
1991 }
1992
1993
1996 {
2001 2);
2002 }
2003
2004
2005 if ((IsSessionAddress) &&
2008 {
2009
2011
2012
2014 {
2015
2020 13);
2021 }
2022
2023
2025 }
2026
2027
2030
2031
2033 }
2034
2035
2037 {
2038
2045 {
2046
2049 FaultCode,
2051 4);
2052 }
2053
2054
2056
2057
2058 if ((IsSessionAddress) &&
2060 {
2061
2063 &ProtectionCode,
2064 &Vad);
2066 }
2067 }
2068 else
2069 {
2070
2072
2073
2075 {
2076
2079 FaultCode,
2081 1);
2082 }
2083
2084
2086 {
2087
2090 FaultCode,
2092 0);
2093 }
2094 }
2095
2096
2098 !(ProtoPte) &&
2099 !(IsSessionAddress) &&
2101 {
2102
2105 {
2106
2111 14);
2112 }
2113 }
2114
2115
2118 PointerPte,
2119 ProtoPte,
2121 CurrentProcess,
2122 TrapInformation,
2124
2125
2129
2131 {
2133 goto RetryKernel;
2134 }
2135
2136
2139 }
2140
2141
2142UserFault:
2145
2146
2148
2150
2151#if (_MI_PAGING_LEVELS == 4)
2152
2154 {
2155
2157
2158
2160
2161
2164 {
2167 }
2168
2169
2171 PointerPxe,
2173 CurrentProcess,
2176 {
2177 goto ExitUser;
2178 }
2179
2180
2182 }
2183#endif
2184
2185#if (_MI_PAGING_LEVELS >= 3)
2186
2188 {
2189
2191
2192
2194
2195
2197 {
2199 }
2200
2202 {
2205 }
2206
2207
2209 PointerPpe,
2211 CurrentProcess,
2214 {
2215 goto ExitUser;
2216 }
2217
2218
2221 }
2222#endif
2223
2224
2226 {
2227
2229
2230
2231#if MI_TRACE_PFNS
2232 UserPdeFault =
TRUE;
2233#endif
2234
2236 {
2238 }
2239
2241 {
2242#if (_MI_PAGING_LEVELS == 2)
2243
2245#endif
2246
2248
2249
2252 }
2253
2254
2256 PointerPde,
2258 CurrentProcess,
2261 {
2262 goto ExitUser;
2263 }
2264
2265#if _MI_PAGING_LEVELS >= 3
2267#endif
2268
2269#if MI_TRACE_PFNS
2270 UserPdeFault =
FALSE;
2271
2272 if (TrapInformation)
2274 else
2276#endif
2277
2280 }
2281 else
2282 {
2283
2285 }
2286
2287
2289
2290
2292 {
2293
2295 {
2296
2298 {
2299 PFN_NUMBER PageFrameIndex, OldPageFrameIndex;
2301
2302 LockIrql = MiAcquirePfnLock();
2303
2305
2308
2309
2311 if (PageFrameIndex == 0)
2312 {
2313 MiReleasePfnLock(LockIrql);
2315 goto ExitUser;
2316 }
2318
2319 MiCopyPfn(PageFrameIndex, OldPageFrameIndex);
2320
2321
2327
2328
2332 TempPte.u.Hard.CopyOnWrite = 0;
2333
2335
2336 MiReleasePfnLock(LockIrql);
2337
2338
2341 }
2342
2343
2345 {
2346
2349 }
2350 }
2351
2352#if _MI_HAS_NO_EXECUTE
2353
2356 {
2357
2359 {
2360
2365 }
2366
2367
2370 }
2371#endif
2372
2373
2376 }
2377
2378
2381 {
2382
2384 PointerPte,
2386 CurrentProcess,
2389 {
2390 goto ExitUser;
2391 }
2392
2393#if MI_TRACE_PFNS
2394
2395 if (TrapInformation)
2397 else
2399#endif
2400
2401
2404 }
2405
2406
2408 {
2409
2412 {
2413#if (_MI_PAGING_LEVELS == 2)
2414
2416#endif
2417
2419
2420
2423 }
2424
2425
2426
2427
2428
2434#endif
2435#endif
2436 )
2437 {
2438
2440 }
2441
2442
2444 {
2445
2447
2448
2449 TempPte.u.Soft.Protection = ProtectionCode & ~MM_GUARDPAGE;
2451
2452
2454 ASSERT(CurrentThread->ApcNeeded == 0);
2455
2456
2459
2460
2462 }
2463
2464
2465 if (!ProtoPte)
2466 {
2467
2469 {
2470
2471#ifdef _M_ARM
2472 _WARN(
"This is probably completely broken!");
2474#else
2476#endif
2477 }
2478 else
2479 {
2480
2481 TempPte.u.Soft.Protection = ProtectionCode;
2483 }
2484
2485
2487
2488
2489
2490
2491
2496 if (!PageFrameIndex)
2497 {
2498
2500
2501
2503
2504 if (PageFrameIndex == 0)
2505 {
2507 goto ExitUser;
2508 }
2509
2510
2512
2513
2515 }
2516
2517
2519
2520
2522
2523
2525
2526
2528
2529
2531 {
2532
2534 PointerPte,
2536 PageFrameIndex);
2537 }
2538 else
2539 {
2540
2542 PointerPte,
2544 PageFrameIndex);
2545 }
2546
2547
2549
2550
2554
2555
2559 }
2560
2561
2562 ASSERT(ProtectionCode != 0x100);
2563
2564
2566 TempPte.u.Soft.Protection = ProtectionCode;
2569 }
2570 else
2571 {
2572
2575 {
2576
2578 {
2579
2581 &ProtectionCode,
2582 &Vad);
2583 if (!ProtoPte)
2584 {
2588 }
2589 }
2590 else
2591 {
2592
2594
2595
2597 {
2598
2600 }
2601 else
2602 {
2603
2604 ProtectionCode = 0x100;
2606 }
2607 }
2608 }
2609 }
2610
2611
2612 if (ProtectionCode != 0x100)
2613 {
2614
2618 ProtectionCode,
2619 TrapInformation,
2622 {
2623
2624 ASSERT(CurrentThread->ApcNeeded == 0);
2625
2626
2629
2630
2632 {
2633
2635 }
2636
2637
2639 }
2640 }
2641
2642
2645 PointerPte,
2646 ProtoPte,
2648 CurrentProcess,
2649 TrapInformation,
2650 Vad);
2651
2652ExitUser:
2653
2654
2657
2659 {
2661 goto UserFault;
2662 }
2663
2665}
DECLSPEC_NORETURN VOID NTAPI KeBugCheckEx(IN ULONG BugCheckCode, IN ULONG_PTR BugCheckParameter1, IN ULONG_PTR BugCheckParameter2, IN ULONG_PTR BugCheckParameter3, IN ULONG_PTR BugCheckParameter4)
#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)
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)
#define MiAddressToPde(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)
PFN_NUMBER NumberOfPrivatePages
ULONG OwnsSessionWorkingSetExclusive
ULONG OwnsSessionWorkingSetShared
ULONG OwnsSystemWorkingSetShared
ULONG OwnsProcessWorkingSetShared
ULONG OwnsProcessWorkingSetExclusive
ULONG OwnsSystemWorkingSetExclusive
struct _MM_SESSION_SPACE * GlobalVirtualAddress