Merge branch 'syscall-args' into 'master'
am,asye: use macros `SYSCALL_ARGx()` to get syscall arguments See merge request !136
This commit is contained in:
commit
1173fc6d21
3
SPEC.md
3
SPEC.md
|
@ -46,7 +46,8 @@
|
|||
* `_EVENT_BUS_ERROR`:总线错误(cause: 产生错误的地址)
|
||||
* `_EVENT_NUMERIC`:数值错误(无cause)
|
||||
* `_EVENT_TRAP`:内核态自陷(无cause)
|
||||
* `_EVENT_SYSCALL`: 系统调用(无cause),系统调用参数将`_RegSet`转换为`intptr_t*`后按次序排列。第一个参数为返回值。
|
||||
* `_EVENT_SYSCALL`: 系统调用(无cause)
|
||||
* `SYSCALL_ARGx(reg);`从寄存器现场中获取系统调用的参数。其中`x`为`1`~`4`。
|
||||
* `_RegSet *_make(_Area kstack, void *entry, void *arg);`创建一个内核上下文,参数arg。
|
||||
* `void _trap();`在内核态自陷。线程需要睡眠/让出CPU时使用。
|
||||
* `int _istatus(int enable);`设置中断状态(enable非0时打开)。返回设置前的中断状态(0/1)。
|
||||
|
|
|
@ -16,6 +16,10 @@ struct _RegSet {
|
|||
};
|
||||
|
||||
typedef struct _RegSet TrapFrame;
|
||||
#define SYSCALL_ARG1(r) ((r)->eax)
|
||||
#define SYSCALL_ARG2(r) ((r)->ebx)
|
||||
#define SYSCALL_ARG3(r) ((r)->ecx)
|
||||
#define SYSCALL_ARG4(r) ((r)->edx)
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
|
|
@ -12,27 +12,14 @@ uintptr_t irq_handle(_RegSet *r) {
|
|||
_RegSet *next = r;
|
||||
if (H) {
|
||||
_Event ev;
|
||||
intptr_t args[4];
|
||||
switch (r->irq) {
|
||||
case 32: ev.event = _EVENT_IRQ_TIME; break;
|
||||
case 0x80: {
|
||||
ev.event = _EVENT_SYSCALL;
|
||||
args[0] = r->eax;
|
||||
args[1] = r->ebx;
|
||||
args[2] = r->ecx;
|
||||
args[3] = r->edx;
|
||||
ev.cause = (intptr_t)args;
|
||||
break;
|
||||
}
|
||||
case 0x80: ev.event = _EVENT_SYSCALL; break;
|
||||
case 0x81: ev.event = _EVENT_TRAP; break;
|
||||
default: ev.event = _EVENT_ERROR; break;
|
||||
}
|
||||
|
||||
next = H(ev, r);
|
||||
if (ev.event == _EVENT_SYSCALL) {
|
||||
r->eax = args[0];
|
||||
}
|
||||
|
||||
if (next == NULL) {
|
||||
next = r;
|
||||
}
|
||||
|
|
|
@ -1,14 +1,15 @@
|
|||
#include "common.h"
|
||||
|
||||
_RegSet* schedule(_RegSet *);
|
||||
_RegSet* do_syscall(uintptr_t *);
|
||||
_RegSet* do_syscall(_RegSet *);
|
||||
|
||||
static _RegSet* do_event(_Event e, _RegSet* r) {
|
||||
_RegSet *ret = NULL;
|
||||
|
||||
switch (e.event) {
|
||||
case _EVENT_IRQ_TIME: ret = schedule(r); break;
|
||||
case _EVENT_TRAP: ret = schedule(r); break;
|
||||
case _EVENT_SYSCALL: ret = do_syscall((uintptr_t *)e.cause); break;
|
||||
case _EVENT_SYSCALL: ret = do_syscall(r); break;
|
||||
default: panic("Unhandled event ID = %d", e.event);
|
||||
}
|
||||
|
||||
|
|
|
@ -37,19 +37,27 @@ int sys_brk(uintptr_t brk) {
|
|||
return mm_brk(brk);
|
||||
}
|
||||
|
||||
_RegSet* do_syscall(uintptr_t *args) {
|
||||
_RegSet* do_syscall(_RegSet *r) {
|
||||
int ret = 0;
|
||||
switch (args[0]) {
|
||||
case SYS_exit: sys_exit(args[1]); break;
|
||||
case SYS_read: ret = sys_read(args[1], (void *)args[2], args[3]); break;
|
||||
case SYS_write: ret = sys_write(args[1], (const void *)args[2], args[3]); break;
|
||||
case SYS_open: ret = sys_open((const char *)args[1], args[2], args[3]); break;
|
||||
case SYS_lseek: ret = sys_lseek(args[1], args[2], args[3]); break;
|
||||
case SYS_close: ret = sys_close(args[1]); break;
|
||||
case SYS_brk: ret = sys_brk(args[1]); break;
|
||||
default: panic("Unhandled syscall ID = %d", args[0]);
|
||||
uintptr_t a[4];
|
||||
a[0] = SYSCALL_ARG1(r);
|
||||
a[1] = SYSCALL_ARG2(r);
|
||||
a[2] = SYSCALL_ARG3(r);
|
||||
a[3] = SYSCALL_ARG4(r);
|
||||
Log("syscall = %d", a[0]);
|
||||
|
||||
switch (a[0]) {
|
||||
case SYS_none: break;
|
||||
case SYS_exit: sys_exit(a[1]); break;
|
||||
case SYS_read: ret = sys_read(a[1], (void *)a[2], a[3]); break;
|
||||
case SYS_write: ret = sys_write(a[1], (const void *)a[2], a[3]); break;
|
||||
case SYS_open: ret = sys_open((const char *)a[1], a[2], a[3]); break;
|
||||
case SYS_lseek: ret = sys_lseek(a[1], a[2], a[3]); break;
|
||||
case SYS_close: ret = sys_close(a[1]); break;
|
||||
case SYS_brk: ret = sys_brk(a[1]); break;
|
||||
default: panic("Unhandled syscall ID = %d", a[0]);
|
||||
}
|
||||
|
||||
args[0] = ret;
|
||||
SYSCALL_ARG1(r) = ret;
|
||||
return NULL;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue