📄 excalib.s
字号:
and t1, t2 /* t1 = IM[15:8] & IP[15:8] */ beqz t1, 0f /* if still no interrupt, skip */ /* use low-order interrupt */ srl t1, IC_IMASKSHIFT /* right justify */ addu t1, t4 /* calculate table index */ lbu t2, 0(t1) /* read table index */ addu t2, 8 /* adjust to upper half */ b 1f /* skip down to function call *//* get to here if IP[7:0] -or- not using Rm7k extended interrrupts */0: srl t1, SR_IMASKSHIFT /* right justify */ addu t1, t4 /* calculate table index */ lbu t2, 0(t1) /* read table index *//* make the function call */1: addu a0, t2, MIN_INT_ID+1 li a1, TRG_CLASS1_INDEX li a2, 0x0 lw t1, _func_trgCheck jal t1 /* call evtLogT0 routine */ lw v0, E_STK_CAUSE(sp) /* restore the value of v0. We */noIntEnt: /* windview instrumentation - END */ lw k0,errno sw k0,E_ERRNO(sp) /* save errno */#else /* WV_INSTRUMENTATION */ SW t3,E_STK_T3(sp) /* save temp reg 3 (early) */ SW t2,E_STK_T2(sp) /* save temp reg 2 (early) */ SW t1,E_STK_T1(sp) /* save temp reg 1 (early) */#endif /* WV_INSTRUMENTATION */ lw t1, intStubSelect bnez t1, excIntStubExtendedexcIntStubNormal: /* * Note that it is possible to arrive here with * (CAUSE & STATUS & SR_IMASK) == 0 */ /* now k1 has STATUS and v0 has CAUSE */ andi t2, v0, SR_IMASK /* check for spurious interrupt */ and v0, k1, t2 /* v0 = ints enabled and pending */ lw t1, sysHashOrder /* load address of hash table */#ifdef WV_INSTRUMENTATION beqz v0, Restore /* return if no interrupt */#else /* WV_INSTRUMENTATION */ beqz v0, restoreVolatile /* check for spurious interrupt */#endif /* WV_INSTRUMENTATION */ srl t2, v0, SR_IMASKSHIFT /* t2 = v0 right justified */ addu t2, t2, t1 /* calculate table index */ lbu t1, 0(t2) /* read table index */ sll t1, 4 /* mult by Prio table size */ /* * The deterministic search implemented is a hash table * search, it is necessary that the Prio table be organized * in an ordered fashion for this to work. * * Volatile registers in MIPSville are considered EPC, * SR, and CAUSE. Our kernel implementation also places * sp and AT registers in this catagory. We use t1, t2, and * v0 as working registers and call the formentioned set * of registers volatile in the context of vxWorks. It * is critical that no other registers are used above * this point in excIntStub without restoring them * after the label restoreVolatile. Register t1 now * contains the pointer to the prio table which will * be used in code that follows. Be sure not to corrupt * this value. */#if 0 lw t2, intPrioTable+8(t1) /* get user mask */#else .set noat lui AT, %hi(intPrioTable+8) addu AT, t1 lw t2, %lo(intPrioTable+8)(AT) .set at#endif or v0, v0, t2 /* add user mask */ not v0 /* invert interrupt mask */ and k1, v0, k1 /* apply interrupt mask to k1 */excIntStubCommonExit: #ifdef _WRS_R3K_EXC_SUPPORT mtc0 k1, C0_SR /* update SR */ HAZARD_CP_WRITE or k1, SR_IEC /* now enable ints */ mtc0 k1, C0_SR /* update SR */#endif#ifndef _WRS_R3K_EXC_SUPPORT mtc0 k1, C0_SR /* SPR 78857: ensure ints masked */ /* before clearing EXL */ and k1, ~SR_EXL HAZARD_VR5400 mtc0 k1, C0_SR /* enable interrupts w/ new mask */#endif /* _WRS_R3k_EXC_SUPPORT */ #if 0 lw v0, intPrioTable+4(t1) /* get vector ptr; */ /* don't touch v0 after this */#else .set noat lui AT, %hi(intPrioTable+4) addu AT, t1 lw v0, %lo(intPrioTable+4)(AT) .set at#endif#if 0 lw t1, intPrioTable+12(t1) /* get vector base; */ /* don't touch t1 after this */#else .set noat lui AT, %hi(intPrioTable+12) addu AT, t1 lw t1, %lo(intPrioTable+12)(AT) .set at#endif#ifndef WV_INSTRUMENTATION/* * Begin state save */intStateSave: mflo t2 /* read entry lo reg */ SW t2,E_STK_LO(sp) /* save entry lo reg */ mfhi t2 /* read entry hi reg */ SW t2,E_STK_HI(sp) /* save entry hi reg */0: /* save func return 0, see above */ SW v1,E_STK_V1(sp) /* save func return 1 */ SW a0,E_STK_A0(sp) /* save passed param 0 */ SW a1,E_STK_A1(sp) /* save passed param 1 */ SW a2,E_STK_A2(sp) /* save passed param 2 */ SW a3,E_STK_A3(sp) /* save passed param 3 */ SW t0,E_STK_T0(sp) /* save temp reg 0 */ /* save temp reg 1, see above */ /* save temp reg 2, see above */ /* save temp reg 3, see above */ SW t4,E_STK_T4(sp) /* save temp reg 4 */ SW t5,E_STK_T5(sp) /* save temp reg 5 */ SW t6,E_STK_T6(sp) /* save temp reg 6 */ SW t7,E_STK_T7(sp) /* save temp reg 7 */ SW t8,E_STK_T8(sp) /* save temp reg 8 */ SW t9,E_STK_T9(sp) /* save temp reg 9 */ SW ra,E_STK_RA(sp) /* save return address */#endif /* WV_INSTRUMENTATION */ beq t1, zero, call /* if pad == 0, don't demux */ move a0, t1 /* pass vector base to demux */ jal v0 /* call demux routine, v0 now */ /* contains vector */call: move a0, v0 /* pass vector number */ move a1, sp /* pass exc stack frame */ sll v0, 2 /* mult index by wordsize */ la t0, excBsrTbl addu v0, t0 lw v1, (v0) /* grab routine addr */ jal v1 /* jump to routine *//* * Begin state restoration */Restore: lw t2,E_ERRNO(sp) sw t2,errno /* restore errno */ LW v1,E_STK_V1(sp) /* restore func ret 0 */ LW a0,E_STK_A0(sp) /* restore passed param 0 */ LW a1,E_STK_A1(sp) /* restore passed param 1 */ LW a2,E_STK_A2(sp) /* restore passed param 2 */ LW a3,E_STK_A3(sp) /* restore passed param 3 */ LW t0,E_STK_T0(sp) /* restore temp reg 0 */ LW t4,E_STK_T4(sp) /* restore temp reg 4 */ LW t5,E_STK_T5(sp) /* restore temp reg 5 */ LW t6,E_STK_T6(sp) /* restore temp reg 6 */ LW t7,E_STK_T7(sp) /* restore temp reg 7 */ LW t8,E_STK_T8(sp) /* restore temp reg 8 */ LW ra,E_STK_RA(sp) /* restore return addr */ LW t9,E_STK_LO(sp) /* grab entry hi reg */ mtlo t9 /* restore entry hi reg */ LW t9,E_STK_HI(sp) /* grab entry lo reg */ mthi t9 /* restore entry hi reg */0: LW t9,E_STK_T9(sp) /* restore temp reg 9 */ /* * Registers restored after this point must only be registers * which are considered volatile. This currently * includes SR, EPC, AT, sp, v0, t1, and t2. Any additions to * the volatile set of registers (see comments above) should * be mirrored with restores after the label restoreVolatile. */restoreVolatile: lw t1,E_STK_SR(sp) /* read old SR */#ifndef _WRS_R3K_EXC_SUPPORT /* ensure imask == 0 before setting EXL */ li v0,SR_IE HAZARD_VR5400 mtc0 v0,C0_SR HAZARD_CP_WRITE#endif#ifdef _WRS_R3K_EXC_SUPPORT and v0,t1,~SR_IMASK&~SR_IEC /* mask/disable all interrupts */ mtc0 v0,C0_SR /* restore SR (without ints) */ HAZARD_INTERRUPT#endif .set noreorder /* If extended interrupts are supported, the saved value of the * Interrupt Control register will have been placed in the ESF * in place of the zero register. If the saved value is zero, * it implies that either a) extended interrupts are not * supported, or b) that the IC register was clear when its * contents were saved, meaning that it is not necessary to * restore its contents. */ LW t2, E_STK_ZERO(sp) /* get IntCount from ESF */ beqz t2, 1f nop ctc0 t2, C0_1_IC /* set IntControl */1: mtc0 t1,C0_SR /* put on processor */ .set reorder LW v0,E_STK_V0(sp) /* restore func ret 0 */ LW t3,E_STK_T3(sp) /* restore temp reg 3 */ LW t2,E_STK_T2(sp) /* restore temp reg 2 */ LW t1,E_STK_T1(sp) /* restore temp reg 1 */ j intExit /* exit kernel, exception frame */ /* on interrupt stack */ /* stub for handling extended interrupts on RM7000 */excIntStubExtended: /* * Note that it is possible to arrive here with * (CAUSE & STATUS & SR_IMASK) == 0 */ /* now k1 has STATUS and v0 has CAUSE */ cfc0 t2, C0_1_IC /* get IntControl */ srl t1, k1, 8 /* get IM[7:0] */ and t1, 0xff and t2, 0xff00 /* get IM[15:8] */ or t1, t2 /* t1 = IM[15:0] */ srl t2, v0, 8 and t2, 0xffff /* t2 = IP[15:0] */ and t2, t1 /* t2 = IP & IM */#ifdef WV_INSTRUMENTATION beqz t2, Restore /* return if no interrupt */#else /* WV_INSTRUMENTATION */ beqz t2, restoreVolatile /* return if no interrupt */#endif /* WV_INSTRUMENTATION */ and t1, t2, 0xff /* t1 = (IP&IM)[7:0] */ beqz t1, 0f /* branch if no low int asserted */ lw t2, sysHashOrder /* load address of hash table */ addu t2, t1 /* calculate table index */ lbu t1, 0(t2) /* read table index */ sll t1, 4 /* mult by Prio table size */ b 1f0: srl t1, t2, 8 /* t1 = (IP&IM)[15:8] */ lw t2, sysHashOrder /* load address of hash table */ addu t2, t1 /* calculate table index */ lbu t1, 0(t2) /* read table index */ add t1, 8 /* adjust to upper half of table */ sll t1, 4 /* mult by Prio table size */1: /* * The deterministic search implemented is a hash table * search, it is necessary that the Prio table be organized * in an ordered fashion for this to work. * * Volatile registers in MIPSville are considered EPC, * SR, and CAUSE. Our kernel implementation also places * sp and AT registers in this catagory. We use t1, t2, and * v0 as working registers and call the formentioned set * of registers volatile in the context of vxWorks. It * is critical that no other registers are used above * this point in excIntStub without restoring them * after the label restoreVolatile. Register t1 now * contains the pointer to the prio table which will * be used in code that follows. Be sure not to corrupt * this value. */#if 0 lw t2, intPrioTable+8(t1) /* get user mask */#else .set noat lui AT, %hi(intPrioTable+8) addu AT, t1 lw t2, %lo(intPrioTable+8)(AT) .set at#endif or t2, v0 /* add cause bits */ and t3, t2, 0xff00 /* get just SR interrupts */ not t3 /* invert interrupt mask */ and k1, t3, k1 /* apply interrupt mask to k1 */ srl t2, 8 /* get upper int bits */ and t2, 0xff00 /* get just SR ints */ not t2 cfc0 t3, C0_1_IC /* get IntControl */ HAZARD_CP_READ SW t3, E_STK_ZERO(sp) /* stash IntCount in ESF */ and t3, t2 ctc0 t3, C0_1_IC /* set IntControl */ j excIntStubCommonExit .end excIntStub#ifndef _WRS_R3K_EXC_SUPPORT/********************************************************************************* excCache - catch and handle cache exceptions** This is the exception handler that is pointed to by the r4000 * vector at address 0xa0000100, the cache exception vector. * In this routine we attempt to fix the cache error and then continue.* If too many cache excpetions occur, the cache is disabled.** NOTE
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -