// Copyright 2011-2019 Molecular Matters GmbH, all rights reserved. #include "LC_Patch.h" #include "LC_Assembly.h" #include "LC_PointerUtil.h" #include "LC_Platform.h" #include "LC_Logging.h" namespace { void Install(process::Handle processHandle, void* address, const assembly::Instruction& instruction) { process::WriteProcessMemory(processHandle, address, instruction.code, instruction.size); process::FlushInstructionCache(processHandle, address, instruction.size); } } void patch::InstallNOPs(process::Handle processHandle, void* address, size_t size) { const assembly::Instruction nop = assembly::MakeNOP(); for (size_t i = 0u; i < size; ++i) { process::WriteProcessMemory(processHandle, pointer::Offset(address, i), nop.code, nop.size); } process::FlushInstructionCache(processHandle, address, size); } void patch::InstallJumpToSelf(process::Handle processHandle, void* address) { InstallRelativeShortJump(processHandle, address, address); } void patch::InstallRelativeShortJump(process::Handle processHandle, void* address, void* destination) { char* oldFuncAddr = static_cast(address); char* newFuncAddr = static_cast(destination); const ptrdiff_t displacement = newFuncAddr - oldFuncAddr; LC_ASSERT(displacement >= std::numeric_limits::min(), "Displacement is out-of-range."); LC_ASSERT(displacement <= std::numeric_limits::max(), "Displacement is out-of-range."); const assembly::Instruction jump = assembly::MakeRelativeShortJump(static_cast(displacement)); Install(processHandle, address, jump); } void patch::InstallRelativeNearJump(process::Handle processHandle, void* address, void* destination) { char* oldFuncAddr = static_cast(address); char* newFuncAddr = static_cast(destination); const ptrdiff_t displacement = newFuncAddr - oldFuncAddr; LC_ASSERT(displacement >= std::numeric_limits::min(), "Displacement is out-of-range."); LC_ASSERT(displacement <= std::numeric_limits::max(), "Displacement is out-of-range."); const assembly::Instruction jump = assembly::MakeRelativeNearJump(static_cast(displacement)); Install(processHandle, address, jump); }