You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

118 lines
1.9 KiB

#pragma once
#include "types.h"
#if _M_IX86
#define OFFSET_TO_ADDRESS 0x1
#elif _M_X64
#define OFFSET_TO_ADDRESS 0x2
#endif
inline void write_to_readonly(void* addr, void* data, int size)
{
if(!addr || !data || !size)
return;
{
//
// disable write protection.
//
auto cr0 = __readcr0();
cr0 &= 0xfffffffffffeffff;
__writecr0(cr0);
_disable();
}
memcpy(addr, data, size);
{
//
// enable write protection.
//
auto cr0 = __readcr0();
cr0 |= 0x10000;
_enable();
__writecr0(cr0);
}
}
class detour
{
public:
detour() {};
detour(void* addr_to_hook, void* jmp_to, bool enable = true)
: hook_addr(addr_to_hook), detour_addr(jmp_to), hook_installed(false)
{ init(addr_to_hook, jmp_to, enable); }
void init(void* addr_to_hook, void* jmp_to, bool enable = true)
{
//setup hook
memcpy(
jmp_code + OFFSET_TO_ADDRESS,
&jmp_to,
sizeof(jmp_to)
);
//save bytes
memcpy(
org_bytes,
hook_addr,
sizeof(org_bytes)
);
if (enable)
install();
}
void install()
{
if (hook_installed)
return;
write_to_readonly(hook_addr, jmp_code, sizeof(jmp_code));
hook_installed = true;
}
void uninstall()
{
if (!hook_installed)
return;
write_to_readonly(hook_addr, org_bytes, sizeof(org_bytes));
hook_installed = false;
}
bool installed() { return hook_installed; }
void* hook_address() { return hook_addr; }
void* detour_address() { return detour_addr; }
private:
bool hook_installed;
void* hook_addr, * detour_addr;
#if _M_IX86
/*
0: b8 ff ff ff ff mov eax, 0xffffffff
5: ff e0 jmp eax
*/
unsigned char jmp_code[7] = {
0xb8, 0x0, 0x0, 0x0, 0x0,
0xFF, 0xE0
};
#elif _M_X64
/*
0: 48 c7 c0 ff ff ff ff mov rax,0xffffffffffffffff
7: ff e0 jmp rax
*/
unsigned char jmp_code[12] = {
0x48, 0xb8,
0x0,
0x0,
0x0,
0x0,
0x0,
0x0,
0x0,
0x0,
0xff, 0xe0
};
#endif
unsigned char org_bytes[sizeof(jmp_code)];
};