#define SR_IM_SHIFT 8
#define TIMER_IRQ 7
+#define CAUSE_EXCCODE 0x000000FF
+#define CAUSE_IP 0x0000FF00
+#define CAUSE_EXCCODE_SHIFT 0
+#define CAUSE_IP_SHIFT 8
+
#define FP_RD_NE 0
#define FP_RD_0 1
#define FP_RD_DN 2
fromhost = 0;
count = 0;
compare = 0;
- interrupts_pending = 0;
set_sr(SR_S | SR_SX); // SX ignored if 64b mode not supported
set_fsr(0);
{
for( ; i < n; i++)
{
- uint32_t interrupts = interrupts_pending & ((sr & SR_IM) >> SR_IM_SHIFT);
- if((sr & SR_ET) && interrupts)
- {
- for(int i = 0; interrupts; i++, interrupts >>= 1)
- if(interrupts & 1)
- throw trap_t(16+i);
- }
+ uint32_t interrupts = (cause & CAUSE_IP) >> CAUSE_IP_SHIFT;
+ interrupts &= (sr & SR_IM) >> SR_IM_SHIFT;
+ if(interrupts && (sr & SR_ET))
+ take_trap(trap_interrupt,noisy);
insn_t insn = mmu.load_insn(pc);
XPR[0] = 0;
if(count++ == compare)
- interrupts_pending |= 1 << TIMER_IRQ;
+ cause |= 1 << (TIMER_IRQ+CAUSE_IP_SHIFT);
}
return;
}
id, trap_name(t), (unsigned long long)pc);
set_sr((((sr & ~SR_ET) | SR_S) & ~SR_PS) | ((sr & SR_S) ? SR_PS : 0));
- cause = t;
+ cause = (cause & ~CAUSE_EXCCODE) | (t << CAUSE_EXCCODE_SHIFT);
epc = pc;
pc = evec;
badvaddr = mmu.get_badvaddr();
DECLARE_TRAP(privileged_instruction), \
DECLARE_TRAP(fp_disabled), \
DECLARE_TRAP(syscall), \
- DECLARE_TRAP(breakpoint), \
+ DECLARE_TRAP(interrupt), \
DECLARE_TRAP(data_address_misaligned), \
DECLARE_TRAP(load_access_fault), \
DECLARE_TRAP(store_access_fault), \