⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vectors.s

📁 eCos1.31版
💻 S
📖 第 1 页 / 共 3 页
字号:
        # Save registers used in vsr (r14+r15)        stw     r14,CYGARC_PPCREG_REGS+14*4(sp)        stw     r15,CYGARC_PPCREG_REGS+15*4(sp)        # get remaining family CPU registers        mfxer   r3        mfctr   r4        mfsrr0  r5        mfsrr1  r6        # and store them        stw     r3,CYGARC_PPCREG_XER(sp)        stw     r4,CYGARC_PPCREG_CTR(sp)        stw     r5,CYGARC_PPCREG_PC(sp)        stw     r6,CYGARC_PPCREG_MSR(sp)                        # Save variant registers        hal_variant_save sp        # Save FPU registers        hal_fpu_save sp        # The entire CPU state is now stashed on the stack,        # increment the scheduler lock and call the ISR        # for this vector.#ifdef CYGFUN_HAL_COMMON_KERNEL_SUPPORT                         .extern cyg_scheduler_sched_lock        lwi     r3,cyg_scheduler_sched_lock        lwz     r4,0(r3)        addi    r4,r4,1        stw     r4,0(r3)#endif                mr      r14,sp                          # r14 = register dump        #ifdef CYGIMP_HAL_COMMON_INTERRUPTS_USE_INTERRUPT_STACK         lwi     r3,__interrupt_stack            # stack top        lwi     r4,__interrupt_stack_base       # stack base        sub.    r5,sp,r4                        # sp - base        blt     1f                              # if < 0 - not on istack        sub.    r5,r3,sp                        # top - sp        bgt     2f                              # if > 0 - already on istack1:      mr      sp,r3                           # switch to istack2:      stwu    r14,-4(sp)                      # save old SP on stack#endif                subi    sp,sp,CYGARC_PPC_STACK_FRAME_SIZE # make a null frame        li      r0,0                            # R0 = 0        stw     r0,0(sp)                        # backchain = 0        stw     r0,8(sp)                        # return pc = 0                stwu    sp,-CYGARC_PPC_STACK_FRAME_SIZE(sp) # create new stack frame                                                # where C code can save LR        #if defined(CYGPKG_KERNEL_INSTRUMENT) && defined(CYGDBG_KERNEL_INSTRUMENT_INTR)        lwi     r3,0x0301                       # r3 = type = INTR,RAISE        lwz     r4,CYGARC_PPCREG_VECTOR(r14)    # arg1 = vector address        srwi    r4,r4,8                         # arg1 = vector number        xor     r5,r5,r5                        # arg2 = 0        bl      cyg_instrument                  # call instrument function        #endif        hal_intc_decode r15,r14                # get table index#ifdef CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT        .extern cyg_hal_gdb_isr        lwz     r3,CYGARC_PPCREG_PC(r14)        # for serial receive irq.        bl      cyg_hal_gdb_isr                 # (arg1 is PC)        cmpwi   r3,0x0000                       # Call ISR proper?        beq     2f                              # (r3 is 0 when skipping                                                #  to avoid DSR call)1:#endif#ifdef CYGSEM_HAL_COMMON_INTERRUPTS_ALLOW_NESTING#ifdef CYGPKG_HAL_POWERPC_MPC8xx        # The CPM controller allows nested interrupts. However,        # it sits on the back of the SIU controller which has no        # HW support for this. In effect, SW masking of lower        # priority IRQs in the SIU would be required for this to work.#endif#endif        lwz     r3,CYGARC_PPCREG_VECTOR(r14)    # retrieve decoded vector #        lwi     r6,hal_interrupt_handlers       # get interrupt handler table        lwzx    r6,r6,r15                       # load routine pointer        lwi     r4,hal_interrupt_data           # get interrupt data table        lwzx    r4,r4,r15                       # load data pointer                                                # R4 = data argument                mtctr   r6                              # put isr address in ctr        bctrl                                   # branch to ctr reg and link#ifdef CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT        # If interrupt was caused by GDB, the ISR call above        # is skipped by jumping here.2:#endif        #ifdef CYGIMP_HAL_COMMON_INTERRUPTS_USE_INTERRUPT_STACK        # If we are returning from the last nested interrupt, move back        # to the thread stack. interrupt_end() must be called on the        # thread stack since it potentially causes a context switch.        # Since we have arranged for the top of stack location to        # contain the sp we need to go back to here, just pop it off        # and put it in SP.                lwz     sp,CYGARC_PPC_STACK_FRAME_SIZE*2(sp) # sp = *sp        subi    sp,sp,CYGARC_PPC_STACK_FRAME_SIZE # make a null frame        li      r0,0                            # R0 = 0        stw     r0,0(sp)                        # backchain = 0        stw     r0,8(sp)                        # return pc = 0                stwu    sp,-CYGARC_PPC_STACK_FRAME_SIZE(sp) # create new stack frame                                                # where C code can save LR#endif  #ifdef CYGFUN_HAL_COMMON_KERNEL_SUPPORT        # We only need to call _interrupt_end() when there is a kernel        # present to do any tidying up.                # on return r3 bit 1 will indicate whether a DSR is        # to be posted. Pass this together with a pointer to        # the interrupt object we have just used to the        # interrupt tidy up routine.        # Note that r14 and r15 are defined to be preserved across        # calls by the calling convention, so they still contain        # the register dump and the vector number respectively.        lwi     r4,hal_interrupt_objects        # get interrupt object table        lwzx    r4,r4,r15                       # load object pointer        mr      r5,r14                          # arg3 = saved register dump        .extern interrupt_end        bl      interrupt_end                   # call into C to finish off #endifrestore_state:          # All done, restore CPU state and continue        addi    sp,sp,CYGARC_PPC_STACK_FRAME_SIZE*2 # retrieve CPU state pointer        # get sprs we want to restore        # stuff some of them into the CPU        lwz     r3,CYGARC_PPCREG_XER(sp)        lwz     r4,CYGARC_PPCREG_LR(sp)        lwz     r5,CYGARC_PPCREG_CTR(sp)        mtxer   r3        mtlr    r4        mtctr   r5        # Restore registers used in vsr (r14+r15)        lwz     r14,CYGARC_PPCREG_REGS+14*4(r1)        lwz     r15,CYGARC_PPCREG_REGS+15*4(r1)        # restore registers r6..r12/r31        .set    _reg,6        .rept   MAX_SAVE_REG+1-6        lwz     _reg,(CYGARC_PPCREG_REGS+_reg*4)(sp)        .set    _reg,_reg+1        .endr        hal_cpu_int_disable                # restore R0 and R2        lwz     r0,CYGARC_PPCREG_REGS+0*4(sp)        lwz     r2,CYGARC_PPCREG_REGS+2*4(sp)        # Here all the registers are loaded except        # sp = HAL_SavedRegisters        # r3 = ccr        # r4 = srr0 = pc        # r5 = srr1 = msr        #        # We have to disable interrupts while srr0 and        # srr1 are loaded, since another interrupt will        # destroy them.        lwz     r3,CYGARC_PPCREG_CR(sp)        lwz     r4,CYGARC_PPCREG_PC(sp)        lwz     r5,CYGARC_PPCREG_MSR(sp)        mtcr    r3                      # set ccr        mtsrr0  r4                      # load old pc        mtsrr1  r5                      # load old msr        #ifdef CYGDBG_HAL_POWERPC_FRAME_WALLS        # Mark this frame as (almost) dead.        lwi     r3,0xDDDDDDD0        stw     r3,CYGARC_PPCREG_WALL_HEAD(sp)        lwi     r3,0xDDDDDDD1        stw     r3,CYGARC_PPCREG_WALL_TAIL(sp)#endif        lwz     r3,CYGARC_PPCREG_REGS+3*4(sp)  # load r3 value        lwz     r4,CYGARC_PPCREG_REGS+4*4(sp)  # load r4 value        lwz     r5,CYGARC_PPCREG_REGS+5*4(sp)  # load r5 value        lwz     sp,CYGARC_PPCREG_REGS+1*4(sp)  # restore sp                        sync                            # settle things down        isync           rfi                             # and return##-----------------------------------------------------------------------------## Execute pending DSRs on the interrupt stack with interrupts enabled.## Note: this can only be called from code running on a thread stack#ifdef CYGIMP_HAL_COMMON_INTERRUPTS_USE_INTERRUPT_STACK	.extern cyg_interrupt_call_pending_DSRsFUNC_START(hal_interrupt_stack_call_pending_DSRs)        # Change to interrupt stack, save state and set up stack for        # calls to C code.        mr      r3,sp        lwi     r4,__interrupt_stack        subi    r4,r4,24                        # make space on stack        mr      sp,r4        stw     r3,12(sp)                       # save old sp        mfmsr   r3        stw     r3,16(sp)                       # save old MSR        mflr    r3        stw     r3,20(sp)                       # save old LR        li      r0,0        stw     r0,0(sp)                        # clear back chain        stw     r0,8(sp)                        # zero return pc        hal_cpu_int_enable        # Call into kernel which will execute DSRs        stwu    sp,-CYGARC_PPC_STACK_FRAME_SIZE(sp)        bl      cyg_interrupt_call_pending_DSRs        addi    sp,sp,CYGARC_PPC_STACK_FRAME_SIZE        lwz     r3,20(sp)                       # restore LR        mtlr    r3        lwz     r5,12(sp)                       # get SP from saved state        lwz     r3,16(sp)                       # restore interrupt setting        hal_cpu_int_merge r3        mr      sp,r5                           # restore stack pointer        blr                                     # and return to caller#endif		#---------------------------------------------------------------------------## Temporary interrupt stack                .section ".bss"	.balign 16	.global cyg_interrupt_stack_basecyg_interrupt_stack_base:__interrupt_stack_base:	.rept CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE	.byte 0	.endr	.balign 16	.global cyg_interrupt_stackcyg_interrupt_stack:__interrupt_stack:                .long   0,0,0,0,0,0,0,0 #---------------------------------------------------------------------------# end of vectors.S

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -