aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZeex <zeex@rocketmail.com>2021-11-28 22:27:23 +0600
committerGitHub <noreply@github.com>2021-11-28 22:27:23 +0600
commit86c102f28fb7f3b396f6879bd6ee8f8bb0199c9e (patch)
tree72bd9819a7cb55694bf71bdcac862ba46cae6a61
parent284047b761bd61e3c0518b0be235aa77172b1010 (diff)
parentba0872c0b24d9739d8f973f7e66683c1fc7dced5 (diff)
downloadsubhook-86c102f28fb7f3b396f6879bd6ee8f8bb0199c9e.zip
subhook-86c102f28fb7f3b396f6879bd6ee8f8bb0199c9e.tar.gz
subhook-86c102f28fb7f3b396f6879bd6ee8f8bb0199c9e.tar.bz2
Merge pull request #63 from ElDuderinos/master
Add support for MacOS Catalina+ (maxprot issue)
-rw-r--r--README.md6
-rw-r--r--subhook.h5
-rw-r--r--subhook_unix.c20
3 files changed, 25 insertions, 6 deletions
diff --git a/README.md b/README.md
index ff51c9c..01c905a 100644
--- a/README.md
+++ b/README.md
@@ -152,10 +152,8 @@ Known issues
memory as executable, which prevents the use of trampolines.
For example, on Fedora you can have such problems because of SELinux (though
- you can disable it or exclude your files). On macOS Catalina the
- `mprotect()` call inside `subhook_new` will fail with "Permission denied"
- (see https://github.com/Zeex/subhook/issues/45).
-
+ you can disable it or exclude your files).
+
License
-------
diff --git a/subhook.h b/subhook.h
index d2f6814..5633f39 100644
--- a/subhook.h
+++ b/subhook.h
@@ -41,9 +41,12 @@
#if defined _WIN32 || defined __CYGWIN__
#define SUBHOOK_WINDOWS
-#elif defined __linux__ || defined __APPLE__ \
+#elif defined __linux__ \
|| defined __FreeBSD__ || defined __OpenBSD__ || defined __NetBSD__
#define SUBHOOK_UNIX
+ #elif defined __APPLE__
+ #define SUBHOOK_APPLE
+ #define SUBHOOK_UNIX
#else
#error Unsupported operating system
#endif
diff --git a/subhook_unix.c b/subhook_unix.c
index 6a5410b..4d9c03a 100644
--- a/subhook_unix.c
+++ b/subhook_unix.c
@@ -27,6 +27,11 @@
#include <stddef.h>
#include <unistd.h>
#include <sys/mman.h>
+#include "subhook.h"
+#ifdef SUBHOOK_APPLE
+#include <mach/mach.h>
+#endif
+
#define SUBHOOK_CODE_PROTECT_FLAGS (PROT_READ | PROT_WRITE | PROT_EXEC)
@@ -36,7 +41,20 @@ int subhook_unprotect(void *address, size_t size) {
pagesize = sysconf(_SC_PAGESIZE);
address = (void *)((long)address & ~(pagesize - 1));
- return mprotect(address, size, SUBHOOK_CODE_PROTECT_FLAGS);
+ int error = mprotect(address, size, SUBHOOK_CODE_PROTECT_FLAGS);
+#ifdef SUBHOOK_APPLE
+ if (-1 == error)
+ {
+ /* If mprotect fails, try to use VM_PROT_COPY with vm_protect. */
+ kern_return_t kret = vm_protect(mach_task_self(), (unsigned long)address, size, 0, SUBHOOK_CODE_PROTECT_FLAGS | VM_PROT_COPY);
+ if (kret != KERN_SUCCESS)
+ {
+ error = -1;
+ }
+ error = 0;
+ }
+#endif
+ return error;
}
void *subhook_alloc_code(size_t size) {