kernel: syscalls

This commit is contained in:
Matheus
2023-05-07 20:22:51 -03:00
parent ca80c22f50
commit 8c3b2f4947
4 changed files with 131 additions and 1 deletions
+109
View File
@@ -0,0 +1,109 @@
section .rodata
syscalltab:
syscallcount equ 0
section .text
global arch_syscall_entry
; on entry:
; rcx has the return address
; r11 has the old rflags
; syscall arguments:
; rax has the syscall number
; rdi has the first argument
; rsi has the second argument
; rdx has the third argument
; r10 has the fourth argument
; r8 has the fifth argument
; r9 has the sixth argument
; return:
; rdx has errno
; rax has return value
arch_syscall_entry:
swapgs
; save return address on user stack
push rcx
mov rcx, [gs:0x0] ; thread pointer
mov rcx, [rcx] ; kernel stack top
xchg rsp, rcx ; switch stack pointers
; push context
push qword 0x1b ; user SS
push qword rcx
add qword [rsp], 8 ; correct the old stack pointer to before the return address push
push r11 ; rflags is stored in r11
push qword 0x23 ; user CS
push qword [rcx] ; save return RIP
push qword 0 ; error
push rbp
push rsi
push rdi
push r15
push r14
push r13
push r12
push r11
push r10
push r9
push r8
push rdx
push rcx
push rbx
push rax
mov rbx, ds
push rbx
mov rbx, es
push rbx
mov rbx, fs
push rbx
mov rbx, gs
push rbx
mov rbx, cr2
push rbx
; prepare arguments for the functions
push r9
mov r9, r8
mov r8, r10
mov rcx, rdx
mov rdx, rsi
mov rsi, rdi
mov rdi, rsp
sti
cmp rax, syscallcount
jae .nosyscall
call [syscalltab + rax * 8]
jmp .return
.nosyscall:
extern syscall_invalid
call syscall_invalid
.return:
cli
; restore context
add rsp, 32 ; r9 argument, cr2, gs, and fs are not popped.
pop rbx
mov es,rbx
pop rbx
mov ds,rbx
add rsp, 8 ; rax
pop rbx
pop rcx
add rsp, 8 ; rdx
pop r8
pop r9
pop r10
pop r11
pop r12
pop r13
pop r14
pop r15
pop rdi
pop rsi
pop rbp
add rsp, 8 ; remove error code
pop rcx
add rsp, 8 ; user CS
pop r11 ; rflags
pop rsp
swapgs
o64 sysret
+1 -1
View File
@@ -14,6 +14,7 @@
struct proc_t;
typedef struct thread_t {
void *kernelstacktop;
struct thread_t *next;
struct thread_t *prev;
struct proc_t *proc;
@@ -21,7 +22,6 @@ typedef struct thread_t {
context_t context;
extracontext_t extracontext;
void *kernelstack;
void *kernelstacktop;
size_t kernelstacksize;
vmmcontext_t *vmmctx;
tid_t tid;
+11
View File
@@ -0,0 +1,11 @@
#ifndef _SYSCALLS_H
#define _SYSCALLS_H
#include <stdint.h>
typedef struct {
uint64_t ret;
uint64_t errno;
} syscallret_t;
#endif
+10
View File
@@ -0,0 +1,10 @@
#include <kernel/syscalls.h>
#include <errno.h>
syscallret_t syscall_invalid() {
syscallret_t ret = {
.errno = ENOSYS,
.ret = -1
};
return ret;
}