Annotation of cci/d/dmp4/fault_handlers.s, revision 1.1

1.1     ! root        1: 
        !             2: /******************************************************************************
        !             3: *
        !             4: *      SPECIAL FAULT HANDLERS FOR THE FPP DEMAND PAGE TEST
        !             5: *
        !             6: *  This file contains the special handlers for Translation (page) Fault,
        !             7: *  Priveleged Instruction Fault events, and the FPP Emulation (FPM) Traps. 
        !             8: *  The handlers for the other events are located in "evthandlers.s". There 
        !             9: *  handlers for these events in "evthandlers.s" too but they aren't used in 
        !            10: *  this *  macro test.
        !            11: *  These routines are included in the systems initialyzer (init.x) at 
        !            12: *  assembly time. While it doesn't appear in the makefile, terrible things 
        !            13: *  will happen if this file is removed.
        !            14: *
        !            15: *   7-Jun-85  -added code to trap on a specific page fault occurrence.
        !            16: *  13-Jun-85  -added code to spot corrupted return addresses
        !            17: *  18-Jul-85  -added the FPM trap handler
        !            18: ******************************************************************************/
        !            19: 
        !            20: 
        !            21: /******************************************************************************
        !            22: *              ADDRESS TRANSLATION EXCEPTION HANDLER
        !            23: *
        !            24: *  This code is executed on an address translation (page) fault.
        !            25: *  It will bump the translation fault count, validate the page that caused
        !            26: *  the fault, change the code cache key, and restart the failing instruction.
        !            27: *  If the faulting instruction is not a 'load accumulator' type then the
        !            28: *  current accumulator will be checked to see if it was corrupted by the
        !            29: *  event.
        !            30: *
        !            31: *  On entry, the stack is:
        !            32: *      ( SP+12 ) PSL value at the time of the fault
        !            33: *      ( SP+8  ) PC of the faulting instruction
        !            34: *      ( SP+4  ) Virtual Address of the fault (operand or instruction)
        !            35: *      ( SP    ) Fault Type  ( unused here )
        !            36: *
        !            37: *  NOTE: The PC and the PSL aren't removed from the stack. This keeps them 
        !            38: *        where the REI can use them to return to the test code.
        !            39: *****************************************************************************/
        !            40:        .align  2
        !            41:        .globl  _Trans
        !            42: _Trans:
        !            43:        mtpr    $0x1f,$IPL              /* disable the clock, etc.          */
        !            44:        movl    r0,_trans_r0            /* save register 0                  */
        !            45:        movl    (sp)+,r0                /* Ignore the fault type            */
        !            46:        movl    (sp)+,_f_vaddr          /* Get VA that caused fault         */
        !            47:        incl    _no_page_faults         /* bump translation fault count     */
        !            48:        tstl    _pipe_test              /* If we aren't running one of the  */
        !            49:        bneq    1f                      /*    pipelined tests then compare  */
        !            50:        cmpl    (sp),_code_addr         /*       the fault's address to the */
        !            51:        beql    1f                      /*          instruction's address   */
        !            52:        movl    r0,_pop_val_1           /* MAJOR ERROR!! -CORRUPTED STACK!! */
        !            53:        movl    _f_vaddr,_pop_val_2     /*   save the stack data for the    */
        !            54:        movl    (sp),_pop_val_3         /*      error report                */
        !            55:        movl    (sp)+,_pop_val_3        /*  ( type, VA, PC, & PSL saved )   */
        !            56:        callf   $4,_bad_trans_stack     /* handle it (and don't come back)  */
        !            57: 1:     nop
        !            58:        shar    $PGSHIFT,_f_vaddr,r0    /* R0 = PTE at fault                */
        !            59:        orl2    $0x80000000,_Sysmap[r0] /* Turn Valid bit on in page table  */
        !            60:        mtpr    _f_vaddr,$TBIS
        !            61: /*****************************************************************************
        !            62: *      How many page faults have occurred? (a fun place to sync an analyzer)
        !            63: *****************************************************************************/
        !            64:        movl    _no_page_faults,r0
        !            65:        cmpl    $1,r0
        !            66:        bneq    1f
        !            67:        brb     2f                      /* This is the 1st page fault       */
        !            68: 1:     cmpl    $2,r0
        !            69:        bneq    1f
        !            70:        nop
        !            71:        nop
        !            72:        brb     2f                      /* This is the 2nd page fault       */
        !            73: 1:     cmpl    $3,r0
        !            74:        bneq    1f
        !            75:        nop
        !            76:        nop
        !            77:        brb     2f                      /* This is the 3rd page fault       */
        !            78: 1:     cmpl    $4,r0
        !            79:        bneq    1f
        !            80:        nop
        !            81:        nop
        !            82:        brb     2f                      /* This is the 4th page fault       */
        !            83: 1:     cmpl    $5,r0
        !            84:        bneq    1f
        !            85:        nop
        !            86:        nop
        !            87:        brb     2f                      /* This is the 5th page fault       */
        !            88: 1:     cmpl    $6,r0
        !            89:        bneq    1f
        !            90:        nop
        !            91:        nop
        !            92:        brb     2f                      /* This is the 6th page fault       */
        !            93: 1:     cmpl    $7,r0
        !            94:        bneq    1f
        !            95:        nop
        !            96:        nop
        !            97:        brb     2f                      /* This is the 7th page fault       */
        !            98: 1:     cmpl    $8,r0
        !            99:        bneq    1f
        !           100:        nop
        !           101:        nop
        !           102:        brb     2f                      /* This is the 8th page fault       */
        !           103: 1:     cmpl    $9,r0
        !           104:        bneq    1f
        !           105:        nop
        !           106:        nop
        !           107:        brb     2f                      /* This is the  9th page fault      */
        !           108:        nop                             /* This is the 10th page fault      */
        !           109:        nop
        !           110: 2:
        !           111: /*****************************************************************************
        !           112: *      Should we compare the current accumulator to the initial one?
        !           113: *****************************************************************************/
        !           114:        tstl    _pipe_test              /* don't check the accumulator      */
        !           115:        bneq    1f                      /*   ... during pipelined subtests  */
        !           116:        tstl    _load_type_inst         /* don't check the accumulator      */
        !           117:        bneq    1f                      /*   ... for load type instructions */
        !           118:        tstl    _force_loop             /* don't check the accumulator      */
        !           119:        bneq    1f                      /*   ... during error loops         */
        !           120:        tstl    _trans_acc_error        /* don't check the accumulator      */
        !           121:        bneq    1f                      /*   ... if it is already bad       */
        !           122:        callf   $4,_chk_trans_acc       /* verify the current accumulator   */
        !           123: 1:
        !           124: /*****************************************************************************
        !           125: *      Bump the code cache key if we're running with code cache misses
        !           126: *****************************************************************************/
        !           127:        tstl    _i_cache_hit            /* are we running with cache hits?  */
        !           128:        bneq    2f                      /*    yes -don't bump the cache key */
        !           129:        incl    _Codek                  /*     no -bump code cache key      */
        !           130:        cmpl    _Codek,$255             /* Last key yet ?                   */
        !           131:        jlss    1f
        !           132:        movl    $1,_Codek               /* Reset Code key to 1              */
        !           133:        mtpr    $1,$PACC                /* Purge all code cache             */
        !           134: 1:
        !           135:        mtpr    _Codek,$CCK             /* Set new key                      */
        !           136: 2:
        !           137:        nop
        !           138:        movl    _trans_r0,r0            /* restore register 0               */
        !           139:        rei                             /* return to the instruction        */
        !           140:  
        !           141:        .align  2
        !           142: _trans_r0:                             /* save register 0 here             */
        !           143:        .long   0
        !           144: 
        !           145: 
        !           146: 
        !           147: 
        !           148: 
        !           149: /*****************************************************************************
        !           150: *           PRIVILEGE INSTRUCTION EXEPTION HANDLER
        !           151: * The privileged instruction event is used by the RUN_CODE routine to switch
        !           152: * from User Mode back to Kernal Mode.
        !           153: *
        !           154: *  On entry, the stack is:
        !           155: *        PSL value at the time of the fault
        !           156: *        PC of the faulting instruction
        !           157: *              
        !           158: *****************************************************************************/
        !           159:        .align  2
        !           160:        .globl  _Prvis
        !           161: _Prvis:
        !           162:        mtpr    $0x1f,$IPL              /* Set IPL to HIGH                  */
        !           163:        movl    (sp)+,_act_pc           /* Get the PC that caused the fault */
        !           164:        movl    (sp)+,_f_ptr            /* Get the PSL from the stack       */
        !           165:        cmpl    _act_pc,$_run_code_mtpr /* was it from RUN_CODE?            */
        !           166:        bneq    1f
        !           167:        pushl   _run_code_psl           /* push "run_code"'s PSL            */
        !           168:        pushl   $_run_code_mtpr         /* push the return address          */
        !           169:        rei                             /* return to "run_code"             */
        !           170: 1:
        !           171:        pushl   _f_ptr                  /* push the PSL back on the stack   */
        !           172:        pushl   _act_pc                 /* push the PC back on the stack    */
        !           173:        pushl   $0x2c                   /* push the Priv. Instr. Fault code */
        !           174:        callf   $8,_XTrap               /* report an invalid fault          */
        !           175: 
        !           176: 
        !           177: 
        !           178: 
        !           179: /******************************************************************************
        !           180: *              FPP EMULATION TRAP HANDLER
        !           181: *
        !           182: *  This code is executed after an FPP Emulation trap. These traps are to allow
        !           183: *  the software to emulate complex FPP instructions when there is no FPP in
        !           184: *  the system.
        !           185: *  If the trap was expected, this code will save the stack values and go to 
        !           186: *  the address in "event_return". If the trap wasn't expected then the
        !           187: *  general event handler ("fpp_event") will be called.
        !           188: *
        !           189: *  On entry, the stack is:
        !           190: *      ( SP+16 ) PSL value at the time of the fault
        !           191: *      ( SP+12 ) PC of the NEXT instruction
        !           192: *      ( SP+8  ) OP-CODE of the instruction to be emulated
        !           193: *      ( SP+4  ) Least significant longword of the operand (if any)
        !           194: *      ( SP    )  Most significant longword of the operand (if any)
        !           195: *
        !           196: *  NOTE: If the trap was not expected then nothing will be popped from the
        !           197: *        stack. If is was expected then everything will be popped.
        !           198: * 
        !           199: *  NOTE2: This code is responsible for saving the PSL, registers, and the
        !           200: *       accumulator - it bypasses the parts in "run_code" that save them.
        !           201: *****************************************************************************/
        !           202:        .align  2
        !           203:        .globl  _FPM_handler
        !           204: _FPM_handler:
        !           205:        movpsl  _psl_val                /* save the psl        */
        !           206:        mtpr    $0x1f,$IPL              /* disable the clock, etc.   */
        !           207:        movl    _psl_val,_post_event_psl   /* make a copy for DMP4 */
        !           208:        storer  $0x1fff,_store_regs     /* store regs 0 - 12   */
        !           209:        moval   (r13),_post_event_fp    /* save the frame pointer */
        !           210:        moval   (r14),_post_event_sp    /* save the stack pointer */
        !           211:        movl    $1,_fpm_trap_occurred   /* set Trap Occurred flag */
        !           212:        tstl    _emulated_inst          /* Was the trap expected? */
        !           213:        bneq    1f                      /*   Yes, jump            */
        !           214:        pushl   $FPM_CODE               /*   No, -unexpected event */
        !           215:        callf   $8,_XTrap
        !           216:        halt
        !           217: 1:                                     /* The trap was expected */
        !           218:        cmpl    _acc_st_size,$DBL       /* check the accumulator's size */
        !           219:        beql    1f
        !           220:        stf     _dbl_st_acc             /* store the sgl accumulator */
        !           221:        brb     2f
        !           222: 1:     std     _dbl_st_acc             /* store the dbl accumulator */
        !           223: 2:
        !           224:        movl    (sp)+,_fpm_ms_op        /* pop the MS operand  */
        !           225:        movl    (sp)+,_fpm_ls_op        /* pop the LS operand  */
        !           226:        movl    (sp)+,_fpm_op_code      /* pop the op-code     */
        !           227:        movl    (sp)+,_fpm_pc           /* pop the next PC     */
        !           228:        movl    (sp)+,_fpm_psl          /* pop the stack's PSL */
        !           229:        bitl    $PSL_DBL,_psl_val       /* check for DBL Acc.  */
        !           230:        beql    1f 
        !           231:        std     _post_evt_acc           /* save the DBL Acc.   */
        !           232:        brb     2f
        !           233: 1:     stf     _post_evt_acc           /* save the SGL Acc.   */
        !           234:        clrl    _post_evt_acc+4
        !           235: 2:
        !           236:        pushl   _run_code_psl           /* push this Kernal mode PSL       */
        !           237:        pushl   _event_return           /* push the return address         */
        !           238:        rei                             /* return to "run_code"            */
        !           239: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.