serenity/Ports/quake3/patches/0008-Engine-Use-Serenity-style-PROT_EXEC-mmap.patch

70 lines
2.5 KiB
Diff

From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Jesse Buhagiar <jooster669@gmail.com>
Date: Sat, 26 Mar 2022 00:08:46 +1100
Subject: [PATCH] Engine: Use Serenity style PROT_EXEC mmap
The code for this was really old and crusty, so let's `ifdef` it out and
use some more friendly Serenity style memory code.
---
code/qcommon/vm_x86.c | 29 +++++++++++++++++++++++++++--
1 file changed, 27 insertions(+), 2 deletions(-)
diff --git a/code/qcommon/vm_x86.c b/code/qcommon/vm_x86.c
index 8d6321a..d155efc 100644
--- a/code/qcommon/vm_x86.c
+++ b/code/qcommon/vm_x86.c
@@ -42,6 +42,12 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#endif
#endif
+#ifdef __serenity__
+#include <fcntl.h>
+#include <unistd.h> // for `pledge()`
+#include <serenity.h>
+#endif
+
#if defined (__i386__) || defined(__x86_64__)
static void VM_Destroy_Compiled(vm_t* self);
@@ -1649,9 +1655,24 @@ void VM_Compile(vm_t *vm, vmHeader_t *header)
// copy to an exact sized buffer with the appropriate permission bits
vm->codeLength = compiledOfs;
#ifdef VM_X86_MMAP
+#ifdef __serenity__
+ // Round up by a page for `anon_create` (so we don't blow up in the Kernel)
+ int compiledOfsPageAligned = compiledOfs + (4096u - (compiledOfs % 4096u));
+
+ // Create the fd...
+ int fd = anon_create(compiledOfsPageAligned, O_CLOEXEC);
+ if (fd == -1)
+ Com_Error(ERR_FATAL, "VM_CompileX86: anon_create failed (a very bad thing!)");
+
+ vm->codeBase = mmap_with_name(NULL, compiledOfs, PROT_WRITE|PROT_READ|PROT_EXEC, MAP_SHARED, fd, 0, "Quake3 VM Page");
+ if(vm->codeBase == MAP_FAILED)
+ Com_Error(ERR_FATAL, "VM_CompileX86: can't mmap memory");
+ close(fd);
+#else
vm->codeBase = mmap(NULL, compiledOfs, PROT_WRITE, MAP_SHARED|MAP_ANONYMOUS, -1, 0);
if(vm->codeBase == MAP_FAILED)
Com_Error(ERR_FATAL, "VM_CompileX86: can't mmap memory");
+#endif
#elif _WIN32
// allocate memory with EXECUTE permissions under windows.
vm->codeBase = VirtualAlloc(NULL, compiledOfs, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
@@ -1665,9 +1686,13 @@ void VM_Compile(vm_t *vm, vmHeader_t *header)
Com_Memcpy( vm->codeBase, buf, compiledOfs );
+
#ifdef VM_X86_MMAP
- if(mprotect(vm->codeBase, compiledOfs, PROT_READ|PROT_EXEC))
- Com_Error(ERR_FATAL, "VM_CompileX86: mprotect failed");
+#ifndef __serenity__
+ int rc = mprotect(vm->codeBase, compiledOfs, PROT_READ|PROT_EXEC);
+ if(rc)
+ Com_Error(ERR_FATAL, "VM_CompileX86: mprotect failed with %d", rc);
+#endif
#elif _WIN32
{
DWORD oldProtect = 0;