From 6dd868b2919c594760d6cb671c859c1d35f12f2b Mon Sep 17 00:00:00 2001 From: Richard Qin Date: Wed, 13 May 2026 16:25:25 +0800 Subject: feat: implement syscall dispatcher and initialization for system calls --- na/kernel/syscall.cc | 99 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 99 insertions(+) create mode 100644 na/kernel/syscall.cc diff --git a/na/kernel/syscall.cc b/na/kernel/syscall.cc new file mode 100644 index 0000000..4dfbb5d --- /dev/null +++ b/na/kernel/syscall.cc @@ -0,0 +1,99 @@ +/* SPDX-License-Identifier: GPL-2.0-or-later */ +/* Copyright (C) 2026 Richard Qin */ + +/* + * System Call MI Layer — Jump Table & Dispatcher + * + * O(1) function pointer array dispatch. No switch-case. + * syscall_init() registers all implemented handlers. + * + * Reference: docs/specs/syscall.md §6 + */ + +#include +#include +#include +#include +#include + +/* ====================================================================== + * Jump table + * ====================================================================== */ + +inline constexpr int kNrSyscalls = 512; + +static SyscallHandler sys_call_table[kNrSyscalls]; + +/* ====================================================================== + * MI Dispatcher + * ====================================================================== */ + +int64 syscall_dispatch(uint64 nr, uint64 args[6]) +{ + if (nr >= static_cast(kNrSyscalls)) + return -ENOSYS; + + SyscallHandler handler = sys_call_table[nr]; + if (!handler) + return -ENOSYS; + + return handler(args[0], args[1], args[2], + args[3], args[4], args[5]); +} + +/* ====================================================================== + * Forward declarations of sys_* handlers + * ====================================================================== */ + +/* sys_process.cc */ +int64 sys_exit(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_exit_group(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_getpid(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_gettid(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_getppid(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_sched_yield_wrapper(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_clone_wrapper(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_wait4_wrapper(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_set_tid_address(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_getuid(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_getgid(uint64, uint64, uint64, uint64, uint64, uint64); + +/* sys_mm.cc */ +int64 sys_brk(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_mmap(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_munmap(uint64, uint64, uint64, uint64, uint64, uint64); +int64 sys_mprotect(uint64, uint64, uint64, uint64, uint64, uint64); + +/* sys_info.cc */ +int64 sys_uname(uint64, uint64, uint64, uint64, uint64, uint64); + +/* ====================================================================== + * syscall_init — register all handlers + * ====================================================================== */ + +void syscall_init() +{ + /* Zero the table (redundant for BSS, but explicit) */ + for (int i = 0; i < kNrSyscalls; i++) + sys_call_table[i] = nullptr; + + /* Phase 2: minimal runnable set */ + sys_call_table[SYS_exit] = sys_exit; + sys_call_table[SYS_exit_group] = sys_exit_group; + sys_call_table[SYS_getpid] = sys_getpid; + sys_call_table[SYS_gettid] = sys_gettid; + sys_call_table[SYS_getppid] = sys_getppid; + sys_call_table[SYS_sched_yield] = sys_sched_yield_wrapper; + sys_call_table[SYS_clone] = sys_clone_wrapper; + sys_call_table[SYS_wait4] = sys_wait4_wrapper; + sys_call_table[SYS_set_tid_address] = sys_set_tid_address; + sys_call_table[SYS_getuid] = sys_getuid; + sys_call_table[SYS_getgid] = sys_getgid; + sys_call_table[SYS_brk] = sys_brk; + sys_call_table[SYS_mmap] = sys_mmap; + sys_call_table[SYS_munmap] = sys_munmap; + sys_call_table[SYS_mprotect] = sys_mprotect; + sys_call_table[SYS_uname] = sys_uname; + + printk(KERN_INFO "init: syscall_init done (16 handlers registered)\n"); +} -- cgit v1.2.3