diff --git a/libs/libc/include/luna/syscall.h b/libs/libc/include/luna/syscall.h index 3112cd0c..fae8482c 100644 --- a/libs/libc/include/luna/syscall.h +++ b/libs/libc/include/luna/syscall.h @@ -1,17 +1,32 @@ -#ifndef _SYSCALL_H -#define _SYSCALL_H +#ifndef _LUNA_SYSCALL_H +#define _LUNA_SYSCALL_H #define SYS_exit 0 +#define SYS_yield 1 +#define SYS_sleep 2 +#define SYS_write 3 +#define SYS_paint 4 +#define SYS_rand 5 +#define SYS_version 6 +#define SYS_gettid 7 +#ifndef __want_syscalls #ifdef __cplusplus extern "C" { #endif - long int __syscall0(int sys_num); + long int __luna_syscall0(int sys_num); + long int __luna_syscall1(int sys_num, unsigned long int arg0); + long int __luna_syscall2(int sys_num, unsigned long int arg0, unsigned long int arg1); + long int __luna_syscall3(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2); + long int __luna_syscall4(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2, + unsigned long int arg3); + long int __luna_syscall5(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2, + unsigned long int arg3, unsigned long int arg4); #ifdef __cplusplus } #endif - +#endif #endif \ No newline at end of file diff --git a/libs/libc/include/sys/syscall.h b/libs/libc/include/sys/syscall.h new file mode 100644 index 00000000..41de7d74 --- /dev/null +++ b/libs/libc/include/sys/syscall.h @@ -0,0 +1,9 @@ +#ifndef _SYS_SYSCALL_H +#define _SYS_SYSCALL_H + +#define __want_syscalls +#include +#undef __want_syscalls +#undef _LUNA_SYSCALL_H + +#endif \ No newline at end of file diff --git a/libs/libc/include/unistd.h b/libs/libc/include/unistd.h index cdc2e435..cb3fd234 100644 --- a/libs/libc/include/unistd.h +++ b/libs/libc/include/unistd.h @@ -9,6 +9,8 @@ extern "C" int execve(const char*, char* const[], char* const[]); int execvp(const char*, char* const[]); pid_t fork(void); + long syscall(long, ...); + #ifdef __cplusplus } #endif diff --git a/libs/libc/src/luna/syscall.c b/libs/libc/src/luna/syscall.c new file mode 100644 index 00000000..b4d15fcf --- /dev/null +++ b/libs/libc/src/luna/syscall.c @@ -0,0 +1,48 @@ +#include + +long int __luna_syscall0(int sys_num) +{ + long int result; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num)); + return result; +} + +long int __luna_syscall1(int sys_num, unsigned long int arg0) +{ + long int result; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num), "D"(arg0)); + return result; +} + +long int __luna_syscall2(int sys_num, unsigned long int arg0, unsigned long int arg1) +{ + long int result; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num), "D"(arg0), "S"(arg1)); + return result; +} + +long int __luna_syscall3(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2) +{ + long int result; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num), "D"(arg0), "S"(arg1), "d"(arg2)); + return result; +} + +long int __luna_syscall4(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2, + unsigned long int arg3) +{ + long int result; + register unsigned long int value0 asm("r10") = arg3; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num), "D"(arg0), "S"(arg1), "d"(arg2), "r"(value0)); + return result; +} + +long int __luna_syscall5(int sys_num, unsigned long int arg0, unsigned long int arg1, unsigned long int arg2, + unsigned long int arg3, unsigned long int arg4) +{ + long int result; + register unsigned long int value0 asm("r10") = arg3; + register unsigned long int value1 asm("r10") = arg4; + asm volatile("int $0x42" : "=a"(result) : "a"(sys_num), "D"(arg0), "S"(arg1), "d"(arg2), "r"(value0), "r"(value1)); + return result; +} \ No newline at end of file diff --git a/libs/libc/src/luna/syscall.cpp b/libs/libc/src/luna/syscall.cpp deleted file mode 100644 index c265638f..00000000 --- a/libs/libc/src/luna/syscall.cpp +++ /dev/null @@ -1,12 +0,0 @@ -#include -#include - -extern "C" -{ - long int __syscall0(int sys_num) - { - long int result; - asm volatile("int $0x42" : "=a"(result) : "a"(sys_num)); - return result; - } -} \ No newline at end of file diff --git a/libs/libc/src/stdlib.cpp b/libs/libc/src/stdlib.cpp index 31f7d6a5..3aa49bb5 100644 --- a/libs/libc/src/stdlib.cpp +++ b/libs/libc/src/stdlib.cpp @@ -1,5 +1,8 @@ -#include #include +#include +#include + +#define noreturn __attribute__((noreturn)) #define maybe_unused __attribute__((maybe_unused)) #define unused __attribute__((unused)) @@ -13,7 +16,7 @@ extern "C" noreturn void exit(int) { - __syscall0(SYS_exit); + syscall(SYS_exit); __builtin_unreachable(); } diff --git a/libs/libc/src/unistd.cpp b/libs/libc/src/unistd.cpp index 7e2dc820..cf7417b6 100644 --- a/libs/libc/src/unistd.cpp +++ b/libs/libc/src/unistd.cpp @@ -1,3 +1,5 @@ +#include +#include #include extern "C" @@ -18,4 +20,39 @@ extern "C" { return -1; } + + long syscall(long number, ...) + { + typedef unsigned long int arg; + long result; + va_list ap; + va_start(ap, number); + switch (number) + { + case SYS_exit: + case SYS_yield: + case SYS_gettid: + case SYS_rand: result = __luna_syscall0(number); break; + case SYS_sleep: result = __luna_syscall1(number, va_arg(ap, arg)); break; + case SYS_write: + case SYS_version: { + arg arg0 = va_arg(ap, arg); + arg arg1 = va_arg(ap, arg); + result = __luna_syscall2(number, arg0, arg1); + break; + } + case SYS_paint: { + arg arg0 = va_arg(ap, arg); + arg arg1 = va_arg(ap, arg); + arg arg2 = va_arg(ap, arg); + arg arg3 = va_arg(ap, arg); + arg arg4 = va_arg(ap, arg); + result = __luna_syscall5(number, arg0, arg1, arg2, arg3, arg4); + break; + } + default: result = -1; break; + } + va_end(ap); + return result; + } } \ No newline at end of file