[NTOS:Mm] Implement MmCreatePhysicalMapping and MmDeletePhysicalMapping to handle pyhsical memory sections

This commit is contained in:
Timo Kreuzer 2023-04-10 21:14:06 +03:00
parent 918e331970
commit 73de609917
4 changed files with 89 additions and 12 deletions

View file

@ -1135,6 +1135,14 @@ MmCreateVirtualMappingUnsafe(
PFN_NUMBER Page PFN_NUMBER Page
); );
NTSTATUS
NTAPI
MmCreatePhysicalMapping(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_In_ ULONG flProtect,
_In_ PFN_NUMBER Page);
ULONG ULONG
NTAPI NTAPI
MmGetPageProtect( MmGetPageProtect(
@ -1291,12 +1299,21 @@ MmGetExecuteOptions(IN PULONG ExecuteOptions);
_Success_(return) _Success_(return)
BOOLEAN BOOLEAN
MmDeleteVirtualMapping( MmDeleteVirtualMapping(
_In_opt_ PEPROCESS Process, _Inout_opt_ PEPROCESS Process,
_In_ PVOID Address, _In_ PVOID Address,
_Out_opt_ BOOLEAN* WasDirty, _Out_opt_ BOOLEAN* WasDirty,
_Out_opt_ PPFN_NUMBER Page _Out_opt_ PPFN_NUMBER Page
); );
_Success_(return)
BOOLEAN
MmDeletePhysicalMapping(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_Out_opt_ BOOLEAN * WasDirty,
_Out_opt_ PPFN_NUMBER Page
);
/* arch/procsup.c ************************************************************/ /* arch/procsup.c ************************************************************/
BOOLEAN BOOLEAN

View file

@ -234,11 +234,12 @@ MmGetPfnForProcess(PEPROCESS Process,
*/ */
_Success_(return) _Success_(return)
BOOLEAN BOOLEAN
MmDeleteVirtualMapping( MmDeleteVirtualMappingEx(
_In_opt_ PEPROCESS Process, _Inout_opt_ PEPROCESS Process,
_In_ PVOID Address, _In_ PVOID Address,
_Out_opt_ BOOLEAN* WasDirty, _Out_opt_ BOOLEAN* WasDirty,
_Out_opt_ PPFN_NUMBER Page) _Out_opt_ PPFN_NUMBER Page,
_In_ BOOLEAN IsPhysical)
{ {
PMMPTE PointerPte; PMMPTE PointerPte;
MMPTE OldPte; MMPTE OldPte;
@ -322,12 +323,38 @@ MmDeleteVirtualMapping(
} }
} }
if (!IsPhysical && OldPte.u.Hard.Valid)
{
// TODO: Handle PFN ShareCount
}
MiUnlockProcessWorkingSetUnsafe(Process, PsGetCurrentThread()); MiUnlockProcessWorkingSetUnsafe(Process, PsGetCurrentThread());
} }
return OldPte.u.Long != 0; return OldPte.u.Long != 0;
} }
_Success_(return)
BOOLEAN
MmDeleteVirtualMapping(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_Out_opt_ BOOLEAN * WasDirty,
_Out_opt_ PPFN_NUMBER Page)
{
return MmDeleteVirtualMappingEx(Process, Address, WasDirty, Page, FALSE);
}
_Success_(return)
BOOLEAN
MmDeletePhysicalMapping(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_Out_opt_ BOOLEAN * WasDirty,
_Out_opt_ PPFN_NUMBER Page)
{
return MmDeleteVirtualMappingEx(Process, Address, WasDirty, Page, TRUE);
}
VOID VOID
NTAPI NTAPI
@ -588,10 +615,12 @@ MmCreatePageFileMapping(PEPROCESS Process,
NTSTATUS NTSTATUS
NTAPI NTAPI
MmCreateVirtualMappingUnsafe(PEPROCESS Process, MmCreateVirtualMappingUnsafeEx(
PVOID Address, _Inout_opt_ PEPROCESS Process,
ULONG flProtect, _In_ PVOID Address,
PFN_NUMBER Page) _In_ ULONG flProtect,
_In_ PFN_NUMBER Page,
_In_ BOOLEAN IsPhysical)
{ {
ULONG ProtectionMask; ULONG ProtectionMask;
PMMPTE PointerPte; PMMPTE PointerPte;
@ -654,6 +683,11 @@ MmCreateVirtualMappingUnsafe(PEPROCESS Process,
KeBugCheck(MEMORY_MANAGEMENT); KeBugCheck(MEMORY_MANAGEMENT);
} }
if (!IsPhysical)
{
// TODO: Handle PFN ShareCount
}
/* We don't need to flush the TLB here because it only caches valid translations /* We don't need to flush the TLB here because it only caches valid translations
* and we're moving this PTE from invalid to valid so it can't be cached right now */ * and we're moving this PTE from invalid to valid so it can't be cached right now */
@ -667,6 +701,28 @@ MmCreateVirtualMappingUnsafe(PEPROCESS Process,
return(STATUS_SUCCESS); return(STATUS_SUCCESS);
} }
NTSTATUS
NTAPI
MmCreateVirtualMappingUnsafe(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_In_ ULONG flProtect,
_In_ PFN_NUMBER Page)
{
return MmCreateVirtualMappingUnsafeEx(Process, Address, flProtect, Page, FALSE);
}
NTSTATUS
NTAPI
MmCreatePhysicalMapping(
_Inout_opt_ PEPROCESS Process,
_In_ PVOID Address,
_In_ ULONG flProtect,
_In_ PFN_NUMBER Page)
{
return MmCreateVirtualMappingUnsafeEx(Process, Address, flProtect, Page, TRUE);
}
NTSTATUS NTSTATUS
NTAPI NTAPI
MmCreateVirtualMapping(PEPROCESS Process, MmCreateVirtualMapping(PEPROCESS Process,

View file

@ -322,6 +322,10 @@ MmFreeMemoryArea(
/* We'll have to do some cleanup when we're on the page file */ /* We'll have to do some cleanup when we're on the page file */
DoFree = TRUE; DoFree = TRUE;
} }
else if (FreePage == NULL)
{
DoFree = MmDeletePhysicalMapping(Process, (PVOID)Address, &Dirty, &Page);
}
else else
{ {
DoFree = MmDeleteVirtualMapping(Process, (PVOID)Address, &Dirty, &Page); DoFree = MmDeleteVirtualMapping(Process, (PVOID)Address, &Dirty, &Page);

View file

@ -1689,7 +1689,7 @@ MmNotPresentFaultSectionView(PMMSUPPORT AddressSpace,
* Just map the desired physical page * Just map the desired physical page
*/ */
Page = (PFN_NUMBER)(Offset.QuadPart >> PAGE_SHIFT); Page = (PFN_NUMBER)(Offset.QuadPart >> PAGE_SHIFT);
Status = MmCreateVirtualMappingUnsafe(Process, Status = MmCreatePhysicalMapping(Process,
PAddress, PAddress,
Region->Protect, Region->Protect,
Page); Page);