提交 1ec1f9ef 编写于 作者: 张梓悦's avatar 张梓悦

amtest: add soft intr test

上级 b87c52d2
......@@ -19,6 +19,7 @@ extern "C" {
enum {
_EVENT_NULL = 0,
_EVENT_ERROR,
_EVENT_IRQ_SOFT,
_EVENT_IRQ_TIMER,
_EVENT_IRQ_IODEV,
_EVENT_PAGEFAULT,
......
......@@ -3,6 +3,7 @@
#include <klib.h>
// static _Context* (*user_handler)(_Event, _Context*) = NULL;
static _Context* (*custom_soft_handler)(_Event, _Context*) = NULL;
static _Context* (*custom_timer_handler)(_Event, _Context*) = NULL;
static _Context* (*custom_external_handler)(_Event, _Context*) = NULL;
static _Context* (*custom_secall_handler)(_Event, _Context*) = NULL;
......@@ -26,6 +27,27 @@ _Context* __am_irq_default_handler(_Event *ev, _Context *c) {
return c;
}
/*
* default handler for Supervisor Software Interrupt
* set event to IRQ_SOFT
* may call custom soft handler if registered
*/
_Context* __am_irq_SSIP_handler(_Event *ev, _Context *c) {
#if __riscv_xlen == 64
asm volatile ("csrwi sip, 0");
#endif
// printf("inside irq SSIP handler\n");
ev->event = _EVENT_IRQ_SOFT;
if (custom_soft_handler != NULL) {
// printf("dive into custom soft handler");
custom_soft_handler(*ev, c);
}
// machine mode will clear stip
asm volatile("csrs mie, 0");
// printf("SSIP handler finished\n");
return c;
}
/*
* default handler for Supervisor Timer Interrupt
* set event to IRQ_TIMER
......@@ -108,6 +130,14 @@ _Context* __am_irq_handle(_Context *c) {
extern void __am_asm_trap(void);
/*
* Supervisor soft interrupt custom handler register function
* handler: the function to be registered
*/
void ssip_handler_reg(_Context*(*handler)(_Event, _Context*)) {
custom_soft_handler = handler;
}
/*
* Supervisor timer interrupt custom handler register function
* handler: the function to be registered
......@@ -141,6 +171,8 @@ void custom_handler_reg(uintptr_t code, _Context*(*handler)(_Event, _Context*))
switch (code) {
#if __riscv_xlen == 64
case INTR_BIT | SCAUSE_SSIP:
ssip_handler_reg(handler);
break;
#endif
case INTR_BIT | SCAUSE_STIP:
stip_handler_reg(handler);
......@@ -195,10 +227,9 @@ int _cte_init(_Context *(*handler)(_Event ev, _Context *ctx)) {
}
#if __riscv_xlen == 64
interrupt_handler[SCAUSE_SSIP] = __am_irq_STIP_handler;
#else
interrupt_handler[SCAUSE_STIP] = __am_irq_STIP_handler;
interrupt_handler[SCAUSE_SSIP] = __am_irq_SSIP_handler;
#endif
interrupt_handler[SCAUSE_STIP] = __am_irq_STIP_handler;
interrupt_handler[SCAUSE_SEIP] = __am_irq_SEIP_handler;
exception_handler[SCAUSE_SECALL] = __am_irq_SECALL_handler;
......
......@@ -62,6 +62,7 @@ void enable_timer();
void set_timer_inc(uintptr_t inc);
// =========== Interrupt handler registration =======
void ssip_handler_reg(_Context*(*handler)(_Event, _Context*));
void stip_handler_reg(_Context*(*handler)(_Event, _Context*));
void seip_handler_reg(_Context*(*handler)(_Event, _Context*));
void secall_handler_reg(_Context*(*handler)(_Event, _Context*));
......
......@@ -9,6 +9,7 @@
#define IOE ({ _ioe_init(); })
#define CTE(h) ({ _Context *h(_Event, _Context *); _cte_init(h); })
#define RSEH(h) ({ _Context *h(_Event, _Context *); ssip_handler_reg(h);})
#define REEH(h) ({ _Context *h(_Event, _Context *); seip_handler_reg(h);})
#define RTEH(h) ({ _Context *h(_Event, _Context *); stip_handler_reg(h);})
#define RCEH(h) ({ _Context *h(_Event, _Context *); secall_handler_reg(h);})
......
......@@ -17,6 +17,7 @@ static const char *tests[256] = {
['c'] = "risc-v physical memory protection test",
['s'] = "risc-v virtual memory test",
['r'] = "risc-v RTC tick test",
['z'] = "risc-v soft intr test",
};
int main(const char *args) {
......@@ -24,6 +25,7 @@ int main(const char *args) {
CASE('x', dma_test);
CASE('h', hello);
CASE('i', hello_intr, IOE, CTE(simple_trap), REEH(simple_trap), RCEH(simple_trap), RTEH(simple_trap));
CASE('z', soft_intr, IOE, CTE(soft_trap), RSEH(soft_trap), REEH(soft_trap), RCEH(soft_trap), RTEH(soft_trap));
CASE('e', external_intr, IOE, NOTIMEINT(), CTE(external_trap), REEH(external_trap), RTEH(external_trap));
CASE('u', test_BEU, IOE, NOTIMEINT(), CTE(handle_external_trap), REEH(handle_external_trap), RTEH(handle_external_trap));
CASE('d', devscan, IOE);
......
#include <amtest.h>
#include <xs.h>
#include <nemu.h>
#if defined(__ARCH_RISCV64_NOOP) || defined(__ARCH_RISCV64_XS) || defined(__ARCH_RISCV64_XS_SOUTHLAKE) || defined(__ARCH_RISCV64_XS_SOUTHLAKE_FLASH)
#define CLINT_SOFT_ADDRESS (RTC_ADDR - 0xbff8)
#else
#define CLINT_SOFT_ADDRESS 0xa2000000
#endif
_Context *soft_trap(_Event ev, _Context *ctx) {
switch(ev.event) {
case _EVENT_IRQ_SOFT:
printf("s"); break;
case _EVENT_IRQ_TIMER:
printf("t"); break;
case _EVENT_IRQ_IODEV:
printf("d"); read_key(); break;
case _EVENT_YIELD:
printf("y"); break;
}
return ctx;
}
static void soft_intr_init() {
// enable supervisor software interrupt (sie.ssie and sstatus.sie)
asm volatile("csrs sstatus, %0" : : "r"(1 << 1));
asm volatile("csrs sie, %0" : : "r"(1 << 1));
}
void soft_intr() {
soft_intr_init();
*(uint32_t *)(CLINT_SOFT_ADDRESS) = 1;
asm volatile("csrw sip, 2");
}
\ No newline at end of file
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册