Add initial project files (excluding ignored content)
This commit is contained in:
39
external/safetyhook/example/dll.cpp
vendored
Normal file
39
external/safetyhook/example/dll.cpp
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
#if __has_include(<Windows.h>)
|
||||
#include <Windows.h>
|
||||
#elif __has_include(<windows.h>)
|
||||
#include <windows.h>
|
||||
#else
|
||||
#error "Windows.h not found"
|
||||
#endif
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
SafetyHookInline g_PeekMessageA_hook{};
|
||||
SafetyHookInline g_PeekMessageW_hook{};
|
||||
|
||||
BOOL WINAPI hooked_PeekMessageA(LPMSG msg, HWND wnd, UINT filter_min, UINT filter_max, UINT remove_msg) {
|
||||
OutputDebugString("hooked_PeekMessageA\n");
|
||||
return g_PeekMessageA_hook.stdcall<BOOL>(msg, wnd, filter_min, filter_max, remove_msg);
|
||||
}
|
||||
|
||||
BOOL WINAPI hooked_PeekMessageW(LPMSG msg, HWND wnd, UINT filter_min, UINT filter_max, UINT remove_msg) {
|
||||
OutputDebugString("hooked_PeekMessageW\n");
|
||||
return g_PeekMessageW_hook.stdcall<BOOL>(msg, wnd, filter_min, filter_max, remove_msg);
|
||||
}
|
||||
|
||||
BOOL WINAPI DllMain(HINSTANCE, DWORD reason, LPVOID) {
|
||||
switch (reason) {
|
||||
case DLL_PROCESS_ATTACH:
|
||||
g_PeekMessageA_hook = safetyhook::create_inline(
|
||||
reinterpret_cast<void*>(&PeekMessageA), reinterpret_cast<void*>(&hooked_PeekMessageA));
|
||||
g_PeekMessageW_hook = safetyhook::create_inline(
|
||||
reinterpret_cast<void*>(&PeekMessageW), reinterpret_cast<void*>(&hooked_PeekMessageW));
|
||||
break;
|
||||
|
||||
case DLL_PROCESS_DETACH:
|
||||
g_PeekMessageW_hook.reset();
|
||||
g_PeekMessageA_hook.reset();
|
||||
break;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
65
external/safetyhook/example/midhook.cpp
vendored
Normal file
65
external/safetyhook/example/midhook.cpp
vendored
Normal file
@@ -0,0 +1,65 @@
|
||||
#include <print>
|
||||
|
||||
#if __has_include("Zydis/Zydis.h")
|
||||
#include "Zydis/Zydis.h"
|
||||
#elif __has_include("Zydis.h")
|
||||
#include "Zydis.h"
|
||||
#else
|
||||
#error "Zydis not found"
|
||||
#endif
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
SAFETYHOOK_NOINLINE int add_42(int a) {
|
||||
return a + 42;
|
||||
}
|
||||
|
||||
void hooked_add_42(SafetyHookContext& ctx) {
|
||||
#if SAFETYHOOK_ARCH_X86_64
|
||||
ctx.rax = 1337;
|
||||
#elif SAFETYHOOK_ARCH_X86_32
|
||||
ctx.eax = 1337;
|
||||
#endif
|
||||
}
|
||||
|
||||
SafetyHookMid g_hook{};
|
||||
|
||||
int main() {
|
||||
std::println("unhooked add_42(2) = {}", add_42(2));
|
||||
|
||||
// Let's disassemble add_42 and hook its RET.
|
||||
// NOTE: On Linux we should specify -falign-functions=32 to add some padding to the function otherwise we'll
|
||||
// end up hooking the next function's prologue. This is pretty hacky in general but it's just an example.
|
||||
ZydisDecoder decoder{};
|
||||
|
||||
#if SAFETYHOOK_ARCH_X86_64
|
||||
ZydisDecoderInit(&decoder, ZYDIS_MACHINE_MODE_LONG_64, ZYDIS_STACK_WIDTH_64);
|
||||
#elif SAFETYHOOK_ARCH_X86_32
|
||||
ZydisDecoderInit(&decoder, ZYDIS_MACHINE_MODE_LEGACY_32, ZYDIS_STACK_WIDTH_32);
|
||||
#endif
|
||||
|
||||
auto ip = reinterpret_cast<uint8_t*>(add_42);
|
||||
|
||||
while (*ip != 0xC3) {
|
||||
ZydisDecodedInstruction ix{};
|
||||
|
||||
ZydisDecoderDecodeInstruction(&decoder, nullptr, reinterpret_cast<void*>(ip), 15, &ix);
|
||||
|
||||
// Follow JMPs
|
||||
if (ix.opcode == 0xE9) {
|
||||
ip += ix.length + (int32_t)ix.raw.imm[0].value.s;
|
||||
} else {
|
||||
ip += ix.length;
|
||||
}
|
||||
}
|
||||
|
||||
g_hook = safetyhook::create_mid(ip, hooked_add_42);
|
||||
|
||||
std::println("hooked add_42(3) = {}", add_42(3));
|
||||
|
||||
g_hook = {};
|
||||
|
||||
std::println("unhooked add_42(4) = {}", add_42(4));
|
||||
|
||||
return 0;
|
||||
}
|
||||
28
external/safetyhook/example/minimal.cpp
vendored
Normal file
28
external/safetyhook/example/minimal.cpp
vendored
Normal file
@@ -0,0 +1,28 @@
|
||||
#include <print>
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
SAFETYHOOK_NOINLINE int add(int x, int y) {
|
||||
return x + y;
|
||||
}
|
||||
|
||||
SafetyHookInline g_add_hook{};
|
||||
|
||||
int hook_add(int x, int y) {
|
||||
return g_add_hook.call<int>(x * 2, y * 2);
|
||||
}
|
||||
|
||||
int main() {
|
||||
std::println("unhooked add(2, 3) = {}", add(2, 3));
|
||||
|
||||
// Create a hook on add.
|
||||
g_add_hook = safetyhook::create_inline(reinterpret_cast<void*>(add), reinterpret_cast<void*>(hook_add));
|
||||
|
||||
std::println("hooked add(3, 4) = {}", add(3, 4));
|
||||
|
||||
g_add_hook = {};
|
||||
|
||||
std::println("unhooked add(5, 6) = {}", add(5, 6));
|
||||
|
||||
return 0;
|
||||
}
|
||||
36
external/safetyhook/example/multiple.cpp
vendored
Normal file
36
external/safetyhook/example/multiple.cpp
vendored
Normal file
@@ -0,0 +1,36 @@
|
||||
#include <print>
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
SafetyHookInline hook0, hook1, hook2, hook3;
|
||||
|
||||
SAFETYHOOK_NOINLINE void say_hi(const std::string& name) {
|
||||
std::println("hello {}", name);
|
||||
}
|
||||
|
||||
void hook0_fn(const std::string& name) {
|
||||
hook0.call<void, const std::string&>(name + " and bob");
|
||||
}
|
||||
|
||||
void hook1_fn(const std::string& name) {
|
||||
hook1.call<void, const std::string&>(name + " and alice");
|
||||
}
|
||||
|
||||
void hook2_fn(const std::string& name) {
|
||||
hook2.call<void, const std::string&>(name + " and eve");
|
||||
}
|
||||
|
||||
void hook3_fn(const std::string& name) {
|
||||
hook3.call<void, const std::string&>(name + " and carol");
|
||||
}
|
||||
|
||||
int main() {
|
||||
hook0 = safetyhook::create_inline(reinterpret_cast<void*>(say_hi), reinterpret_cast<void*>(hook0_fn));
|
||||
hook1 = safetyhook::create_inline(reinterpret_cast<void*>(say_hi), reinterpret_cast<void*>(hook1_fn));
|
||||
hook2 = safetyhook::create_inline(reinterpret_cast<void*>(say_hi), reinterpret_cast<void*>(hook2_fn));
|
||||
hook3 = safetyhook::create_inline(reinterpret_cast<void*>(say_hi), reinterpret_cast<void*>(hook3_fn));
|
||||
|
||||
say_hi("world");
|
||||
|
||||
return 0;
|
||||
}
|
||||
38
external/safetyhook/example/threadsafe.cpp
vendored
Normal file
38
external/safetyhook/example/threadsafe.cpp
vendored
Normal file
@@ -0,0 +1,38 @@
|
||||
#include <print>
|
||||
#include <thread>
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
SafetyHookInline g_hook{};
|
||||
|
||||
SAFETYHOOK_NOINLINE void SayHello(int times) {
|
||||
std::println("Hello #{}", times);
|
||||
}
|
||||
|
||||
void Hooked_SayHello(int times [[maybe_unused]]) {
|
||||
g_hook.call<void, int>(1337);
|
||||
}
|
||||
|
||||
void SayHelloInfinitely() {
|
||||
int count = 0;
|
||||
|
||||
while (true) {
|
||||
SayHello(count++);
|
||||
}
|
||||
}
|
||||
|
||||
int main() {
|
||||
// Starting a thread for SayHello
|
||||
std::thread t(SayHelloInfinitely);
|
||||
t.detach();
|
||||
|
||||
g_hook = safetyhook::create_inline(reinterpret_cast<void*>(SayHello), reinterpret_cast<void*>(Hooked_SayHello));
|
||||
|
||||
std::this_thread::sleep_for(std::chrono::seconds(1));
|
||||
|
||||
g_hook.reset();
|
||||
|
||||
std::this_thread::sleep_for(std::chrono::seconds(1));
|
||||
|
||||
return 0;
|
||||
}
|
||||
45
external/safetyhook/example/vmthook.cpp
vendored
Normal file
45
external/safetyhook/example/vmthook.cpp
vendored
Normal file
@@ -0,0 +1,45 @@
|
||||
#include <memory>
|
||||
#include <print>
|
||||
|
||||
#include <safetyhook.hpp>
|
||||
|
||||
class Interface {
|
||||
public:
|
||||
virtual ~Interface() = default;
|
||||
virtual int add_42(int a) = 0;
|
||||
};
|
||||
|
||||
class Target : public Interface {
|
||||
public:
|
||||
int add_42(int a) override { return a + 42; }
|
||||
};
|
||||
|
||||
SafetyHookVmt g_target_hook;
|
||||
SafetyHookVm g_add_42_hook;
|
||||
|
||||
class Hook : public Target {
|
||||
public:
|
||||
int hooked_add_42(int a) { return g_add_42_hook.thiscall<int>(this, a) + 1337; }
|
||||
};
|
||||
|
||||
int main() {
|
||||
auto target = std::make_unique<Target>();
|
||||
|
||||
std::println("unhooked target->add_42(1) = {}", target->add_42(1));
|
||||
|
||||
g_target_hook = safetyhook::create_vmt(target.get());
|
||||
|
||||
#if SAFETYHOOK_OS_WINDOWS
|
||||
g_add_42_hook = safetyhook::create_vm(g_target_hook, 1, &Hook::hooked_add_42);
|
||||
#elif SAFETYHOOK_OS_LINUX
|
||||
g_add_42_hook = safetyhook::create_vm(g_target_hook, 2, &Hook::hooked_add_42);
|
||||
#endif
|
||||
|
||||
std::println("hooked target->add_42(2) = {}", target->add_42(2));
|
||||
|
||||
g_target_hook = {};
|
||||
|
||||
std::println("unhooked target->add_42(3) = {}", target->add_42(3));
|
||||
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user