提交 035cb8c1 编写于 作者: Z Zihao Yu

riscv64-noop: use independent vme.c and trap.S apart from riscv64-nemu

上级 fbe141b9
......@@ -4,9 +4,9 @@ AM_SRCS := $(ISA)/noop/trm.c \
$(ISA)/noop/uartlite.c \
$(ISA)/noop/perf.c \
$(ISA)/noop/cte.c \
$(ISA)/nemu/trap.S \
$(ISA)/noop/trap.S \
$(ISA)/noop/instr.c \
$(ISA)/nemu/vme.c \
$(ISA)/noop/vme.c \
nemu-common/ioe.c \
$(ISA)/noop/input.c \
nemu-common/nemu-timer.c \
......
......@@ -49,7 +49,7 @@ _Context* __am_irq_handle(_Context *c) {
}
}
// __am__switch(next);
__am_switch(next);
return next;
}
......@@ -73,7 +73,7 @@ _Context *_kcontext(_Area stack, void (*entry)(void *), void *arg) {
_Context *c = (_Context*)stack.end - 1;
c->mepc = (uintptr_t)entry;
c->mstatus = 0x000c0180;
c->mstatus = 0x000c1880;
return c;
}
......
// unmodified for cputest
#define concat_temp(x, y) x ## y
#define concat(x, y) concat_temp(x, y)
#define MAP(c, f) c(f)
#define REGS(f) \
f( 1) f( 3) f( 4) f( 5) f( 6) f( 7) f( 8) f( 9) \
f(10) f(11) f(12) f(13) f(14) f(15) f(16) f(17) f(18) f(19) \
f(20) f(21) f(22) f(23) f(24) f(25) f(26) f(27) f(28) f(29) \
f(30) f(31)
#define PUSH(n) sd concat(x, n), (n * 8)(sp);
#define POP(n) ld concat(x, n), (n * 8)(sp);
#define CONTEXT_SIZE ((31 + 4) * 8)
#define OFFSET_SP ( 2 * 8)
#define OFFSET_CAUSE (32 * 8)
#define OFFSET_STATUS (33 * 8)
#define OFFSET_EPC (34 * 8)
.globl __am_asm_trap
__am_asm_trap:
addi sp, sp, -CONTEXT_SIZE
MAP(REGS, PUSH)
mv t0, sp
addi t0, t0, CONTEXT_SIZE
sd t0, OFFSET_SP(sp)
csrr t0, mcause
csrr t1, mstatus
csrr t2, mepc
sd t0, OFFSET_CAUSE(sp)
sd t1, OFFSET_STATUS(sp)
sd t2, OFFSET_EPC(sp)
mv a0, sp
jal __am_irq_handle
mv sp, a0
ld t1, OFFSET_STATUS(sp)
ld t2, OFFSET_EPC(sp)
csrw mstatus, t1
csrw mepc, t2
MAP(REGS, POP)
addi sp, sp, CONTEXT_SIZE
mret
#include <riscv64.h>
#include <nemu.h>
#include <klib.h>
#define PG_ALIGN __attribute((aligned(PGSIZE)))
static _AddressSpace kas; // Kernel address space
static void* (*pgalloc_usr)(size_t) = NULL;
static void (*pgfree_usr)(void*) = NULL;
static int vme_enable = 0;
static _Area segments[] = { // Kernel memory mappings
{.start = (void*)0x80000000u, .end = (void*)(0x80000000u + 0x3000000)}, //PMEM_SIZE)},
{.start = (void*)0x40600000u, .end = (void*)(0x40600000u + 0x1000)}, // uart
{.start = (void*)0x40700000u, .end = (void*)(0x40700000u + 0x1000)}, // clint/timer
{.start = (void*)0x40000000u, .end = (void*)(0x40000000u + 0x400000)}, // vmem
{.start = (void*)0x40800000u, .end = (void*)(0x40800000u + 0x1000)} // vga ctrl
};
#define NR_KSEG_MAP (sizeof(segments) / sizeof(segments[0]))
static inline void set_satp(void *pdir) {
uintptr_t mode = 8ull << 60;
asm volatile("csrw satp, %0" : : "r"(mode | PN(pdir)));
}
int _vme_init(void* (*pgalloc_f)(size_t), void (*pgfree_f)(void*)) {
pgalloc_usr = pgalloc_f;
pgfree_usr = pgfree_f;
kas.ptr = pgalloc_f(1);
// make all PTEs invalid
memset(kas.ptr, 0, PGSIZE);
int i;
for (i = 0; i < NR_KSEG_MAP; i ++) {
void *va = segments[i].start;
for (; va < segments[i].end; va += PGSIZE) {
_map(&kas, va, va, 0);
}
}
set_satp(kas.ptr);
vme_enable = 1;
return 0;
}
int _protect(_AddressSpace *as) {
PTE *updir = (PTE *)(pgalloc_usr(1));
as->ptr = updir;
// map kernel space
memcpy(updir, kas.ptr, PGSIZE);
return 0;
}
void _unprotect(_AddressSpace *as) {
}
static _AddressSpace *cur_as = NULL;
void __am_get_cur_as(_Context *c) {
c->as = cur_as;
}
void __am_switch(_Context *c) {
if (vme_enable) {
set_satp(c->as->ptr);
cur_as = c->as;
}
}
int _map(_AddressSpace *as, void *va, void *pa, int prot) {
PTE *pg_base = as->ptr;
PTE *pte;
int level;
for (level = PTW_LEVEL - 1; level >= 0; level --) {
pte = &pg_base[VPNi((uintptr_t)va, level)];
pg_base = (PTE *)PTE_ADDR(*pte);
if (level != 0 && !(*pte & PTE_V)) {
pg_base = pgalloc_usr(1);
*pte = PTE_V | (PN(pg_base) << 10);
}
}
if (!(*pte & PTE_V)) {
*pte = PTE_V | PTE_R | PTE_W | PTE_X | (PN(pa) << 10);
}
return 0;
}
_Context *_ucontext(_AddressSpace *as, _Area ustack, _Area kstack, void *entry, void *args) {
_Context *c = (_Context*)ustack.end - 1;
c->gpr[10] = c->gpr[11] = 0;
c->as = as;
c->mepc = (uintptr_t)entry;
c->mstatus = 0x000c1880;
return c;
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册