diff options
author | Andrew Waterman <waterman@s141.Millennium.Berkeley.EDU> | 2011-02-04 16:09:47 -0800 |
---|---|---|
committer | Andrew Waterman <waterman@s141.Millennium.Berkeley.EDU> | 2011-02-04 16:09:47 -0800 |
commit | 5c9d48945e6c62e77f22e32efcb963a56bf3dc74 (patch) | |
tree | 39008b7c01fc76ec86369c1d0b8d676896748bf9 /pk/handlers.c | |
parent | af2d471a4e6c2e4551238a2cc209f9c0d997c82f (diff) | |
download | pk-5c9d48945e6c62e77f22e32efcb963a56bf3dc74.zip pk-5c9d48945e6c62e77f22e32efcb963a56bf3dc74.tar.gz pk-5c9d48945e6c62e77f22e32efcb963a56bf3dc74.tar.bz2 |
[sim,pk] added interrupt-pending field to cause reg
Diffstat (limited to 'pk/handlers.c')
-rw-r--r-- | pk/handlers.c | 66 |
1 files changed, 29 insertions, 37 deletions
diff --git a/pk/handlers.c b/pk/handlers.c index cb580e6..430210d 100644 --- a/pk/handlers.c +++ b/pk/handlers.c @@ -1,16 +1,9 @@ #include "pcr.h" #include "pk.h" -int have_fp = 1; +int have_fp = 1; // initialized to 1 because it can't be in the .bss section! -void handle_breakpoint(trapframe_t* tf) -{ - printk("Breakpoint\n"); - dump_tf(tf); - tf->epc += 4; -} - -void handle_fp_disabled(trapframe_t* tf) +static void handle_fp_disabled(trapframe_t* tf) { if(have_fp) init_fp(); @@ -28,19 +21,13 @@ void handle_fp_disabled(trapframe_t* tf) } } -void handle_badtrap(trapframe_t* tf) -{ - dump_tf(tf); - panic("Bad trap vector!"); -} - -void handle_privileged_instruction(trapframe_t* tf) +static void handle_privileged_instruction(trapframe_t* tf) { dump_tf(tf); panic("A privileged instruction was executed!"); } -void handle_illegal_instruction(trapframe_t* tf) +static void handle_illegal_instruction(trapframe_t* tf) { #ifdef PK_ENABLE_FP_EMULATION if(emulate_fp(tf) == 0) @@ -51,7 +38,7 @@ void handle_illegal_instruction(trapframe_t* tf) panic("An illegal instruction was executed!"); } -void handle_misaligned_fetch(trapframe_t* tf) +static void handle_misaligned_fetch(trapframe_t* tf) { dump_tf(tf); panic("Misaligned instruction access!"); @@ -63,7 +50,7 @@ void handle_misaligned_ldst(trapframe_t* tf) panic("Misaligned data access!"); } -void handle_fault_fetch(trapframe_t* tf) +static void handle_fault_fetch(trapframe_t* tf) { dump_tf(tf); panic("Faulting instruction access!"); @@ -81,11 +68,29 @@ void handle_fault_store(trapframe_t* tf) panic("Faulting store!"); } -void handle_timer_interrupt(trapframe_t* tf) +static void handle_bad_interrupt(trapframe_t* tf, int interrupt) +{ + panic("Bad interrupt %d!",interrupt); +} + +static void handle_timer_interrupt(trapframe_t* tf) { mtpcr(mfpcr(PCR_COMPARE)+TIMER_PERIOD,PCR_COMPARE); } +static void handle_interrupt(trapframe_t* tf) +{ + int interrupts = (tf->cause & CAUSE_IP) >> CAUSE_IP_SHIFT; + + for(int i = 0; interrupts; interrupts >>= 1, i++) + { + if(i == TIMER_IRQ) + handle_timer_interrupt(tf); + else + handle_bad_interrupt(tf,i); + } +} + void handle_trap(trapframe_t* tf) { typedef void (*trap_handler)(trapframe_t*); @@ -96,29 +101,16 @@ void handle_trap(trapframe_t* tf) handle_privileged_instruction, handle_fp_disabled, handle_syscall, - handle_breakpoint, + handle_interrupt, handle_misaligned_ldst, handle_fault_load, handle_fault_store, - handle_badtrap, - handle_badtrap, - handle_badtrap, - handle_badtrap, - handle_badtrap, - handle_badtrap, - handle_badtrap, /* irq 0 */ - handle_badtrap, /* irq 1 */ - handle_badtrap, /* irq 2 */ - handle_badtrap, /* irq 3 */ - handle_badtrap, /* irq 4 */ - handle_badtrap, /* irq 5 */ - handle_badtrap, /* irq 6 */ - handle_timer_interrupt, /* irq 7 */ }; - kassert(tf->cause < sizeof(trap_handlers)/sizeof(trap_handlers[0])); + int exccode = (tf->cause & CAUSE_EXCCODE) >> CAUSE_EXCCODE_SHIFT; + kassert(exccode < sizeof(trap_handlers)/sizeof(trap_handlers[0])); - trap_handlers[tf->cause](tf); + trap_handlers[exccode](tf); pop_tf(tf); } |