diff options
| -rw-r--r-- | Makefile | 2 | ||||
| -rw-r--r-- | arch/riscv64/kernel/proc.c | 8 | ||||
| -rw-r--r-- | arch/riscv64/kernel/vmem.c | 9 | ||||
| -rw-r--r-- | common/tcb.c | 31 |
4 files changed, 34 insertions, 16 deletions
@@ -2,7 +2,7 @@ DO != echo -n > deps.mk # this could be done better DEBUGFLAGS != [ $(RELEASE) ] \ - && echo "-flto -O2 -g -DNDEBUG" \ + && echo "-flto -O2 -g -DDEBUG" \ || echo "-O0 -g -DDEBUG" CFLAGS = -ffreestanding -nostdlib -static -fno-pie -std=c17 -Wall -Wextra -Wvla -D$(ARCH) diff --git a/arch/riscv64/kernel/proc.c b/arch/riscv64/kernel/proc.c index 3c2ea59..b8f6c5d 100644 --- a/arch/riscv64/kernel/proc.c +++ b/arch/riscv64/kernel/proc.c @@ -65,20 +65,22 @@ vm_t get_stack(struct tcb *t) void save_regs(struct tcb *t, void *p) { struct riscv_regs *r = (struct riscv_regs *)(t) - 1; - memcpy(p, r, sizeof(*r)); + struct riscv_regs *rp = (struct riscv_regs *)(p); + *rp = *r; } void load_regs(void *p, struct tcb *t) { struct riscv_regs *r = (struct riscv_regs *)(t) - 1; - memcpy(r, p, sizeof(*r)); + struct riscv_regs *rp = (struct riscv_regs *)(p); + *r = *rp; } void clone_regs(struct tcb *d, struct tcb *s) { struct riscv_regs *rd = (struct riscv_regs *)(d) - 1; struct riscv_regs *rs = (struct riscv_regs *)(s) - 1; - memcpy(rd, rs, sizeof(*rs)); + *rd = *rs; } void adjust_ipi(struct tcb *t) diff --git a/arch/riscv64/kernel/vmem.c b/arch/riscv64/kernel/vmem.c index 68ccbd3..a3903f1 100644 --- a/arch/riscv64/kernel/vmem.c +++ b/arch/riscv64/kernel/vmem.c @@ -345,11 +345,16 @@ vm_t setup_kernel_io(struct vmem *b, vm_t paddr) } #endif +struct uvmem_map { + struct vmem *leaf[CSTACK_PAGE - 1]; +}; + stat_t clone_uvmem(struct vmem *r, struct vmem *b) { /** \todo error checking? */ - for (size_t i = 0; i < CSTACK_PAGE; ++i) - b->leaf[i] = r->leaf[i]; + struct uvmem_map *rm = (struct uvmem_map *)(r); + struct uvmem_map *bm = (struct uvmem_map *)(b); + *bm = *rm; return OK; } diff --git a/common/tcb.c b/common/tcb.c index daaae4d..478bd05 100644 --- a/common/tcb.c +++ b/common/tcb.c @@ -407,6 +407,12 @@ static void mark_rpc_accessible(struct tcb *t, vm_t start, vm_t end) set_vpage_flags(t->rpc.vmem, start + pages * page_size, VM_U); } +struct call_ctx { + vm_t exec; + vm_t rpc_stack; + id_t eid, pid; +}; + void save_context(struct tcb *t) { vm_t rpc_stack = t->rpc_stack; @@ -414,11 +420,15 @@ void save_context(struct tcb *t) /** @todo what if user uses their own stack? */ rpc_stack = align_down(get_stack(t), BASE_PAGE_SIZE); - struct tcb *copy = (struct tcb *)(rpc_stack - sizeof(struct tcb)); - memcpy(copy, t, sizeof(struct tcb)); - clone_regs(copy, t); - rpc_stack -= BASE_PAGE_SIZE; + + struct call_ctx *ctx = (struct call_ctx *)rpc_stack; + ctx->exec = t->exec; + ctx->pid = t->pid; + ctx->eid = t->eid; + ctx->rpc_stack = rpc_stack + BASE_PAGE_SIZE; + save_regs(t, ctx + 1); + mark_rpc_inaccessible(t, rpc_stack, t->rpc_stack); t->rpc_stack = rpc_stack; } @@ -426,10 +436,11 @@ void save_context(struct tcb *t) void load_context(struct tcb *t) { vm_t rpc_stack = t->rpc_stack; - struct tcb *copy = - (struct tcb *)(rpc_stack + BASE_PAGE_SIZE - sizeof(struct tcb)); - memcpy(t, copy, sizeof(struct tcb)); - clone_regs(t, copy); - - mark_rpc_accessible(t, rpc_stack, t->rpc_stack); + struct call_ctx *ctx = (struct call_ctx *)rpc_stack; + set_return(t, ctx->exec); + mark_rpc_accessible(t, t->rpc_stack, ctx->rpc_stack); + load_regs(ctx + 1, t); + t->rpc_stack = ctx->rpc_stack; + t->pid = ctx->pid; + t->eid = ctx->eid; } |
