aboutsummaryrefslogtreecommitdiff
path: root/subhook_windows.c
diff options
context:
space:
mode:
authorZeex <zeex@rocketmail.com>2023-02-10 00:00:32 +0600
committerZeex <zeex@rocketmail.com>2023-02-10 00:02:01 +0600
commit85a2406774613c7aa942a41b5651c7af79f7c702 (patch)
treeefba1620400e97d6f83c5bf14e246a79074ed6bb /subhook_windows.c
parent4f173b23239c017a9f3e53364fe371975aca2321 (diff)
downloadsubhook-85a2406774613c7aa942a41b5651c7af79f7c702.zip
subhook-85a2406774613c7aa942a41b5651c7af79f7c702.tar.gz
subhook-85a2406774613c7aa942a41b5651c7af79f7c702.tar.bz2
Add flag to support allocation of trampolines within 32-bit offset range of target code on 64-bit Windows
Plus minor formatting fixes and more documentation for flags. Fixes #9
Diffstat (limited to 'subhook_windows.c')
-rw-r--r--subhook_windows.c35
1 files changed, 34 insertions, 1 deletions
diff --git a/subhook_windows.c b/subhook_windows.c
index 321207e..8c9b477 100644
--- a/subhook_windows.c
+++ b/subhook_windows.c
@@ -27,6 +27,8 @@
#include <stddef.h>
#include <windows.h>
+typedef __int64 QWORD;
+
#define SUBHOOK_CODE_PROTECT_FLAGS PAGE_EXECUTE_READWRITE
int subhook_unprotect(void *address, size_t size) {
@@ -38,7 +40,38 @@ int subhook_unprotect(void *address, size_t size) {
return !result;
}
-void *subhook_alloc_code(size_t size) {
+void *subhook_alloc_code(void *target_address, size_t size) {
+ SYSTEM_INFO sys_info;
+ DWORD page_size = 0x1000;
+ QWORD offset;
+
+#if defined _M_AMD64 || defined __amd64__
+ if (target_address != NULL) {
+ GetSystemInfo(&sys_info);
+ page_size = sys_info.dwPageSize;
+
+ QWORD pivot = (QWORD)target_address & ~((QWORD)page_size - 1);
+ void *result;
+
+ for (offset = page_size; offset <= ((QWORD)1 << 31); offset += page_size) {
+ result = VirtualAlloc((void *)(pivot - offset),
+ size,
+ MEM_COMMIT | MEM_RESERVE,
+ SUBHOOK_CODE_PROTECT_FLAGS);
+ if (result != NULL) {
+ return result;
+ }
+ result = VirtualAlloc((void *)(pivot + offset),
+ size,
+ MEM_COMMIT | MEM_RESERVE,
+ SUBHOOK_CODE_PROTECT_FLAGS);
+ if (result != NULL) {
+ return result;
+ }
+ }
+ }
+#endif
+
return VirtualAlloc(NULL,
size,
MEM_COMMIT | MEM_RESERVE,