mirror of
https://github.com/HyperDbg/HyperDbg.git
synced 2026-07-13 02:59:30 +00:00
293 lines
6.8 KiB
C
293 lines
6.8 KiB
C
/**
|
|
* @file Conversion.c
|
|
* @author Sina Karvandi (sina@hyperdbg.org)
|
|
* @brief Functions for memory conversions
|
|
*
|
|
* @version 0.2
|
|
* @date 2023-04-27
|
|
*
|
|
* @copyright This project is released under the GNU Public License v3.
|
|
*
|
|
*/
|
|
#include "pch.h"
|
|
|
|
/**
|
|
* @brief Converts Physical Address to Virtual Address
|
|
*
|
|
* @param PhysicalAddress The target physical address
|
|
* @return UINT64 Returns the virtual address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
PhysicalAddressToVirtualAddress(UINT64 PhysicalAddress)
|
|
{
|
|
PHYSICAL_ADDRESS PhysicalAddr;
|
|
PhysicalAddr.QuadPart = PhysicalAddress;
|
|
|
|
return (UINT64)MmGetVirtualForPhysical(PhysicalAddr);
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Physical Address to Virtual Address based
|
|
* on a specific process id
|
|
*
|
|
* @details this function should NOT be called from vmx-root mode
|
|
*
|
|
* @param PhysicalAddress The target physical address
|
|
* @param ProcessId The target's process id
|
|
* @return UINT64 Returns the virtual address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
PhysicalAddressToVirtualAddressByProcessId(PVOID PhysicalAddress, UINT32 ProcessId)
|
|
{
|
|
CR3_TYPE CurrentProcessCr3;
|
|
UINT64 VirtualAddress;
|
|
PHYSICAL_ADDRESS PhysicalAddr;
|
|
|
|
//
|
|
// Switch to new process's memory layout
|
|
//
|
|
CurrentProcessCr3 = SwitchToProcessMemoryLayout(ProcessId);
|
|
|
|
//
|
|
// Validate if process id is valid
|
|
//
|
|
if (CurrentProcessCr3.Flags == NULL64_ZERO)
|
|
{
|
|
//
|
|
// Pid is invalid
|
|
//
|
|
return NULL64_ZERO;
|
|
}
|
|
|
|
//
|
|
// Read the virtual address based on new cr3
|
|
//
|
|
PhysicalAddr.QuadPart = (LONGLONG)PhysicalAddress;
|
|
VirtualAddress = (UINT64)MmGetVirtualForPhysical(PhysicalAddr);
|
|
|
|
//
|
|
// Restore the original process
|
|
//
|
|
SwitchToPreviousProcess(CurrentProcessCr3);
|
|
|
|
return VirtualAddress;
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Physical Address to Virtual Address based
|
|
* on a specific process's kernel cr3
|
|
*
|
|
* @details this function should NOT be called from vmx-root mode
|
|
*
|
|
* @param PhysicalAddress The target physical address
|
|
* @param TargetCr3 The target's process cr3
|
|
* @return UINT64 Returns the virtual address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
PhysicalAddressToVirtualAddressByCr3(PVOID PhysicalAddress, CR3_TYPE TargetCr3)
|
|
{
|
|
CR3_TYPE CurrentProcessCr3;
|
|
UINT64 VirtualAddress;
|
|
PHYSICAL_ADDRESS PhysicalAddr;
|
|
|
|
//
|
|
// Switch to new process's memory layout
|
|
//
|
|
CurrentProcessCr3 = SwitchToProcessMemoryLayoutByCr3(TargetCr3);
|
|
|
|
//
|
|
// Validate if process id is valid
|
|
//
|
|
if (CurrentProcessCr3.Flags == NULL64_ZERO)
|
|
{
|
|
//
|
|
// Pid is invalid
|
|
//
|
|
return NULL64_ZERO;
|
|
}
|
|
|
|
//
|
|
// Read the virtual address based on new cr3
|
|
//
|
|
PhysicalAddr.QuadPart = (LONGLONG)PhysicalAddress;
|
|
VirtualAddress = (UINT64)MmGetVirtualForPhysical(PhysicalAddr);
|
|
|
|
//
|
|
// Restore the original process
|
|
//
|
|
SwitchToPreviousProcess(CurrentProcessCr3);
|
|
|
|
return VirtualAddress;
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Physical Address to Virtual Address based
|
|
* on current process's kernel cr3
|
|
*
|
|
* @details this function should NOT be called from vmx-root mode
|
|
*
|
|
* @param PhysicalAddress The target physical address
|
|
* @return UINT64 Returns the virtual address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
PhysicalAddressToVirtualAddressOnTargetProcess(PVOID PhysicalAddress)
|
|
{
|
|
CR3_TYPE GuestCr3;
|
|
|
|
GuestCr3.Flags = LayoutGetCurrentProcessCr3().Flags;
|
|
|
|
return PhysicalAddressToVirtualAddressByCr3(PhysicalAddress, GuestCr3);
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Virtual Address to Physical Address
|
|
*
|
|
* @param VirtualAddress The target virtual address
|
|
* @return UINT64 Returns the physical address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
VirtualAddressToPhysicalAddress(_In_ PVOID VirtualAddress)
|
|
{
|
|
return MmGetPhysicalAddress(VirtualAddress).QuadPart;
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Virtual Address to Physical Address based
|
|
* on a specific process id's kernel cr3
|
|
*
|
|
* @details this function should NOT be called from vmx-root mode
|
|
*
|
|
* @param VirtualAddress The target virtual address
|
|
* @param ProcessId The target's process id
|
|
* @return UINT64 Returns the physical address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
VirtualAddressToPhysicalAddressByProcessId(PVOID VirtualAddress, UINT32 ProcessId)
|
|
{
|
|
CR3_TYPE CurrentProcessCr3;
|
|
UINT64 PhysicalAddress;
|
|
|
|
//
|
|
// Switch to new process's memory layout
|
|
//
|
|
CurrentProcessCr3 = SwitchToProcessMemoryLayout(ProcessId);
|
|
|
|
//
|
|
// Validate if process id is valid
|
|
//
|
|
if (CurrentProcessCr3.Flags == NULL64_ZERO)
|
|
{
|
|
//
|
|
// Pid is invalid
|
|
//
|
|
return NULL64_ZERO;
|
|
}
|
|
|
|
//
|
|
// Read the physical address based on new cr3
|
|
//
|
|
PhysicalAddress = MmGetPhysicalAddress(VirtualAddress).QuadPart;
|
|
|
|
//
|
|
// Restore the original process
|
|
//
|
|
SwitchToPreviousProcess(CurrentProcessCr3);
|
|
|
|
return PhysicalAddress;
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Virtual Address to Physical Address based
|
|
* on a specific process's kernel cr3
|
|
*
|
|
* @param VirtualAddress The target virtual address
|
|
* @param TargetCr3 The target's process cr3
|
|
* @return UINT64 Returns the physical address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
VirtualAddressToPhysicalAddressByProcessCr3(PVOID VirtualAddress, CR3_TYPE TargetCr3)
|
|
{
|
|
CR3_TYPE CurrentProcessCr3;
|
|
UINT64 PhysicalAddress;
|
|
|
|
//
|
|
// Switch to new process's memory layout
|
|
//
|
|
CurrentProcessCr3 = SwitchToProcessMemoryLayoutByCr3(TargetCr3);
|
|
|
|
//
|
|
// Validate if process id is valid
|
|
//
|
|
if (CurrentProcessCr3.Flags == NULL64_ZERO)
|
|
{
|
|
//
|
|
// Pid is invalid
|
|
//
|
|
return NULL64_ZERO;
|
|
}
|
|
|
|
//
|
|
// Read the physical address based on new cr3
|
|
//
|
|
PhysicalAddress = MmGetPhysicalAddress(VirtualAddress).QuadPart;
|
|
|
|
//
|
|
// Restore the original process
|
|
//
|
|
SwitchToPreviousProcess(CurrentProcessCr3);
|
|
|
|
return PhysicalAddress;
|
|
}
|
|
|
|
/**
|
|
* @brief Converts Virtual Address to Physical Address based
|
|
* on the current process's kernel cr3
|
|
*
|
|
* @param VirtualAddress The target virtual address
|
|
* @return UINT64 Returns the physical address
|
|
*/
|
|
_Use_decl_annotations_
|
|
UINT64
|
|
VirtualAddressToPhysicalAddressOnTargetProcess(PVOID VirtualAddress)
|
|
{
|
|
CR3_TYPE CurrentCr3;
|
|
CR3_TYPE GuestCr3;
|
|
UINT64 PhysicalAddress;
|
|
|
|
GuestCr3.Flags = LayoutGetCurrentProcessCr3().Flags;
|
|
|
|
//
|
|
// Switch to new process's memory layout
|
|
//
|
|
CurrentCr3 = SwitchToProcessMemoryLayoutByCr3(GuestCr3);
|
|
|
|
//
|
|
// Validate if process id is valid
|
|
//
|
|
if (CurrentCr3.Flags == NULL64_ZERO)
|
|
{
|
|
//
|
|
// Pid is invalid
|
|
//
|
|
return NULL64_ZERO;
|
|
}
|
|
|
|
//
|
|
// Read the physical address based on new cr3
|
|
//
|
|
PhysicalAddress = MmGetPhysicalAddress(VirtualAddress).QuadPart;
|
|
|
|
//
|
|
// Restore the original process
|
|
//
|
|
SwitchToPreviousProcess(CurrentCr3);
|
|
|
|
return PhysicalAddress;
|
|
}
|