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

📄 window.s

📁 RTEMS (Real-Time Executive for Multiprocessor Systems) is a free open source real-time operating sys
💻 S
字号:
/* *  window.s * *  This file contains the register window management routines for the  *  SPARC architecture.  Trap handlers for the following capabilities *  are included in this file: * *    + Window Overflow *    + Window Underflow *    + Flushing All Windows *  *  COPYRIGHT: * *  This file includes the window overflow and underflow handlers from  *  the file srt0.s provided with the binary distribution of the SPARC  *  Instruction Simulator (SIS) found at  *  ftp://ftp.estec.esa.nl/pub/ws/wsd/erc32. * *  COPYRIGHT (c) 1995. European Space Agency. * *  This terms of the RTEMS license apply to this file. * *  $Id: window.S,v 1.1 1998/12/14 23:15:35 joel Exp $ */#include <asm.h>        .seg    "text"        /*         *  Window overflow trap handler.         *         *  On entry:         *         *    l0 = psr (from trap table)         *    l1 = pc         *    l2 = npc         */        PUBLIC(window_overflow_trap_handler)SYM(window_overflow_trap_handler):        /*         *  Calculate new WIM by "rotating" the valid bits in the WIM right          *  by one position.  The following shows how the bits move for a SPARC         *  cpu implementation where SPARC_NUMBER_OF_REGISTER_WINDOWS is 8.         *         *    OLD WIM = 76543210         *    NEW WIM = 07654321         *         *  NOTE: New WIM must be stored in a global register since the         *        "save" instruction just prior to the load of the wim          *        register will result in the local register set changing.         */        mov  %wim, %l3                   ! l3 = WIM        mov  %g1, %l7                    ! save g1        srl  %l3, 1, %g1                 ! g1 = WIM >> 1        sll  %l3, SPARC_NUMBER_OF_REGISTER_WINDOWS-1 , %l4                                         ! l4 = WIM << (Number Windows - 1)        or   %l4, %g1, %g1               ! g1 = (WIM >> 1) |                                          !      (WIM << (Number Windows - 1))        save                             ! Get into window to be saved.        mov  %g1, %wim                   ! load new WIM        nop; nop; nop                    ! 3 slot delay        std  %l0, [%sp + 0x00]           ! save local register set        std  %l2, [%sp + 0x08]        std  %l4, [%sp + 0x10]        std  %l6, [%sp + 0x18]        std  %i0, [%sp + 0x20]           ! save input register set        std  %i2, [%sp + 0x28]        std  %i4, [%sp + 0x30]        std  %i6, [%sp + 0x38]        restore                          ! Go back to trap window.        mov  %l7, %g1                    ! restore g1        jmp  %l1                         ! Re-execute save.        rett %l2        /*         *  Window underflow trap handler.         *         *  On entry:         *         *    l0 = psr (from trap table)         *    l1 = pc         *    l2 = npc         */        PUBLIC(window_underflow_trap_handler)SYM(window_underflow_trap_handler):        /*         *  Calculate new WIM by "rotating" the valid bits in the WIM left          *  by one position.  The following shows how the bits move for a SPARC         *  cpu implementation where SPARC_NUMBER_OF_REGISTER_WINDOWS is 8.         *         *    OLD WIM = 76543210         *    NEW WIM = 07654321         *         *  NOTE: New WIM must be stored in a global register since the         *        "save" instruction just prior to the load of the wim          *        register will result in the local register set changing.         */        mov  %wim, %l3                  ! Calculate new WIM        sll  %l3, 1, %l4                ! l4 = WIM << 1        srl  %l3, SPARC_NUMBER_OF_REGISTER_WINDOWS-1, %l5                                        ! l5 = WIM >> (Number Windows-1)        or   %l5, %l4, %l5              ! l5 = (WIM << 1) |                                        !      (WIM >> (Number Windows-1))        mov  %l5, %wim                  ! load the new WIM        nop; nop; nop        restore                         ! Two restores to get into the        restore                         ! window to restore        ldd  [%sp + 0x00], %l0          ! First the local register set        ldd  [%sp + 0x08], %l2        ldd  [%sp + 0x10], %l4        ldd  [%sp + 0x18], %l6        ldd  [%sp + 0x20], %i0          ! Then the input registers        ldd  [%sp + 0x28], %i2        ldd  [%sp + 0x30], %i4        ldd  [%sp + 0x38], %i6        save                            ! Get back to the trap window.        save        jmp  %l1                        ! Re-execute restore.        rett  %l2        /*         *  Flush All Windows trap handler.         *         *  Flush all windows with valid contents except the current one         *  and the one we will be returning to.         *         *  In examining the set register windows, one may logically divide         *  the windows into sets (some of which may be empty) based on their         *  current status:         *         *    + current (i.e. in use),         *    + used (i.e. a restore would not trap)         *    + invalid (i.e. 1 in corresponding bit in WIM)         *    + unused         *         *  Either the used or unused set of windows may be empty.         *         *  NOTE: We assume only one bit is set in the WIM at a time.         *         *  Given a CWP of 5 and a WIM of 0x1, the registers are divided         *  into sets as follows:         *         *    + 0   - invalid         *    + 1-4 - unused         *    + 5   - current         *    + 6-7 - used         *         *  In this case, we only would save the used windows which we         *  will not be returning to -- 6.         *         *    Register Usage while saving the windows:         *      g1 = current PSR         *      g2 = current wim         *      g3 = CWP         *      g4 = wim scratch         *      g5 = scratch         *         *  On entry:         *         *    l0 = psr (from trap table)         *    l1 = pc         *    l2 = npc         */         PUBLIC(window_flush_trap_handler) SYM(window_flush_trap_handler):        /*         *  Save the global registers we will be using         */        mov     %g1, %l3        mov     %g2, %l4        mov     %g3, %l5        mov     %g4, %l6        mov     %g5, %l7        mov     %l0, %g1                      ! g1 = psr        mov     %wim, %g2                     ! g2 = wim        and     %l0, SPARC_PSR_CWP_MASK, %g3  ! g3 = CWP        add     %g3, 1, %g5                   ! g5 = CWP + 1        and     %g5, SPARC_NUMBER_OF_REGISTER_WINDOWS - 1, %g5        mov     1, %g4        sll     %g4, %g5, %g4                 ! g4 = WIM mask for CWP+1 invalid        restore                               ! go back one register window save_frame_loop:        sll     %g4, 1, %g5                   ! rotate the "wim" left 1        srl     %g4, SPARC_NUMBER_OF_REGISTER_WINDOWS - 1, %g4        or      %g4, %g5, %g4                 ! g4 = wim if we do one restore         /*         *  If a restore would not underflow, then continue.         */         andcc   %g4, %g2, %g0                 ! Any windows to flush?        bnz     done_flushing                 ! No, then continue        nop         restore                               ! back one window         /*         *  Now save the window just as if we overflowed to it.         */         std     %l0, [%sp + CPU_STACK_FRAME_L0_OFFSET]        std     %l2, [%sp + CPU_STACK_FRAME_L2_OFFSET]        std     %l4, [%sp + CPU_STACK_FRAME_L4_OFFSET]        std     %l6, [%sp + CPU_STACK_FRAME_L6_OFFSET]         std     %i0, [%sp + CPU_STACK_FRAME_I0_OFFSET]        std     %i2, [%sp + CPU_STACK_FRAME_I2_OFFSET]        std     %i4, [%sp + CPU_STACK_FRAME_I4_OFFSET]        std     %i6, [%sp + CPU_STACK_FRAME_I6_FP_OFFSET]         ba      save_frame_loop        nop done_flushing:         add     %g3, 2, %g3                   ! calculate desired WIM        and     %g3, SPARC_NUMBER_OF_REGISTER_WINDOWS - 1, %g3        mov     1, %g4        sll     %g4, %g3, %g4                 ! g4 = new WIM        mov     %g4, %wim         mov     %g1, %psr                     ! restore PSR        nop        nop        nop        /*         *  Restore the global registers we used         */        mov     %l3, %g1        mov     %l4, %g2        mov     %l5, %g3        mov     %l6, %g4        mov     %l7, %g5        jmpl    %l2, %g0        rett    %l2 + 4/* end of file */

⌨️ 快捷键说明

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