diff --git a/cpu/riscv.c b/cpu/riscv.c index ed92202..4c7c4bd 100644 --- a/cpu/riscv.c +++ b/cpu/riscv.c @@ -698,6 +698,7 @@ int riscv_init(riscv_t* riscv, uint32_t* rom, uint32_t rom_addr_base, uint32_t r riscv->rom_size = rom_size; riscv->rom_addr_base = rom_addr_base; riscv->pc = riscv->rom_addr_base; + riscv->ra = 0xffffffff; return 0; } @@ -732,8 +733,8 @@ int riscv_irq_check(riscv_t* riscv) { irq_num = 11; } riscv->mtval = 0; - riscv_enter_trap(riscv, 1, irq_num); if (irq_num>0) { + riscv_enter_trap(riscv, 1, irq_num); riscv->mip &= ~(1 << irq_num); irq_num = 0; } @@ -746,15 +747,14 @@ int riscv_run(riscv_t* riscv) { int ret = 0; uint32_t pc; while (1) { - if (riscv->pc == 0) { + if (riscv->pc == 0xfffffffe && riscv->ra == 0xffffffff) { break; } if (riscv->pc >= riscv->rom_addr_base + riscv->rom_size || riscv->pc < riscv->rom_addr_base) { // 指令访问失败 riscv->mtval = riscv->pc; - printf("riscv run out of rom pc=%08x\n",riscv->pc); + // printf("riscv run out of rom pc=%08x\n",riscv->pc); riscv_enter_trap(riscv, 0, 1); - printf("riscv run out of rom pc=%08x\n",riscv->pc); } if (riscv->pc & 0x3) { // 指令地址未对齐 diff --git a/riscv/interrupt.c b/riscv/interrupt.c index a5e7fdf..f28d854 100644 --- a/riscv/interrupt.c +++ b/riscv/interrupt.c @@ -7,7 +7,72 @@ void interrupt_entry(uint32_t irq_num) { my_printf("interrupt_entry %d\n", irq_num); } -void trap_entry(uint32_t irq_num) { - my_printf("trap_entry %d\n", irq_num); - write_csr(mscratch, 0xffffffff); + + +static const char *g_fault_cause[]={ + "Instruction address misaligned",// 0 + "Instruction access fault",// 1 + "Illegal instruction",// 2 + "Breakpoint",// 3 + "Load address misaligned",// 4 + "Load access fault",// 5 + "Store address misaligned",// 6 + "Store access fault",// 7 + "Environment call from U-mode",// 8 + "Environment call from S-mode",// 9 + "", + "Environment call from M-mode",// 11 + "Instruction page fault",// 12 + "Load page fault",// 13 + "", + "Store page fault",// 15 +}; + + + + +void trap_entry(uint32_t irq_num, stack_context *stack) { + my_printf("fault reason is %s\n", g_fault_cause[irq_num]); + my_printf("x1(ra): %08x\n", stack->ra); + my_printf("x2(sp): %08x\n", stack->sp); + my_printf("x3(gp): %08x\n", stack->gp); + my_printf("x4(tp): %08x\n", stack->tp); + my_printf("x5(t0): %08x\n", stack->t0); + my_printf("x6(t1): %08x\n", stack->t1); + my_printf("x7(t2): %08x\n", stack->t2); + my_printf("x8(s0|fp): %08x\n", stack->s0); + my_printf("x9(s1): %08x\n", stack->s1); + my_printf("x10(a0): %08x\n", stack->a0); + my_printf("x11(a1): %08x\n", stack->a1); + my_printf("x12(a2): %08x\n", stack->a2); + my_printf("x13(a3): %08x\n", stack->a3); + my_printf("x14(a4): %08x\n", stack->a4); + my_printf("x15(a5): %08x\n", stack->a5); + my_printf("x16(a6): %08x\n", stack->a6); + my_printf("x17(a7): %08x\n", stack->a7); + my_printf("x18(s2): %08x\n", stack->s2); + my_printf("x19(s3): %08x\n", stack->s3); + my_printf("x20(s4): %08x\n", stack->s4); + my_printf("x21(s5): %08x\n", stack->s5); + my_printf("x22(s6): %08x\n", stack->s6); + my_printf("x23(s7): %08x\n", stack->s7); + my_printf("x24(s8): %08x\n", stack->s8); + my_printf("x25(s9): %08x\n", stack->s9); + my_printf("x26(s10): %08x\n", stack->s10); + my_printf("x27(s11): %08x\n", stack->s11); + my_printf("x28(t3): %08x\n", stack->t3); + my_printf("x29(t4): %08x\n", stack->t4); + my_printf("x30(t5): %08x\n", stack->t5); + my_printf("x31(t6): %08x\n", stack->t6); + my_printf("mstatus: %08x\n", stack->mstatus); + my_printf("mepc: %08x\n", stack->mepc); + my_printf("mtval: %08x\n", read_csr(mtval)); + + // 函数调用错误,直接跳过这个函数 + if(irq_num==1){ + my_printf("skip the function call, return to %08x\n", stack->ra); + stack->mepc = stack->ra; + } + + // write_csr(mscratch, 0xffffffff); } diff --git a/riscv/main.c b/riscv/main.c index 6b2a9a1..ed9b092 100644 --- a/riscv/main.c +++ b/riscv/main.c @@ -44,13 +44,15 @@ int main() { int a=1; int b=2; - // typedef void (*fun_t)(void); - // fun_t fun = (fun_t)0xffffffff; - // fun(); + typedef void (*fun_t)(void); + fun_t fun = (fun_t)0; + fun(); int c = add(a, b); my_printf("Hello World! %s\n", "Andy"); my_printf("add(%d, %d)=%d\n", a, b, c); a = 67;b = -78; + fun=(fun_t)0xff000000; + fun(); my_printf("mul(%d, %d)=%d\n", a, b, a * b); my_printf("ram_val test: %s\n", g_string); set_csr(mstatus, 0x00000008); diff --git a/riscv/trap.S b/riscv/trap.S index c83e5d7..9f7f67b 100644 --- a/riscv/trap.S +++ b/riscv/trap.S @@ -82,10 +82,11 @@ # .section .interrupt.text .extern trap_entry -.global trap_entry_ +.global _trap_entry .align 4 -trap_entry_: +_trap_entry: csrw mscratch, sp + mv a1, sp la sp, _exc_sp call trap_entry csrr sp, mscratch @@ -106,7 +107,7 @@ trap_handler: li a2, 0x000000ff and a1, a0, a1 and a0, a2, a0 - beqz a1, trap_entry_ + beqz a1, _trap_entry csrw mscratch, sp la sp, _irq_sp call interrupt_entry