summaryrefslogtreecommitdiffstats
path: root/sys/syscall_region.c
diff options
context:
space:
mode:
authorJon Santmyer <jon@jonsantmyer.com>2026-10-07 17:37:26 -0400
committerJon Santmyer <jon@jonsantmyer.com>2026-10-07 17:37:26 -0400
commit434ddcd907832b1febc7d70e4faa52109c7eb3bd (patch)
tree00c1ade91f9806d831f10e6006732b294e73f613 /sys/syscall_region.c
parent8d48bbd9746228b63bafa5f92b621998d7d8f3d3 (diff)
downloadjove-kernel-434ddcd907832b1febc7d70e4faa52109c7eb3bd.tar.gz
jove-kernel-434ddcd907832b1febc7d70e4faa52109c7eb3bd.tar.bz2
jove-kernel-434ddcd907832b1febc7d70e4faa52109c7eb3bd.zip
add memory region object for better memory managment
Diffstat (limited to 'sys/syscall_region.c')
-rw-r--r--sys/syscall_region.c68
1 files changed, 68 insertions, 0 deletions
diff --git a/sys/syscall_region.c b/sys/syscall_region.c
new file mode 100644
index 0000000..959d615
--- /dev/null
+++ b/sys/syscall_region.c
@@ -0,0 +1,68 @@
+#include "api/error.h"
+#include "api/syscall.h"
+#include "hal/memory.h"
+#include "lib/printf.h"
+#include "jove.h"
+#include "syscall.h"
+
+static int
+s_syscall_region_alloc(jove_owned_obj_t *region_obj,
+ jove_owned_obj_t *objdir_obj,
+ lockstack_t *lockstack,
+ size_t bytes_left,
+ void *payload_data)
+{
+ size_t bytes_needed = sizeof(struct syscall_region_alloc);
+ CHECK_TOOSMALL(bytes_needed, bytes_left, "Message too small for payload");
+
+ struct syscall_region_alloc *payload = payload_data;
+ bytes_needed += payload->dest_pathlen * sizeof(objpath_part_t);
+
+ CHECK_TOOSMALL(bytes_needed, bytes_left, "Message too small for subject path");
+
+ jove_perm_obj_t subject = link_try_traverse_objdir(
+ objdir_obj, lockstack, payload->dest_pathlen, payload->dest_path);
+ CHECK_OBJEXISTS(subject.obj, "Destination path is bad.");
+ CHECK_OBJPERM(subject, SYSCALL_PERM_REGION_ALLOC_TGT, "Destination path does not have correct permissions.");
+ CHECK_OBJTYPE(subject.obj, JOVE_OBJ_NONE, "Destination object is not JOVE_OBJ_NONE");
+
+ int sysret = 0;
+ if(payload->alloc_pages == 1) {
+ sysret = region_alloc(region_obj, subject.obj);
+ }else{
+ sysret = region_alloc_contig(region_obj, subject.obj, payload->alloc_pages);
+ }
+ if(sysret < 0) {
+ klogf("Region alloc failed with reason: %s\n", errstr(-sysret));
+ }
+ return sysret;
+}
+
+int
+_syscall_handle_region(syscall_context_t *ctx)
+{
+ switch(ctx->header->callid) {
+ case SYSCALL_REGION_ADDRESS:
+ if(ctx->target.permissions & SYSCALL_PERM_REGION_GETTERS)
+ return region_base(ctx->target.obj);
+ return -EPERM;
+
+ case SYSCALL_REGION_TOTAL_PAGES:
+ if(ctx->target.permissions & SYSCALL_PERM_REGION_GETTERS)
+ return region_pages(ctx->target.obj);
+ return -EPERM;
+
+ case SYSCALL_REGION_FREE_PAGES:
+ if(ctx->target.permissions & SYSCALL_PERM_REGION_GETTERS)
+ return region_freepages(ctx->target.obj);
+ return -EPERM;
+
+ case SYSCALL_REGION_ALLOC:
+ if(ctx->target.permissions & SYSCALL_PERM_REGION_ALLOC)
+ return s_syscall_region_alloc(ctx->target.obj, ctx->objdir, &ctx->lockstack, ctx->bytes_left, ctx->payload);
+ return -EPERM;
+
+ default:
+ return -EBADCALL;
+ }
+}