feature (syscalls): implemented syscall arguments and return value

This commit is contained in:
antifallobst 2023-03-08 18:25:20 +01:00
parent f6339e7127
commit 257999f0fe
7 changed files with 167 additions and 31 deletions

View File

@ -25,19 +25,54 @@
#define NOX_SYSCALL_H #define NOX_SYSCALL_H
#include "platform/cpu.h" #include "platform/cpu.h"
#include "utils/status.h"
typedef enum { typedef enum {
SYSCALLS_MISC = 0x00, SYSCALLS_FILES = 0x00,
SYSCALLS_FILE = 0x01, SYSCALLS_MEMORY = 0x01,
SYSCALLS_PROC = 0x02, SYSCALLS_PROC = 0x02,
SYSCALLS_KERNEL = 0xFF, SYSCALLS_RUNTIME_LINKER = 0x02,
SYSCALLS_COMPATABILITY = 0x02,
SYSCALLS_KERNEL = 0xFF
}syscall_group_E; }syscall_group_E;
typedef enum { typedef enum {
SYSCALL_KERNEL_SCHEDULER_START = 0xFF00 SYSCALL_FILES_OPEN = 0x0101,
SYSCALL_FILES_CLOSE = 0x0102,
SYSCALL_FILES_READ = 0x0103,
SYSCALL_FILES_WRITE = 0x0104,
SYSCALL_FILES_DELETE = 0x0105,
SYSCALL_FILES_LIST = 0x0106,
SYSCALL_FILES_FOLLOW = 0x0107, // Warning: nx_follow will probably be kicked out of the ABI
SYSCALL_FILES_INFO = 0x0108,
SYSCALL_MEMORY_ALLOC = 0x0201,
SYSCALL_MEMORY_FREE = 0x0202,
SYSCALL_MEMORY_LABEL = 0x0203,
SYSCALL_MEMORY_RANGE = 0x0204,
SYSCALL_MEMORY_ACCESS = 0x0205,
SYSCALL_PROCESS_CREATE = 0x0301,
SYSCALL_PROCESS_ENVFILE = 0x0302,
SYSCALL_PROCESS_START = 0x0303,
SYSCALL_PROCESS_SIGNAL = 0x0304,
SYSCALL_RUNTIME_LINKER_OPEN = 0x0401,
SYSCALL_RUNTIME_LINKER_CLOSE = 0x0402,
SYSCALL_RUNTIME_LINKER_LOAD_SYMBOL = 0x0403,
SYSCALL_RUNTIME_LINKER_STATUS = 0x0404,
SYSCALL_RUNTIME_LINKER_STANDARD_MOD = 0x0405,
SYSCALL_COMPATABILITY_ABI_TYPE = 0x0501,
SYSCALL_COMPATABILITY_ABI_VERSION = 0x0502,
SYSCALL_COMPATABILITY_ACTION = 0x0503,
SYSCALL_KERNEL_SCHEDULER_START = 0xFF00,
SYSCALL_KERNEL_PANIC = 0xFF01
} syscall_E; } syscall_E;
extern void syscall_perform(syscall_E id); extern status_E syscall_perform(syscall_E id, uint64_t arg1, uint64_t arg2, uint64_t arg3, uint64_t arg4);
cpu_state_T* syscall_handle(cpu_state_T* state); cpu_state_T* syscall_handle(cpu_state_T* state);

38
kernel/inc/utils/status.h Normal file
View File

@ -0,0 +1,38 @@
/*
* Copyright 2023 Antifallobst <antifallobst@systemausfall.org>
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the Software), to deal in
* the Software without restriction, including without limitation the rights to use,
* copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the
* Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
* OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef NOX_STATUS_H
#define NOX_STATUS_H
#include "string.h"
typedef enum {
STATUS_SUCCESS,
STATUS_PERMISSION_DENIED,
STATUS_RESOURCE_NOT_AVAILABLE
} status_E;
extern string_t g_status_code_strings[3];
#endif //NOX_STATUS_H

View File

@ -35,7 +35,7 @@
#include "drivers/fs/vfs.h" #include "drivers/fs/vfs.h"
#include "proc/scheduler.h" #include "proc/scheduler.h"
#include "utils/io.h" #include "platform/syscall.h"
void limine_terminal_print(boot_info_T* boot_info, string_t string) { void limine_terminal_print(boot_info_T* boot_info, string_t string) {
boot_info->terminal->write(boot_info->terminal->terminals[0], string, string_length(string)); boot_info->terminal->write(boot_info->terminal->terminals[0], string, string_length(string));
@ -72,23 +72,21 @@ void kmain(boot_info_T boot_info) {
log(LOG_INFO, "!=====[ Kernel Initialized ]=====!\n"); log(LOG_INFO, "!=====[ Kernel Initialized ]=====!\n");
page_map_dump_info(g_kernel_page_map); status_E status = syscall_perform(SYSCALL_FILES_OPEN, (uint64_t)"/initrd/test.txt", 0, 0, 0);
vfs_node_T* node = vfs_resolve_path(&g_root_fs, "/initrd/test.elf"); log(LOG_DEBUG, "syscall returned status: %s", g_status_code_strings[status]);
void* buffer = memory_allocate(node->size);
vfs_file_read(node, 0, node->size, buffer);
elf_executable_T* exec = elf_executable_create(buffer); // vfs_node_T* node = vfs_resolve_path(&g_root_fs, "/initrd/test.elf");
// void* buffer = memory_allocate(node->size);
pid_t process = process_spawn(PROCESS_KERNEL, "test 1", exec, buffer); // vfs_file_read(node, 0, node->size, buffer);
void* func = (void*)symbol_resolve_from_name(scheduler_get_process(process)->executable->symbols, //
scheduler_get_process(process)->executable->num_symbols, // elf_executable_T* exec = elf_executable_create(buffer);
"_start")->address + MEM_REGION_PROCESS_EXEC; //
thread_start(thread_spawn(process, func)); // pid_t process = process_spawn(PROCESS_KERNEL, "test 1", exec, buffer);
// void* func = (void*)symbol_resolve_from_name(scheduler_get_process(process)->executable->symbols,
while (1){ // scheduler_get_process(process)->executable->num_symbols,
io_out_byte(0x3F8, 'B'); // "_start")->address + MEM_REGION_PROCESS_EXEC;
} // thread_start(thread_spawn(process, func));
// scheduler_dump_info(scheduler_get_process(PROCESS_KERNEL), 0); // scheduler_dump_info(scheduler_get_process(PROCESS_KERNEL), 0);

View File

@ -24,30 +24,53 @@
#include "platform/syscall.h" #include "platform/syscall.h"
#include "utils/logger.h" #include "utils/logger.h"
#include "proc/scheduler.h" #include "proc/scheduler.h"
#include "drivers/fs/vfs.h"
cpu_state_T* syscall_handle(cpu_state_T* state) { cpu_state_T* syscall_handle(cpu_state_T* state) {
cpu_state_T* return_state = state; cpu_state_T* return_state = state;
syscall_group_E group_id = (state->rax & 0xFF00) >> 8; syscall_group_E group_id = (state->rax & 0xFF00) >> 8;
// if (group_id == SYSCALLS_KERNEL && if (group_id == SYSCALLS_KERNEL &&
// scheduler_is_initialized() && scheduler_is_initialized() &&
// scheduler_get_current_process() != PROC_KERNEL) scheduler_get_current_process()->id != PROCESS_KERNEL)
// { {
// log(LOG_WARNING, "non kernel process[%d:%d] tried to perform a kernel syscall (permission denied)", scheduler_get_current_process(), scheduler_get_current_thread()); log(LOG_WARNING, "non kernel process[%d:%d] tried to perform a kernel syscall (permission denied)", scheduler_get_current_process(), scheduler_get_current_thread());
// return return_state; return return_state;
// } }
// read arguments
uint64_t arg1 = state->rdi;
uint64_t arg2 = state->rsi;
uint64_t arg3 = state->rdx;
uint64_t arg4 = state->rcx;
uint64_t ret = STATUS_SUCCESS;
switch (state->rax) { switch (state->rax) {
case SYSCALL_FILES_OPEN: {
vfs_node_T* node = vfs_resolve_path(&g_root_fs, (string_t)arg1);
if (node == NULL) {
ret = STATUS_RESOURCE_NOT_AVAILABLE;
break;
}
log(LOG_DEBUG, "resolved file '%s' -> 0x%x", arg1, node);
break;
}
case SYSCALL_KERNEL_SCHEDULER_START: { case SYSCALL_KERNEL_SCHEDULER_START: {
return_state = scheduler_start(state); return_state = scheduler_start(state);
break; break;
} }
default: { default: {
log(LOG_WARNING, "Unhandled syscall: 0x%xw RAX[0x%x]", state->rax, state->rax); log(LOG_WARNING, "unhandled syscall: 0x%xw", state->rax);
break; break;
} }
} }
// apply return value
state->rax = ret;
return return_state; return return_state;
} }

View File

@ -20,7 +20,18 @@
; OTHER DEALINGS IN THE SOFTWARE. ; OTHER DEALINGS IN THE SOFTWARE.
syscall_perform: syscall_perform:
; set the interrupt ID
mov rax, rdi mov rax, rdi
; set the arguments
mov rdi, rsi
mov rsi, rdx
mov rdx, rcx
mov rcx, r8
int 0x80 int 0x80
; the return value is already set in RAX
ret ret
GLOBAL syscall_perform GLOBAL syscall_perform

View File

@ -78,7 +78,7 @@ void scheduler_init(boot_info_T* boot_info) {
process_kernel_spawn(elf_executable_create(boot_info->kernel_file->address)); process_kernel_spawn(elf_executable_create(boot_info->kernel_file->address));
syscall_perform(SYSCALL_KERNEL_SCHEDULER_START); syscall_perform(SYSCALL_KERNEL_SCHEDULER_START, 0, 0, 0, 0);
} }
cpu_state_T* scheduler_start(cpu_state_T* state) { cpu_state_T* scheduler_start(cpu_state_T* state) {

31
kernel/src/utils/status.c Normal file
View File

@ -0,0 +1,31 @@
/*
* Copyright 2023 Antifallobst <antifallobst@systemausfall.org>
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of
* this software and associated documentation files (the Software), to deal in
* the Software without restriction, including without limitation the rights to use,
* copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the
* Software, and to permit persons to whom the Software is furnished to do so,
* subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED AS IS, WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
* OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
* OTHER DEALINGS IN THE SOFTWARE.
*/
#include "utils/status.h"
string_t g_status_code_strings[3] = {
"Success",
"Permission Denied",
"Resource Not Available"
};