From 7151c8a3fa7aa47b5a75a999a95f86641a806f89 Mon Sep 17 00:00:00 2001 From: actboy168 Date: Wed, 8 Jan 2014 13:51:47 +0800 Subject: [PATCH] =?UTF-8?q?=E5=A2=9E=E5=8A=A0base::hook::patch?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../base/hook/detail/memory_protect.cpp | 20 +++++++--------- .../base/hook/detail/memory_protect.h | 15 ++++++------ .../base/hook/detail/replace_pointer.cpp | 2 ++ .../Editor/Core/YDWEBase/base/hook/patch.cpp | 21 +++++++++++++++++ .../Editor/Core/YDWEBase/base/hook/patch.h | 23 +++++++++++++++++++ 5 files changed, 61 insertions(+), 20 deletions(-) create mode 100644 Development/Editor/Core/YDWEBase/base/hook/patch.cpp create mode 100644 Development/Editor/Core/YDWEBase/base/hook/patch.h diff --git a/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.cpp b/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.cpp index 0edb91a62..461fa2635 100644 --- a/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.cpp +++ b/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.cpp @@ -2,19 +2,15 @@ namespace base { namespace hook { namespace detail { - memory_protect::memory_protect(uintptr_t address) + memory_protect::memory_protect(uintptr_t address, size_t size) : success_(false) + , access_(0) + , address_(address) + , size_(size) { - if (0 == ::VirtualQuery((LPCVOID)address, &mbi_, sizeof(mbi_))) - return ; - - - if (!::VirtualProtect(mbi_.BaseAddress, mbi_.RegionSize, PAGE_WRITECOPY, &access_)) + if (!::VirtualProtect((LPVOID)address_, size_, PAGE_READWRITE, &access_)) { - if (!::VirtualProtect(mbi_.BaseAddress, mbi_.RegionSize, PAGE_READWRITE, &access_)) - { - return ; - } + return; } success_ = true; @@ -24,8 +20,8 @@ namespace base { namespace hook { namespace detail { { if (success()) { - DWORD newAccess; - ::VirtualProtect(mbi_.BaseAddress, mbi_.RegionSize, access_, &newAccess); + DWORD new_access; + ::VirtualProtect((LPVOID)address_, size_, access_, &new_access); } } diff --git a/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.h b/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.h index dae8d699d..9103694f4 100644 --- a/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.h +++ b/Development/Editor/Core/YDWEBase/base/hook/detail/memory_protect.h @@ -3,19 +3,18 @@ #include #include -namespace base { -namespace hook { namespace detail { +namespace base { namespace hook { namespace detail { class memory_protect { public: - memory_protect(uintptr_t address); + memory_protect(uintptr_t address, size_t size = sizeof(uintptr_t)); ~memory_protect(); bool success() const; private: - bool success_; - MEMORY_BASIC_INFORMATION mbi_; - DWORD access_; + bool success_; + DWORD access_; + uintptr_t address_; + size_t size_; }; -}} -} +}}} diff --git a/Development/Editor/Core/YDWEBase/base/hook/detail/replace_pointer.cpp b/Development/Editor/Core/YDWEBase/base/hook/detail/replace_pointer.cpp index 6a56c3c61..c57a0ce13 100644 --- a/Development/Editor/Core/YDWEBase/base/hook/detail/replace_pointer.cpp +++ b/Development/Editor/Core/YDWEBase/base/hook/detail/replace_pointer.cpp @@ -20,6 +20,8 @@ namespace base { namespace hook { namespace detail { { return 0; } + + ::FlushInstructionCache(::GetCurrentProcess(), (LPVOID)address, sizeof(uintptr_t)); } return old_value; diff --git a/Development/Editor/Core/YDWEBase/base/hook/patch.cpp b/Development/Editor/Core/YDWEBase/base/hook/patch.cpp new file mode 100644 index 000000000..cd462b415 --- /dev/null +++ b/Development/Editor/Core/YDWEBase/base/hook/patch.cpp @@ -0,0 +1,21 @@ +#include +#include +#include + +namespace base { namespace hook { + + bool patch(uintptr_t address, const char* value, size_t value_size) + { + detail::memory_protect protect_(address, value_size); + if (protect_.success()) + { + DWORD written; + if (::WriteProcessMemory(::GetCurrentProcess(), (LPVOID)address, value, value_size, &written)) + { + ::FlushInstructionCache(::GetCurrentProcess(), (LPVOID)address, value_size); + return true; + } + } + return false; + } +}} diff --git a/Development/Editor/Core/YDWEBase/base/hook/patch.h b/Development/Editor/Core/YDWEBase/base/hook/patch.h new file mode 100644 index 000000000..39ecee0c3 --- /dev/null +++ b/Development/Editor/Core/YDWEBase/base/hook/patch.h @@ -0,0 +1,23 @@ +#pragma once + +#include +#include +#include + +namespace base { namespace hook { + _BASE_API bool patch(uintptr_t address, const char* value, size_t value_size); + + + template + bool patch(uintptr_t address, const char(&value)[n]) + { + assert(n > 1); + return patch(address, value, n - 1); + } + + template + bool patch(uintptr_t address, char(&value)[n]) + { + return patch(address, value, std::string::traits_type::length(value)); + } +}}