-\r
-/*\r
- * IVOR4\r
- * 1. Save stack frames: EXC, VGPR, NVGPR and C\r
- * 2. Call Irq_Entry(void *curr_stack)\r
- * 2.1 Check for exception\r
- * 2.2 If softint, clear it.\r
- * 2.3 If PROC_ISR1, then just call the function\r
- * 2.4 If PROC_ISR2 -> it's a PCB, let the OS handle it.\r
+/* \r
+ *\r
+ * The Irq_IsrTypeTable does not exist any more.\r
+ * The Irq_VectorTable is now a pure function table (not mixed pcb and functions )\r
+ * The PPC interrupt handling is a bit faster.\r
+ * \r
+ *\r
+ * New files for arch offsets? \r
+ * Bypassed Irq_Entry()...\r
+ * TODO:\r
+ * Move pre/post hooks into swap code?\r
+ *\r
+ *\r
+ * IMPLEMENTATION NOTES\r
+ * OPT: For ISR1 (interrupts always off) the there is no need to save r13-r31 since\r
+ * it will be saved by the C-function. \r
*/\r
-\r
-#define _ASSEMBLER_\r
-#include "asm_ppc.h"\r
-#include "asm_offset.h"\r
-#include "asm_book_e.h"\r
-.extern os_intc_pcb_tbl\r
-.extern os_intc_types_tbl\r
-.extern os_sys\r
-\r
-\r
+ \r
/*\r
* Small assembler school\r
- * Compare imm(32-bit)\r
- * > cmpwi rA,100\r
- * Extract bits and right adjust\r
- * > extrwi rA,rS,n,b ( n-number of bits, b- startbit )\r
+ * Compare imm(32-bit)\r
+ * $ cmpwi rA,100\r
+ * Extract bits and right adjust\r
+ * $ extrwi rA,rS,n,b ( n-number of bits, b- startbit )\r
+ * Use of @ha,@h,@l. Use @ha for arithmetic instructions to compensate for sign.\r
+ * To cause less confusion use load and logical instructions instead of arithmetic ones.\r
+ * $ lis r3,0x8000@h \r
+ * $ ori r3,r3,0x08000@l\r
+ * is the same as \r
+ * $ addis r3,0x8000@ha \r
+ * $ addi r3,r3,0x08000@l\r
*\r
* Note!\r
- * The offset's (d or D)for SPE instructins are rediculously low.\r
+ * The offset's (d or D)for SPE instructions are ridiculously low.\r
* Normally you have 16-bits offset, but when using spe load and store\r
* you can use only 8-bit.\r
*/\r
\r
-#define LOCK() wrteei 0\r
-#define UNLOCK() wrteei 1\r
\r
+/* ----------------------------[includes]------------------------------------*/\r
+#define _ASSEMBLER_\r
+#include "asm_ppc.h"\r
+#include "arch_offset.h"\r
+#include "asm_offset.h"\r
+#include "arch_stack.h"\r
\r
-.extern os_proc_start_extended\r
+// #include "asm_book_e.h"\r
+.extern os_intc_pcb_tbl\r
+.extern os_intc_types_tbl\r
+.extern Os_Sys\r
+.extern Os_ArchPanic\r
\r
-//-------------------------------------------------------------------\r
+#if defined(CFG_VLE)\r
+#define lis e_lis\r
+#define li se_li\r
+#define lwz e_lwz\r
+#define stwu e_stwu\r
+#define stw e_stw\r
+#define b e_b\r
+#define addi e_addi /* true ?*/\r
+#define subi e_subi /* true ?*/\r
+#endif \r
\r
- .global os_exception_IVOR8\r
- .balign 16\r
-os_exception_IVOR8:\r
- stwu sp,-(EXC_SIZE+VGPR_SIZE)(sp)\r
- stw r3,EXC_R3_OFF(r1)\r
- stw r4,EXC_R4_OFF(r1)\r
- SAVE_EXC_FRAME(3,1,0,SPR_SRR0,SPR_SRR1)\r
- SAVE_VGPR(1,EXC_SIZE);\r
- li r3,328\r
- stw r3,EXC_VECTOR_OFF(r1)\r
+/* ----------------------------[private define]------------------------------*/\r
\r
- rfi\r
+//#define OLD_CALL \r
\r
-dummy_int:\r
- b dummy_int\r
+#define INTC_IACKR_PRC0 0xfff48010 \r
+#define INTC_EOIR_PRC0 0xfff48018\r
+#define INTC_IACKR 0xfff48010\r
+#define INTC_EOIR 0xfff48018\r
+#define INTC_SSCIR0 0xfff48020\r
\r
-/*--------------------------------------------------------------------\r
- * void os_swap_context(pcb_t *old, pcb_t *new )\r
- *\r
- * Saves a small context on current stack, pops a new one from new context\r
- *\r
- * r3 - pcb for old process\r
- * r4 - pcb for new process\r
- *\r
- *--------------------------------------------------------------------*/\r
+/* ----------------------------[private macro]-------------------------------*/\r
+\r
+#define LOCK() wrteei 0\r
+#define UNLOCK() wrteei 1\r
+\r
+#define EXC_TABLE_CODE(_exc_nr) \\r
+ stwu sp,-EXC_FRM_SIZE(sp); \\r
+ stw r3,EXC_FRM_R3(sp); \\r
+ li r3,_exc_nr; \\r
+ b handleException \r
\r
-// TODO: this assumes that both are in user mode?.. can this happen under trusted functions?\r
-// When I get here we're ALWAYS in kernel mode\r
+#if ISR_FRM_PATTERN!=FUNC_FRM_PATTERN\r
+#error Context pattern must be in the same place\r
+#endif\r
+\r
+/* ----------------------------[private typedef]-----------------------------*/\r
+/* ----------------------------[private function prototypes]-----------------*/\r
+/* ----------------------------[private variables]---------------------------*/\r
+/* ----------------------------[private functions]---------------------------*/\r
+/* ----------------------------[public functions]----------------------------*/\r
+\r
+.extern Os_Isr\r
\r
-.global Os_ArchSwapContextToW\r
.global Os_ArchSwapContextTo\r
.global Os_ArchSwapContext\r
.global Os_ArchSetSpAndCall\r
mtlr r4\r
blr\r
\r
-Os_ArchSwapContextToW:\r
- mr r1,r5\r
- b Os_ArchSwapContextTo\r
-\r
+/**\r
+ * void Os_ArchSwapContext(pcb_t *old, pcb_t *new )\r
+ *\r
+ * Saves a function context on current stack, pops a new one from new context\r
+ *\r
+ * r3 - pcb for old task\r
+ * r4 - pcb for new task\r
+ *\r
+ */\r
Os_ArchSwapContext:\r
- // allocate space for context+nvgpr\r
- // (no need for proper stack-frame here)\r
- stwu r1,-(C_SIZE+NVGPR_SIZE)(r1)\r
- // save lr and cr */\r
- mflr r0\r
- stw r0,C_LR_OFF(sp)\r
- mfcr r0\r
- stw r0,C_CR_OFF(sp)\r
- // Save small-context pattern\r
- li r0,SC_PATTERN\r
- stw r0,C_CONTEXT_OFF(sp)\r
- // Save registers preserved by function call\r
- SAVE_NVGPR(sp,(C_SIZE-14*GPR_SIZE))\r
-// Save stack ptr...\r
- stw sp,PCB_STACK_CURR_P(r3)\r
-\r
-// Stack frame here\r
-// --------- bottom( high address )\r
-// SC_xxx\r
-// C_xxx\r
-// --------- <- stack.curr\r
-//\r
-// --------- top( low address )\r
-\r
-\r
-// TODO: If we change application we must change mmu setup\r
+ stwu sp,-FUNC_FRM_SIZE(sp)\r
+ mflr r0\r
+ stw r0,FUNC_FRM_LR(sp)\r
+ mfcr r0\r
+ stw r0,FUNC_FRM_CR(sp)\r
+ \r
+ /* Save context indicator */\r
+ li r0,FUNC_PATTERN\r
+ stw r0,FUNC_FRM_PATTERN(sp)\r
+\r
+#if defined(CFG_SPE)\r
+ stw r14, FUNC_FRM_R14(sp)\r
+ stw r15, FUNC_FRM_R15(sp)\r
+ stw r16, FUNC_FRM_R16(sp)\r
+ stw r17, FUNC_FRM_R17(sp)\r
+ stw r18, FUNC_FRM_R18(sp)\r
+ stw r19, FUNC_FRM_R19(sp)\r
+ stw r20, FUNC_FRM_R20(sp)\r
+ stw r21, FUNC_FRM_R21(sp)\r
+ stw r22, FUNC_FRM_R22(sp)\r
+ stw r23, FUNC_FRM_R23(sp)\r
+ stw r24, FUNC_FRM_R24(sp)\r
+ stw r25, FUNC_FRM_R25(sp)\r
+ stw r26, FUNC_FRM_R26(sp)\r
+ stw r27, FUNC_FRM_R27(sp)\r
+ stw r28, FUNC_FRM_R28(sp)\r
+ stw r29, FUNC_FRM_R29(sp)\r
+ stw r30, FUNC_FRM_R30(sp)\r
+ stw r31, FUNC_FRM_R31(sp)\r
+\r
+#else\r
+ /* Save registers preserved by function call */\r
+ stw r14, FUNC_FRM_R14(sp)\r
+ stw r15, FUNC_FRM_R15(sp)\r
+ stw r16, FUNC_FRM_R16(sp)\r
+ stw r17, FUNC_FRM_R17(sp)\r
+ stw r18, FUNC_FRM_R18(sp)\r
+ stw r19, FUNC_FRM_R19(sp)\r
+ stw r20, FUNC_FRM_R20(sp)\r
+ stw r21, FUNC_FRM_R21(sp)\r
+ stw r22, FUNC_FRM_R22(sp)\r
+ stw r23, FUNC_FRM_R23(sp)\r
+ stw r24, FUNC_FRM_R24(sp)\r
+ stw r25, FUNC_FRM_R25(sp)\r
+ stw r26, FUNC_FRM_R26(sp)\r
+ stw r27, FUNC_FRM_R27(sp)\r
+ stw r28, FUNC_FRM_R28(sp)\r
+ stw r29, FUNC_FRM_R29(sp)\r
+ stw r30, FUNC_FRM_R30(sp)\r
+ stw r31, FUNC_FRM_R31(sp)\r
+#endif\r
+\r
+ /* Save stack ptr... */\r
+ stw sp,PCB_STACK_CURR_P(r3)\r
+\r
+ /* TODO: Call Os_PretaskHook()? */ \r
+ \r
+ /* Flow down */\r
+ \r
+/**\r
+ * void Os_ArchSwapContextTo( NULL, pcb_t *new )\r
+ * r3 - always NULL\r
+ * r4 - The pcb to switch to.\r
+ */ \r
Os_ArchSwapContextTo:\r
-// Get stack for new task\r
- lwz sp,PCB_STACK_CURR_P(r4)\r
-\r
-// Set new current process\r
- LOAD_ADDR_32(3,os_sys)\r
- stw r4,SYS_CURR_PCB_P(r3)\r
-\r
-// Restore C context\r
- lwz r0,C_CR_OFF(sp)\r
- mtcr r0\r
- lwz r0,C_LR_OFF (sp)\r
- mtlr r0\r
-\r
-// Get the context type\r
- lwz r0,C_CONTEXT_OFF(sp)\r
- cmpli 0,r0,SC_PATTERN\r
- beq+ os_sc_restore\r
- cmpli 0,r0,LC_PATTERN\r
- beq+ os_lc_restore\r
- b os_bad_bad\r
-\r
-\r
-// SC_xxx\r
-// C_xxxx <- We point here\r
-\r
-os_sc_restore:\r
- RESTORE_NVGPR(sp,(C_SIZE-14*GPR_SIZE))\r
- addi sp,sp,(C_SIZE+NVGPR_SIZE)\r
- // TODO: The blr will not do the trick if swapping to a user land task.\r
- blr\r
-\r
-os_lc_restore:\r
- addi r1,r1,C_SIZE\r
- RESTORE_NVGPR(1,0)\r
- addi r1,r1,-C_SIZE\r
- RESTORE_VGPR(1,C_SIZE)\r
-\r
- RESTORE_WORK_AND_MORE\r
+ /* Get stack for new task */\r
+ lwz sp,PCB_STACK_CURR_P(r4)\r
+\r
+ /* Set new current task */\r
+ LOAD_ADDR_32(3,Os_Sys)\r
+ stw r4,SYS_CURR_PCB_P(r3)\r
+\r
+ /* Restore C context */\r
+ lwz r0,FUNC_FRM_CR(sp)\r
+ mtcr r0\r
+ lwz r0,FUNC_FRM_LR (sp)\r
+ mtlr r0\r
+\r
+ /* Get the context type */\r
+ lwz r0, FUNC_FRM_PATTERN(sp)\r
+ cmpli 0, r0, FUNC_PATTERN\r
+ beq+ restoreFuncContext\r
+ cmpli 0, r0,ISR_PATTERN\r
+ beq+ restoreIsrContext\r
+ li r3, OS_ERR_BAD_CONTEXT\r
+ b Os_ArchPanic\r
+\r
+restoreFuncContext:\r
+#if defined(CFG_SPE)\r
+ evldd r14, FUNC_FRM_R14(sp)\r
+ evldd r15, FUNC_FRM_R15(sp)\r
+ evldd r16, FUNC_FRM_R16(sp)\r
+ evldd r17, FUNC_FRM_R17(sp)\r
+ evldd r18, FUNC_FRM_R18(sp)\r
+ evldd r19, FUNC_FRM_R19(sp)\r
+ evldd r20, FUNC_FRM_R20(sp)\r
+ evldd r21, FUNC_FRM_R21(sp)\r
+ evldd r22, FUNC_FRM_R22(sp)\r
+ evldd r23, FUNC_FRM_R23(sp)\r
+ evldd r24, FUNC_FRM_R24(sp)\r
+ evldd r25, FUNC_FRM_R25(sp)\r
+ evldd r26, FUNC_FRM_R26(sp)\r
+ evldd r27, FUNC_FRM_R27(sp)\r
+ evldd r28, FUNC_FRM_R28(sp)\r
+ evldd r29, FUNC_FRM_R29(sp)\r
+ evldd r30, FUNC_FRM_R30(sp)\r
+ evldd r31, FUNC_FRM_R31(sp)\r
+ addi sp,sp,(FUNC_FRM_SIZE)\r
+#else \r
+ lwz r14, FUNC_FRM_R14(sp)\r
+ lwz r15, FUNC_FRM_R15(sp)\r
+ lwz r16, FUNC_FRM_R16(sp)\r
+ lwz r17, FUNC_FRM_R17(sp)\r
+ lwz r18, FUNC_FRM_R18(sp)\r
+ lwz r19, FUNC_FRM_R19(sp)\r
+ lwz r20, FUNC_FRM_R20(sp)\r
+ lwz r21, FUNC_FRM_R21(sp)\r
+ lwz r22, FUNC_FRM_R22(sp)\r
+ lwz r23, FUNC_FRM_R23(sp)\r
+ lwz r24, FUNC_FRM_R24(sp)\r
+ lwz r25, FUNC_FRM_R25(sp)\r
+ lwz r26, FUNC_FRM_R26(sp)\r
+ lwz r27, FUNC_FRM_R27(sp)\r
+ lwz r28, FUNC_FRM_R28(sp)\r
+ lwz r29, FUNC_FRM_R29(sp)\r
+ lwz r30, FUNC_FRM_R30(sp)\r
+ lwz r31, FUNC_FRM_R31(sp)\r
+ addi sp,sp,(FUNC_FRM_SIZE)\r
+#endif \r
+ /* TODO: Call Os_PosttaskHook()? */\r
+ \r
+ blr\r
+\r
+\r
+/**\r
+ * External input exception handlers \r
+ */ \r
+ .global exception_IVOR4\r
+ .global restoreIsrContext\r
+ .balign 16\r
+exception_IVOR4:\r
+\r
+ /* Save the exception frame */\r
+ stwu sp,-EXC_FRM_SIZE(sp)\r
+\r
+ stw r3,EXC_FRM_R3(sp)\r
+\r
+ mfsrr0 r3\r
+ stw r3, EXC_FRM_SRR0(sp)\r
+ mfsrr1 r3\r
+ stw r3, EXC_FRM_SRR1(sp)\r
+\r
+ mfcr r3\r
+ stw r3, EXC_FRM_CR(sp) \r
+ mfxer r3 \r
+ stw r3, EXC_FRM_XER(sp)\r
+ mfctr r3\r
+ stw r3, EXC_FRM_CTR(sp)\r
+ mflr r3\r
+ stw r3, EXC_FRM_LR(sp) \r
+ \r
+ li r3,4\r
+ stw r3, EXC_FRM_VECTOR(sp)\r
+#if defined(CFG_SPE) \r
+\r
+ /* Enable SPE (exceptions turns it off) */\r
+ mfmsr r3\r
+ oris r3,r3,0x0200\r
+ mtmsr r3\r
+ isync\r
+\r
+ /* Create the frame */\r
+ addi sp,sp,-ISR_FRM_SIZE\r
+ evstdd r3, ISR_FRM_R3(sp) /* Save work reg */ \r
+ \r
+ /* SPEFSCR */\r
+ mfspr r3,SPR_SPEFSCR\r
+ clrlwi r3,r3,24 /* Mask off non-status bits */\r
+ stw r3,ISR_FRM_SPE_FSCR(sp)\r
+\r
+ /* Save SPE acc */\r
+ evsubfw r3,r3,r3 /* zero r3 */\r
+ evaddumiaaw r3,r3 /* Add r3 = r3 + acc -> r3 = acc */\r
+ evstdd r3,ISR_FRM_SPE_ACC(r1)\r
+ \r
+ evstdd r0, ISR_FRM_R0(sp)\r
+ evstdd r4, ISR_FRM_R4(sp)\r
+ evstdd r5, ISR_FRM_R5(sp)\r
+ evstdd r6, ISR_FRM_R6(sp)\r
+ evstdd r7, ISR_FRM_R7(sp)\r
+ evstdd r8, ISR_FRM_R8(sp)\r
+ evstdd r9, ISR_FRM_R9(sp)\r
+ evstdd r10, ISR_FRM_R10(sp)\r
+ evstdd r11, ISR_FRM_R11(sp)\r
+ evstdd r12, ISR_FRM_R12(sp)\r
+ evstdd r14, ISR_FRM_R14(sp)\r
+ evstdd r15, ISR_FRM_R15(sp)\r
+ evstdd r16, ISR_FRM_R16(sp)\r
+ evstdd r17, ISR_FRM_R17(sp)\r
+ evstdd r18, ISR_FRM_R18(sp)\r
+ evstdd r19, ISR_FRM_R19(sp)\r
+ evstdd r20, ISR_FRM_R20(sp)\r
+ evstdd r21, ISR_FRM_R21(sp)\r
+ evstdd r22, ISR_FRM_R22(sp)\r
+ evstdd r23, ISR_FRM_R23(sp)\r
+ evstdd r24, ISR_FRM_R24(sp)\r
+ evstdd r25, ISR_FRM_R25(sp)\r
+ evstdd r26, ISR_FRM_R26(sp)\r
+ evstdd r27, ISR_FRM_R27(sp)\r
+ evstdd r28, ISR_FRM_R28(sp)\r
+ evstdd r29, ISR_FRM_R29(sp)\r
+ evstdd r30, ISR_FRM_R30(sp)\r
+ addi sp,sp,8\r
+ evstdd r31, (ISR_FRM_R31-8)(sp)\r
+ addi sp,sp,-8\r
+#else\r
+ /* Save the ISR frame */\r
+ addi sp,sp,-ISR_FRM_SIZE\r
+ stw r0, ISR_FRM_R0(sp)\r
+ stw r4, ISR_FRM_R4(sp)\r
+ stw r5, ISR_FRM_R5(sp)\r
+ stw r6, ISR_FRM_R6(sp)\r
+ stw r7, ISR_FRM_R7(sp)\r
+ stw r8, ISR_FRM_R8(sp)\r
+ stw r9, ISR_FRM_R9(sp)\r
+ stw r10, ISR_FRM_R10(sp)\r
+ stw r11, ISR_FRM_R11(sp)\r
+ stw r12, ISR_FRM_R12(sp)\r
+ stw r14, ISR_FRM_R14(sp)\r
+ stw r15, ISR_FRM_R15(sp)\r
+ stw r16, ISR_FRM_R16(sp)\r
+ stw r17, ISR_FRM_R17(sp)\r
+ stw r18, ISR_FRM_R18(sp)\r
+ stw r19, ISR_FRM_R19(sp)\r
+ stw r20, ISR_FRM_R20(sp)\r
+ stw r21, ISR_FRM_R21(sp)\r
+ stw r22, ISR_FRM_R22(sp)\r
+ stw r23, ISR_FRM_R23(sp)\r
+ stw r24, ISR_FRM_R24(sp)\r
+ stw r25, ISR_FRM_R25(sp)\r
+ stw r26, ISR_FRM_R26(sp)\r
+ stw r27, ISR_FRM_R27(sp)\r
+ stw r28, ISR_FRM_R28(sp)\r
+ stw r29, ISR_FRM_R29(sp)\r
+ stw r30, ISR_FRM_R30(sp)\r
+ stw r31, ISR_FRM_R31(sp)\r
+#endif\r
+ \r
+ li r3,ISR_PATTERN\r
+ stw r3,ISR_FRM_PATTERN(sp)\r
+ /* Save the stack so it later can be saved in the pcb */ \r
+ mr r4,sp \r
+ \r
+ /* Switch to interrupt stack if at depth 0 */\r
+ /* Load the value Os_Sys.int_nest_cnt */\r
+ LOAD_IND_32(r3,Os_Sys+SYS_INT_NEST_CNT)\r
+ cmpli 0,r3,0\r
+ bne- on_int_stack\r
+\r
+ /* Load the interrupt stack */\r
+ LOAD_IND_32(r1,Os_Sys+SYS_INT_STACK)\r
+\r
+on_int_stack:\r
+\r
+#if defined(CFG_MPC5516)\r
+ lis r6, INTC_IACKR_PRC0@ha\r
+ lwz r6, INTC_IACKR_PRC0@l(r6)\r
+#elif defined(CFG_MPC5554) || defined(CFG_MPC5567)\r
+ lis r6, INTC_IACKR@ha \r
+ lwz r6, INTC_IACKR@l(r6)\r
+#endif\r
+ /* Check for 0 entry */\r
+ mr r5,r6\r
+ cmpli 0,r5,0\r
+ bne+ vectorOk\r
+ /* The entry was 0, call panic */\r
+ li r3,OS_ERR_SPURIOUS_INTERRUPT\r
+ li r4, 0\r
+ mr r5,r1\r
+ b Os_ArchPanic\r
+ \r
+vectorOk:\r
+ extrwi r5,r5,9,21\r
+ /* Check for soft INT */\r
+ cmpli 0,r5,7\r
+ bgt noSoftInt\r
+ /* Clear soft interrupt */\r
+ li r0,1 \r
+ lis r3, INTC_SSCIR0@h\r
+ ori r3, r3, INTC_SSCIR0@l\r
+ stbx r0,r5,r3 \r
+ \r
+noSoftInt: \r
+\r
+ lis r3, Os_Isr@h\r
+ ori r3, r3,Os_Isr@l\r
+ mtlr r3\r
+ mr r3,r4 /* "old" stack as arg1 */\r
+#if defined(OLD_CALL) \r
+ lwz r4, 0x0(r6) /* Read the address from the for function/pcb entry */\r
+#else\r
+ mr r4,r5\r
+#endif \r
+ blrl /* Call the entry */\r
+\r
+ /* Notes!\r
+ * The OS interrupt is ACK'd in Os_Isr(). For ISR1 it needs to call Irq_EOI()\r
+ */\r
+ \r
+ /* Irq_Entry have returned the stack we shall use */\r
+ mr sp,r3\r
+\r
+ /* Restore */\r
+restoreIsrContext:\r
+#if defined(CFG_SPE) \r
+\r
+ // Restore SPE control/status reg.\r
+ lwz r3,ISR_FRM_SPE_FSCR(sp)\r
+ mtspr SPR_CSRR0,r3\r
+\r
+ /* Restore SPE acc */\r
+ evldd r3,ISR_FRM_SPE_ACC(r1)\r
+ evmra r3,r3\r
+ \r
+\r
+ evldd r0, ISR_FRM_R0(sp)\r
+ evldd r3, ISR_FRM_R4(sp)\r
+ evldd r4, ISR_FRM_R4(sp)\r
+ evldd r5, ISR_FRM_R5(sp)\r
+ evldd r6, ISR_FRM_R6(sp)\r
+ evldd r7, ISR_FRM_R7(sp)\r
+ evldd r8, ISR_FRM_R8(sp)\r
+ evldd r9, ISR_FRM_R9(sp)\r
+ evldd r10, ISR_FRM_R10(sp)\r
+ evldd r11, ISR_FRM_R11(sp)\r
+ evldd r12, ISR_FRM_R12(sp)\r
+ evldd r14, ISR_FRM_R14(sp)\r
+ evldd r15, ISR_FRM_R15(sp)\r
+ evldd r16, ISR_FRM_R16(sp)\r
+ evldd r17, ISR_FRM_R17(sp)\r
+ evldd r18, ISR_FRM_R18(sp)\r
+ evldd r19, ISR_FRM_R19(sp)\r
+ evldd r20, ISR_FRM_R20(sp)\r
+ evldd r21, ISR_FRM_R21(sp)\r
+ evldd r22, ISR_FRM_R22(sp)\r
+ evldd r23, ISR_FRM_R23(sp)\r
+ evldd r24, ISR_FRM_R24(sp)\r
+ evldd r25, ISR_FRM_R25(sp)\r
+ evldd r26, ISR_FRM_R26(sp)\r
+ evldd r27, ISR_FRM_R27(sp)\r
+ evldd r28, ISR_FRM_R28(sp)\r
+ evldd r29, ISR_FRM_R29(sp)\r
+ evldd r30, ISR_FRM_R30(sp)\r
+ addi sp,sp,8\r
+ evldd r31, (ISR_FRM_R31-8)(sp)\r
+ addi sp,sp,-8\r
+#else\r
+ lwz r0, ISR_FRM_R0(sp)\r
+ lwz r4, ISR_FRM_R4(sp)\r
+ lwz r5, ISR_FRM_R5(sp)\r
+ lwz r6, ISR_FRM_R6(sp)\r
+ lwz r7, ISR_FRM_R7(sp)\r
+ lwz r8, ISR_FRM_R8(sp)\r
+ lwz r9, ISR_FRM_R9(sp)\r
+ lwz r10, ISR_FRM_R10(sp)\r
+ lwz r11, ISR_FRM_R11(sp)\r
+ lwz r12, ISR_FRM_R12(sp)\r
+ lwz r14, ISR_FRM_R14(sp)\r
+ lwz r15, ISR_FRM_R15(sp)\r
+ lwz r16, ISR_FRM_R16(sp)\r
+ lwz r17, ISR_FRM_R17(sp)\r
+ lwz r18, ISR_FRM_R18(sp)\r
+ lwz r19, ISR_FRM_R19(sp)\r
+ lwz r20, ISR_FRM_R20(sp)\r
+ lwz r21, ISR_FRM_R21(sp)\r
+ lwz r22, ISR_FRM_R22(sp)\r
+ lwz r23, ISR_FRM_R23(sp)\r
+ lwz r24, ISR_FRM_R24(sp)\r
+ lwz r25, ISR_FRM_R25(sp)\r
+ lwz r26, ISR_FRM_R26(sp)\r
+ lwz r27, ISR_FRM_R27(sp)\r
+ lwz r28, ISR_FRM_R28(sp)\r
+ lwz r29, ISR_FRM_R29(sp)\r
+ lwz r30, ISR_FRM_R30(sp)\r
+ lwz r31, ISR_FRM_R31(sp)\r
+#endif \r
+ \r
+ /* back to the exception frame */\r
+ addi sp,sp,ISR_FRM_SIZE\r
+ \r
+ lwz r3, EXC_FRM_LR(sp)\r
+ mtlr r3\r
+ lwz r3, EXC_FRM_CTR(sp)\r
+ mtctr r3\r
+ lwz r3, EXC_FRM_XER(sp)\r
+ mtxer r3\r
+ lwz r3, EXC_FRM_CR(sp)\r
+ mtcr r3\r
+ lwz r3, EXC_FRM_SRR0(sp)\r
+ mtsrr0 r3\r
+ lwz r3, EXC_FRM_SRR1(sp)\r
+ mtsrr1 r3\r
+ lwz r3, EXC_FRM_R3(sp)\r
+ addi sp,sp,EXC_FRM_SIZE\r
rfi\r
\r
-// When something really bad happens we end up here for the moment\r
-os_bad_bad:\r
- b os_bad_bad\r
-\r
-\r
\r
\r
-// ------------------------------------------------------------------\r
-\r
-/*\r
- * Trap interface !!!! See article http://www.linuxjournal.com/article/6516\r
- * http://www.osweekly.com/index.php?option=com_content&task=view&id=2229\r
+/**\r
+ * Decrementer exception. It just triggers soft interrupt 7.\r
+ *\r
*/\r
+exception_IVOR10:\r
+ stwu r3,-8(sp)\r
+ stw r4,4(sp)\r
\r
-/* The T32 instruction sim can't handle trap's so we have to make something\r
- * - write SRR0, SRR1, MSR\r
- * - jump to there routines\r
- */\r
+ /* ack dec int */\r
+ lis r3,0x0800\r
+ mtspr SPR_TSR,r3\r
\r
-// ------------------------------------------------------------------\r
+ /* Set soft int */\r
+ li r4,2\r
+ lis r3, INTC_SSCIR7@ha\r
+ stb r4, INTC_SSCIR7@l(r3)\r
\r
+ lwz r3,0(sp)\r
+ lwz r4,4(sp)\r
+ addi sp,sp,8\r
+ rfi\r
\r
-// System call, use this for trusted function ???\r
-// TODO: The example in autosar is not neccesary.. sc here here instead??\r
-//\r
-// NOTE!!!!!\r
-// Since the sc is a sync call, it should be enough to save NV regs(14->)\r
-// If I don't use the NV regs here I shouldn't need to save them\r
-// TODO: Inform compiler in SC_CALL() that I clobber volatile regs( r0, r3->\r
-// (since the compiler does not know it's a function call)\r
-// TODO: Could probably do this shorter....only NV regs that I use need saving\r
-// ( only cr2->cr4 according to e500 ABI )\r
\r
+/* Getting here means that the exception stack is started with:\r
+ * sp - saved\r
+ * r3 - saved and contains the exception number \r
+ */\r
+handleException:\r
+ b handleException \r
+ \r
+#if defined(__GNUC__) \r
+.section ".exception_tbl","ax"\r
+#elif defined(__CWCC__)\r
+.section .exception_tbl,4,"rw"\r
+#endif\r
+.balign 0x1000\r
+.global exception_tbl\r
+\r
+exception_tbl:\r
+ EXC_TABLE_CODE(0)\r
+ EXC_TABLE_CODE(1)\r
+ EXC_TABLE_CODE(2)\r
+ EXC_TABLE_CODE(3)\r
+ b exception_IVOR4\r
+ .skip +0xc\r
+ EXC_TABLE_CODE(5)\r
+ EXC_TABLE_CODE(6)\r
+ EXC_TABLE_CODE(7)\r
+ EXC_TABLE_CODE(8)\r
+ EXC_TABLE_CODE(9)\r
+ b exception_IVOR10\r
+ .skip +0xc\r
+ EXC_TABLE_CODE(11)\r
+ EXC_TABLE_CODE(12)\r
+ EXC_TABLE_CODE(13)\r
+ EXC_TABLE_CODE(14)\r
+#if defined(CFG_SPE)\r
+ EXC_TABLE_CODE(32)\r
+ EXC_TABLE_CODE(33)\r
+ EXC_TABLE_CODE(34)\r
+#endif\r
\r
\r
\r