v0.5.3-pre: refactor syscall handlers and introduce libterm

Moved handlers to syscalls/, implemented libterm (malloc, stdio)
This commit is contained in:
Karina
2026-01-30 04:58:43 +04:00
parent 9c103218d0
commit 888bc5abdd
41 changed files with 818 additions and 103 deletions
+1 -1
View File
@@ -1,7 +1,7 @@
// SPDX-License-Identifier: GPL-3.0-or-later
// Copyright (c) 2026 0xKarinyash
#include "types.h"
#include <types.h>
#include <cpuinfo.h>
#define MSR_GS_BASE 0xC0000101
-1
View File
@@ -60,7 +60,6 @@ syscall_entry:
pop r11 ; rflags
add rsp, 8 ; skip rsp
mov [gs:8], rsp
mov rsp, [gs:0]
swapgs
+11 -13
View File
@@ -8,6 +8,10 @@
#include <mm/pmm.h>
#include <mm/vmm.h>
#include <syscalls/proc.h>
#include <syscalls/mem.h>
#include <syscalls/io.h>
static inline void wrmsr(u32 msr, u64 val) {
u32 low = (u32)val;
u32 high = (u32)(val >> 32);
@@ -47,20 +51,14 @@ void syscall_init() {
}
u64 syscall_dispatch(u64 id, u64 arg1, u64 arg2, u64 arg3, u64 arg4, u64 arg5) {
__asm__ volatile("cli");
switch (id) {
case SYS_EXIT: {
kprintf("\n[Dewar] process exited with code %d", arg1);
while(1) __asm__ ("hlt"); // stub
return 0;
}
case SYS_EXEC: {
kprintf("\n[Dewar] process called exec syscall");
return 0; // stub as well
}
case SYS_WRITE: {
kprintf("%s", (char*)arg1);
return 0;
}
case SYS_EXIT: return sys_exit(arg1);
case SYS_SPAWN: return sys_spawn((const char*)arg1);
case SYS_MEM: return sys_mem(arg1);
case SYS_WRITE: return sys_write(arg1, arg2, arg3);
case SYS_READ: return sys_read(arg1, arg2, arg3);
default: kprintf("[Dewar] Unknown syscall %d\n", id); return -1;
}
__asm__ volatile("sti");
}
+16 -13
View File
@@ -19,27 +19,30 @@ u64 load_hot(process* proc, u8* data) {
}
hot_segment* segments = (hot_segment*)(data + sizeof(hot_header));
u64 kernel_cr3 = vmm_get_current_cr3();
for (u64 i = 0; i < header->segments_count; i++) {
hot_segment* seg = &segments[i];
if (seg->memsz == 0) continue;
u64 start = seg->vaddr & ~(0xFFF);
u64 end = (seg->vaddr + seg->memsz + 0xFFF) & ~(0xFFF);
u64 start = seg->vaddr & ~(0xFFFULL);
u64 end = (seg->vaddr + seg->memsz + 0xFFF) & ~(0xFFFULL);
for (u64 addr = start; addr < end; addr += PAGE_SIZE) {
void* phys = pmm_alloc_page();
vmm_map_page((u64*)proc->pml4_phys, (u64)phys, addr, PTE_USER | PTE_RW | PTE_PRESENT);
}
vmm_map_page((u64*)proc->pml4_phys, (u64)phys, addr, PTE_USER | PTE_RW | PTE_PRESENT);
void* kernel_virt = (void*)((u64)phys + HHDM_OFFSET);
memset(kernel_virt, 0, PAGE_SIZE);
u64 page_overleap_start = (addr > seg->vaddr) ? addr : seg->vaddr;
u64 page_overleap_end = (addr + PAGE_SIZE < seg->vaddr + seg->filesz)
? (addr + PAGE_SIZE)
: (seg->vaddr + seg->filesz);
if (page_overleap_start < page_overleap_end) {
u64 copy_size = page_overleap_end - page_overleap_start;
u64 src_offset = seg->offset + (page_overleap_start - seg->vaddr);
u64 dst_offset = page_overleap_start - addr;
load_cr3(proc->pml4_phys);
if (seg->filesz > 0) memcpy((void*)seg->vaddr, data + seg->offset, seg->filesz);
if (seg->memsz > seg->filesz) {
u64 bss_start = seg->vaddr + seg->filesz;
u64 bss_len = seg->memsz - seg->filesz;
memset((void*)bss_start, 0, bss_len);
memcpy((u8*)kernel_virt + dst_offset, data + src_offset, copy_size);
}
}
load_cr3(kernel_cr3);
}
return header->entry_point;
+35 -15
View File
@@ -20,28 +20,48 @@
#include <types.h>
extern task* curr_task;
extern u32 next_pid;
#define USER_STACK_TOP 0x70000000
#define HEAP_START 0x40000000
void init_task_entry() {
process* init_proc = (process*)malloc(sizeof(process));
init_proc->pid = 1;
init_proc->state = RUNNING;
init_proc->pml4_phys = vmm_create_address_space();
strcpy(init_proc->name, "init");
i32 process_spawn(const char* path, const char* name) {
fs_node* file = vfs_open(path);
if (!file) return -1;
fs_node* file = vfs_open("/init");
if (!file) panic("FATAL: /init not found!");
process* new_proc = (process*)malloc(sizeof(process));
if (!new_proc) return -2;
memset(new_proc, 0, sizeof(process));
new_proc->pid = next_pid++;
new_proc->state = RUNNING;
new_proc->pml4_phys = vmm_create_address_space();
new_proc->heap_start = HEAP_START;
new_proc->heap_cur = HEAP_START;
strncpy(new_proc->name, name, 31);
u8* file_buffer = (u8*)malloc(file->len);
if (!file_buffer) {
free(new_proc);
return -3;
}
vfs_read(file, 0, file->len, file_buffer);
u64 entry = load_hot(init_proc, file_buffer);
if (!entry) panic("Invalid HOT executable");
free(file_buffer);
vmm_setup_user_stack((u64*)init_proc->pml4_phys);
sched_spawn((void(*)())entry, init_proc, true, USER_STACK_TOP);
u64 entry = load_hot(new_proc, file_buffer);
if (!entry) return -4;
while(1) { __asm__("sti; hlt"); }
free(file_buffer);
vmm_setup_user_stack((u64*)new_proc->pml4_phys);
sched_spawn((void(*)())entry, new_proc, true, USER_STACK_TOP);
return new_proc->pid;
}
void init_task_entry() {
i32 pid = process_spawn("/init", "init");
if (pid < 0) {
panic("FATAL: Failed to spawn /init");
}
while (1) { __asm__("sti; hlt"); }
}
-1
View File
@@ -32,7 +32,6 @@ const char* fun_messages[] = {
"Code have been eaten by Aliens",
"That's all, folks!",
"Raiden, answer me, Raiden, respond! Raiden?! RAIDEEEEEEEEEN!",
"Fatal error has been occurred.\n\t\t\t\t Your device will be terminated in 30 seconds.",
"I'll be back",
"Hastla la vista, baby",
"Ti chego mne tut nagovoril...",
+17
View File
@@ -6,6 +6,7 @@
#include <core/string.h>
#include <mm/heap.h>
#include <mm/vmm.h>
#include <mm/memory.h>
#include <cpuinfo.h>
#include <gdt.h>
@@ -17,6 +18,12 @@ extern u64 pml4_kernel_phys;
static process kernel_process;
void idle_task() {
while (1) {
__asm__ volatile ("hlt");
}
}
void sched_init() {
kernel_process.pid = 0;
kernel_process.state = RUNNING;
@@ -24,12 +31,15 @@ void sched_init() {
strcpy(kernel_process.name, "kernel");
task* kt = (task*)malloc(sizeof(task));
memset(kt, 0, sizeof(task));
kt->id = 0;
kt->proc = &kernel_process;
kt->sleep_ticks = 0;
kt->next = kt;
kt->task_state = RUNNING;
curr_task = kt;
sched_spawn(idle_task, &kernel_process, false, 0);
}
task* sched_spawn(void(*entry)(), process* owner, bool is_user, u64 fixed_user_stack) {
@@ -66,6 +76,7 @@ task* sched_spawn(void(*entry)(), process* owner, bool is_user, u64 fixed_user_s
t->sleep_ticks = 0;
t->next = curr_task->next;
t->kernel_stack_top = (u64)stack_base + stack_size;
t->task_state = RUNNING;
curr_task->next = t;
return t;
}
@@ -84,6 +95,12 @@ u64 sched_next(u64 curr_rsp) {
if (curr_task->sleep_ticks > 0) curr_task->sleep_ticks--;
task* next = curr_task->next;
while (next->task_state == DEAD) {
// TODO: add gc here;
next = next->next;
if (next == curr_task) panic("no alive tasks");
}
while (next != curr_task && next->sleep_ticks > 0) next = next->next; // what the fuck i just wrote
if (next->proc->pml4_phys != curr_task->proc->pml4_phys) load_cr3(next->proc->pml4_phys);
+1 -1
View File
@@ -80,7 +80,7 @@ void console_set_cursor_pos(SG_Point *p) {
s_cursor_pos.y = p->y;
}
static void console_putc(char c) {
void console_putc(char c) {
serial_writec(c);
if (!ctx_ptr) return;
if (c == '\n') {
+27
View File
@@ -0,0 +1,27 @@
// SPDX-License-Identifier: GPL-3.0-or-later
// Copyright (c) 2026 0xKarinyash
#include <syscalls/io.h>
#include <drivers/console.h>
u64 sys_write(u64 fd, u64 buff, u64 len) {
if (fd == 1 || fd == 2) {
char* str = (char*)buff;
for (u64 i = 0; i < len; i++) {
console_putc(str[i]);
}
return len;
}
return 0;
}
u64 sys_read(u64 fd, u64 buff, u64 count) {
char* buf = (char*)buff;
if (fd == 0) {
for (u64 i = 0; i < count; i++) {
buf[i] = console_getc();
}
return count;
}
return 0;
}
+32
View File
@@ -0,0 +1,32 @@
// SPDX-License-Identifier: GPL-3.0-or-later
// Copyright (c) 2026 0xKarinyash
#include <syscalls/mem.h>
#include <core/scheduler.h>
#include <mm/pmm.h>
#include <mm/vmm.h>
#include <mm/memory.h>
extern task* curr_task;
u64 sys_mem(u64 size) {
if (size == 0) return 0;
process* proc = curr_task->proc;
u64 addr_to_ret = proc->heap_cur;
u64 pages_needed = (size + (PAGE_SIZE-1)) / PAGE_SIZE;
for (u64 i = 0; i < pages_needed; i++) {
void* phys = pmm_alloc_page();
if (!phys) return 0;
vmm_map_page((u64*)proc->pml4_phys, (u64)phys, proc->heap_cur, PTE_PRESENT | PTE_RW | PTE_USER);
memset((void*)PHYS_TO_HHDM((u64)phys), 0, PAGE_SIZE);
proc->heap_cur += 4096;
}
return addr_to_ret;
}
+22
View File
@@ -0,0 +1,22 @@
// SPDX-License-Identifier: GPL-3.0-or-later
// Copyright (c) 2026 0xKarinyash
#include <syscalls/proc.h>
#include <core/scheduler.h>
#include <drivers/console.h>
#include <core/loader.h>
extern task* curr_task;
u64 sys_exit(i32 code) {
kprintf("\n[Dewar] process %s exited with code %d", curr_task->proc->name, code);
curr_task->task_state = DEAD;
sched_next(curr_task->rsp);
while (1) { __asm__ ("hlt"); }
}
u64 sys_spawn(const char* path) {
return process_spawn(path, path);
}