Annotation of cci/sys/tahoe/locore.s, revision 1.1.1.1

1.1       root        1: /*     locore.s        4.50    81/05/18        */
                      2:  # -------------------
                      3: 
                      4: #include "../machine/mtpr.h"
                      5: #include "../machine/trap.h"
                      6: #include "../machine/psl.h"
                      7: #include "../machine/pte.h"
                      8: #include "../machine/cp.h"
                      9: #include "../machine/mem.h"
                     10: #include "../machine/fp.h"
                     11: 
                     12: #include "../h/errno.h"
                     13: 
                     14:        .set    HIGH,0x1f       # mask for total disable
                     15:        .set    BERVEC,0x80     # offset into scb of the bus error vector 
                     16:        .set    RESTVEC,0x8     # offset into scb of the restart vector 
                     17:        .set    MEMUNIT,64*1024 # minimum memory increment
                     18: 
                     19:        .set    NISP,3          # number of interrupt stack pages
                     20:        .set    SYSTEM,0xC0000000 # virtual address of system start
                     21:        .set    PPAGES,0x100000  # Number of possible pages in P0,P1, etc.
                     22: 
                     23: /* ACBL for non-negative '_add' */
                     24: #define ACBL(_limit,_add,_index,_displ) \
                     25:        addl2   _add,_index; \
                     26:        cmpl    _index,_limit; \
                     27:        bleq    _displ
                     28: 
                     29: /* _ACBL for negative '_add' */
                     30: #define _ACBL(_limit,_add,_index,_displ) \
                     31:        addl2   _add,_index; \
                     32:        cmpl    _index,_limit; \
                     33:        bgeq    _displ
                     34: 
                     35: #define        MOVC3(_len,_srcaddr,_dstaddr) \
                     36:        movl    _srcaddr,r0; \
                     37:        movl    _dstaddr,r1; \
                     38:        movl    _len,r2; \
                     39:        movblk
                     40: 
                     41: /* Keep address of psl if coming from user mode */
                     42: #define CHECK_SFE(_delta) \
                     43:        bitl    $PSL_CURMOD,_delta(sp); \
                     44:        jeql    1f; \
                     45:        moval   _delta(sp),_user_psl; \
                     46: 1:
                     47: 
                     48: /*
                     49:  * User structure is UPAGES at top of user space.
                     50:  */
                     51:        .globl  _u
                     52:        .set    _u,SYSTEM - UPAGES*NBPG
                     53: 
                     54: /*
                     55:  * Restart stack. Used on power recovery or panic.
                     56:  * Takes a core-dump and then halts.
                     57:  */ 
                     58:        .globl  _rsstk
                     59: 
                     60: _rsstk:        .space  1024-8
                     61:        .globl  pwfl_stk        
                     62: pwfl_stk:      .space  4
                     63: dumpflag:      .space  4
                     64: 
                     65:        .globl  _intstack
                     66: _intstack:
                     67:        .space  NISP*NBPG
                     68: eintstack:
                     69: 
                     70:        .data
                     71:        .globl  pwfl_r0
                     72: pwfl_r0:       .space  14*4            # Enough for r0 - r13
                     73:        .globl  pwfl_sp
                     74: pwfl_sp:       .long   0x12345678      # r14
                     75:        .globl  pwfl_SCBB
                     76: pwfl_SCBB:     .long   0x12345678
                     77:        .globl  pwfl_SBR
                     78: pwfl_SBR:      .long   0x12345678
                     79:        .globl  pwfl_SLR
                     80: pwfl_SLR:      .long   0x12345678
                     81:        .globl  pwfl_P0BR
                     82: pwfl_P0BR:     .long   0x12345678
                     83:        .globl  pwfl_P0LR
                     84: pwfl_P0LR:     .long   0x12345678
                     85:        .globl  pwfl_P1BR
                     86: pwfl_P1BR:     .long   0x12345678
                     87:        .globl  pwfl_P1LR
                     88: pwfl_P1LR:     .long   0x12345678
                     89:        .globl  pwfl_P2BR
                     90: pwfl_P2BR:     .long   0x12345678
                     91:        .globl  pwfl_P2LR
                     92: pwfl_P2LR:     .long   0x12345678
                     93:        .globl  pwfl_IPL
                     94: pwfl_IPL:      .long   0x12345678
                     95:        .globl  pwfl_DCK
                     96: pwfl_DCK:      .long   0x12345678
                     97:        .globl  pwfl_CCK
                     98: pwfl_CCK:      .long   0x12345678
                     99:        .globl  pwfl_PCBB
                    100: pwfl_PCBB:     .long   0x12345678
                    101:        .globl  pwfl_ISP
                    102: pwfl_ISP:      .long   0x12345678
                    103:        .globl  pwfl_KSP
                    104: pwfl_KSP:      .long   0x12345678
                    105:        .globl  pwfl_USP
                    106: pwfl_USP:      .long   0x12345678
                    107:        .globl  pwfl_MME
                    108: pwfl_MME:      .long   0x12345678
                    109:        .globl  pwfl_PSL
                    110: pwfl_PSL:      .long   0x12345678
                    111: 
                    112: /*
                    113:  * Do a dump.
                    114:  * Called by auto-restart.
                    115:  * May be called manually.
                    116:  */
                    117:        .align  2
                    118:        .text
                    119:        .globl  _Xdoadump
                    120:        .globl  _doadump
                    121: _Xdoadump:                     # CP brings Tahoe here on power recovery
                    122:        loadr   $0x3fff,pwfl_r0 # Restore r0 - r13
                    123:        movl    pwfl_sp,sp      # Restore sp ( = r14 )
                    124:        mtpr    pwfl_SCBB,$SCBB
                    125:        mtpr    pwfl_SBR,$SBR   # Restore all re_loadable registers
                    126:        mtpr    pwfl_SLR,$SLR
                    127:        mtpr    pwfl_P0BR,$P0BR
                    128:        mtpr    pwfl_P0LR,$P0LR
                    129:        mtpr    pwfl_P1BR,$P1BR
                    130:        mtpr    pwfl_P1LR,$P1LR
                    131:        mtpr    pwfl_P2BR,$P2BR
                    132:        mtpr    pwfl_P2LR,$P2LR
                    133:        mtpr    pwfl_IPL,$IPL
                    134:        mtpr    pwfl_DCK,$DCK
                    135:        mtpr    pwfl_CCK,$CCK
                    136:        mtpr    pwfl_PCBB,$PCBB
                    137:        mtpr    pwfl_ISP,$ISP
                    138:        mtpr    pwfl_KSP,$KSP
                    139:        mtpr    pwfl_USP,$USP
                    140: 
                    141:        bicpsw  $0xff           # Restore PSW.
                    142:        bispsw  pwfl_PSL+2      # Set original bits back (just in case..)
                    143: /* now go to mapped mode */
                    144: /* Have to change PC to system addresses */
                    145:        mtpr    $1,$PACC        # Thoroughly clean up caches.
                    146:        mtpr    $1,$PADC
                    147:        mtpr    $1,$TBIA
                    148:        mtpr    pwfl_MME,$MME   # Restore MME. Last thing to be done.
                    149:        jmp     *$0f
                    150: _doadump:
                    151:        .word 0
                    152: #define        _rsstkmap       _Sysmap+12                      
                    153:                        # Tahoe storage, scb, rsstk, interrupt stack
                    154: 0:
                    155:        mtpr    $HIGH,$IPL
                    156:        andl2   $0!PG_PROT,_rsstkmap
                    157:        orl2    $PG_KW,_rsstkmap                # Make dump stack r/w
                    158:        tstl    dumpflag                        # dump only once!
                    159:        bneq    1f
                    160:        movl    $1,dumpflag
                    161:        mtpr    $0,$TBIA
                    162:        movab   dumpflag,sp
                    163:        callf   $4,_dumpsys
                    164: 1:
                    165:        halt
                    166: 
                    167: /*
                    168:  * Interrupt vector routines
                    169:  */ 
                    170:        .globl  _waittime
                    171: 
                    172: #define        SCBVEC(name) \
                    173:        .align 2; \
                    174:        .globl _X/**/name; \
                    175: _X/**/name
                    176: #define        PANIC(msg)      clrl _waittime; pushab 1f; \
                    177:                        callf $8,_panic; 1: .asciz msg
                    178: #define        PRINTF(n,msg)   pushab 1f; callf $(n*4)+4,_printf; MSG(msg)
                    179: #define        MSG(msg)        .data; 1: .asciz msg; .text
                    180: 
                    181:                        # these registers are not restored by the C-compiler.
                    182: #define        PUSHR           pushl r0; pushl r1;
                    183: #define        POPR            movl (sp)+, r1; movl (sp)+, r0;
                    184:                        # mask for error code on stack.
                    185: 
                    186: #define SAVE_FPSTAT(_delta)    bitl    $PSL_DBL,_delta(sp); \
                    187:                                beql    1f; \
                    188:                                pushl   $1; \
                    189:                                pushd; \
                    190:                                jmp     2f; \
                    191:                        1:      pushl   $0; \
                    192:                                pushl   $0; \
                    193:                                stf     -(sp); \
                    194:                        2:      tstl    _u+PCB_SAVACC; \
                    195:                                bneq    3f; \
                    196:                                moval   0(sp),_u+PCB_SAVACC; \
                    197:                                orl2    $2,8(sp);\
                    198:                        3:      pushl   $0;
                    199: 
                    200: #define REST_FPSTAT            tstl    (sp)+; \
                    201:                                bitl    $2,8(sp);\
                    202:                                beql    1f;\
                    203:                                movl    $0,_u+PCB_SAVACC; \
                    204:                        1:      bitl    $1,8(sp); \
                    205:                                beql    2f; \
                    206:                                ldd     (sp); \
                    207:                                jmp     3f; \
                    208:                        2:      ldf     (sp); \
                    209:                        3:      moval   12(sp),sp;
                    210: 
                    211: #define REST_ACC               tstl    _u+PCB_SAVACC; \
                    212:                                beql    2f; \
                    213:                                movl    _u+PCB_SAVACC,r1; \
                    214:                                andl3   $(EXPMASK|SIGNBIT),(r1),-(sp); \
                    215:                                cmpl    $0x80000000,(sp)+; \
                    216:                                bneq    3f; \
                    217:                                clrl    (r1); \
                    218:                        3:      bitl    $1,8(r1); \
                    219:                                beql    1f; \
                    220:                                ldd     (r1); \
                    221:                                jmp     2f; \
                    222:                        1:      ldf     (r1); \
                    223:                        2:      ;
                    224: 
                    225: #define PUSHBPAR       pushab  6*4(sp) /* Push address of buserr paramters */
                    226: #define BPAR1          28              /* Offset to first hardware parameter */
                    227: 
                    228: SCBVEC(buserr):
                    229:        CHECK_SFE(12)
                    230:        SAVE_FPSTAT(12);
                    231:        PUSHR
                    232:        andl3   BPAR1(sp),$ERRCD,r0
                    233:        jeql    go_on
                    234:        cmpl    r0,$APE
                    235:        jneq    1f
                    236:        halt            # Address parity error !!!
                    237: 1:     cmpl    r0,$VBE
                    238:        jneq    go_on
                    239:        halt            # Versabus error !!!
                    240: go_on:
                    241:        PUSHBPAR        # Pointer to parameters
                    242:        callf   $8,_buserror
                    243:        POPR
                    244:        REST_FPSTAT;
                    245:        movab   8(sp),sp        # Remove hardware parameters
                    246:        rei
                    247: 
                    248: SCBVEC(powfail):               # We should be on interrupt stack now.
                    249:        movpsl  pwfl_PSL        # Keeps all flags, etc.
                    250:        storer  $0x3fff,pwfl_r0 # Saves r0 - r13
                    251:        moval   0(sp),pwfl_sp   # Saves sp ( = r14 )
                    252:        mfpr    $SBR,pwfl_SBR   # Save all re_loadable registers
                    253:        mfpr    $SLR,pwfl_SLR
                    254:        mfpr    $P0BR,pwfl_P0BR
                    255:        mfpr    $P0LR,pwfl_P0LR
                    256:        mfpr    $P1BR,pwfl_P1BR
                    257:        mfpr    $P1LR,pwfl_P1LR
                    258:        mfpr    $P2BR,pwfl_P2BR
                    259:        mfpr    $P2LR,pwfl_P2LR
                    260:        mfpr    $IPL,pwfl_IPL
                    261:        mfpr    $MME,pwfl_MME  
                    262:        mfpr    $DCK,pwfl_DCK
                    263:        mfpr    $CCK,pwfl_CCK
                    264:        mfpr    $PCBB,pwfl_PCBB
                    265:        mfpr    $ISP,pwfl_ISP
                    266:        mfpr    $SCBB,pwfl_SCBB
                    267:        mfpr    $KSP,pwfl_KSP
                    268:        mfpr    $USP,pwfl_USP
                    269:        moval   _Xdoadump-SYSTEM,_scb+RESTVEC
                    270:        halt
                    271: 
                    272: SCBVEC(stray):
                    273:        PUSHR;
                    274:        movpsl  r0
                    275:        shrl    $16, r0,-(sp) 
                    276:        andl2   $0x1f, (sp)
                    277:        PRINTF(2, "******* Undefined interrupt at ipl 0x%x *******\n");
                    278:        POPR;
                    279:        rei
                    280: 
                    281: #include "../net/netisr.h"
                    282:        .globl  _netisr
                    283: SCBVEC(netintr):
                    284:        CHECK_SFE(4)
                    285:        SAVE_FPSTAT(4)
                    286:        PUSHR
                    287: 
                    288:        bbc     $NETISR_RAW,_netisr,1f
                    289:        andl2   $(0!(1<<NETISR_RAW)),_netisr    
                    290:        callf   $4,_rawintr     
                    291: 1:
                    292: #ifdef INET
                    293: #include "../netinet/in_systm.h"
                    294:        bbc     $NETISR_IP,_netisr,1f   
                    295:        andl2   $(0!(1<<NETISR_IP)),_netisr
                    296:        callf   $4,_ipintr      
                    297: 1:
                    298: #endif
                    299: #ifdef NS
                    300:        bbc     $NETISR_NS,_netisr,1f   
                    301:        andl2   $(0!(1<<NETISR_NS)),_netisr
                    302:        callf   $4,_nsintr      
                    303: 1:
                    304: #endif
                    305:        POPR; 
                    306:        REST_FPSTAT
                    307:        rei
                    308: SCBVEC(soft15):
                    309: SCBVEC(soft14):
                    310: SCBVEC(soft13):
                    311: SCBVEC(soft11):
                    312: SCBVEC(soft10):
                    313: #ifndef SIMIO
                    314: SCBVEC(soft9):
                    315: #endif
                    316: SCBVEC(soft7):
                    317: SCBVEC(soft6):
                    318: SCBVEC(soft5):
                    319: SCBVEC(soft4):
                    320: #ifndef SIMIO
                    321: SCBVEC(soft3):
                    322: SCBVEC(soft2):
                    323: SCBVEC(soft1):
                    324: #endif
                    325:        PUSHR
                    326:        PRINTF(1, "******* Undefined software interrupt *******\n")
                    327:        POPR;
                    328:        rei
                    329: 
                    330: #ifdef SIMIO
                    331: SCBVEC(soft2):
                    332: #endif
                    333: SCBVEC(cnrint):
                    334:        CHECK_SFE(4)
                    335:        SAVE_FPSTAT(4);PUSHR; 
                    336:        pushl $CPCONS; callf $8,_cnrint; POPR; incl _cnt+V_INTR;
                    337:        REST_FPSTAT; rei
                    338: #ifdef SIMIO
                    339: SCBVEC(soft3):
                    340: #endif
                    341: SCBVEC(cnxint):
                    342:        CHECK_SFE(4)
                    343:        SAVE_FPSTAT(4);PUSHR; 
                    344:        pushl $CPCONS; callf $8,_cnxint; POPR; REST_FPSTAT;
                    345:        incl _cnt+V_INTR; rei
                    346: SCBVEC(rmtrint):
                    347:        CHECK_SFE(4)
                    348:        SAVE_FPSTAT(4); PUSHR; 
                    349:        pushl $CPREMOT; callf $8,_cnrint; POPR; REST_FPSTAT;
                    350:        incl _cnt+V_INTR; rei
                    351: SCBVEC(rmtxint):
                    352:        CHECK_SFE(4)
                    353:        SAVE_FPSTAT(4); PUSHR; 
                    354:        pushl $CPREMOT; callf $8,_cnxint; POPR; REST_FPSTAT;
                    355:        incl _cnt+V_INTR; rei
                    356: #ifdef SIMIO
                    357: SCBVEC(soft9):
                    358: #endif
                    359: 
                    360: #define PUSHPCPSL      pushl 5*4+2*4(sp); pushl 5*4+2*4(sp);
                    361: 
                    362: SCBVEC(hardclock):
                    363:        CHECK_SFE(4)
                    364:        SAVE_FPSTAT(4)
                    365:        PUSHR
                    366:        PUSHPCPSL                               # push pc and psl
                    367:        callf $12,_hardclock                    # hardclock(pc,psl)
                    368:        POPR;
                    369:        REST_FPSTAT
                    370:        incl    _cnt+V_INTR             ## temp so not to break vmstat -= HZ
                    371:        rei
                    372: SCBVEC(softclock):
                    373:        CHECK_SFE(4)
                    374:        SAVE_FPSTAT(4)
                    375:        PUSHR
                    376:        PUSHPCPSL                               # push pc and psl
                    377:        callf $12,_softclock                    # softclock(pc,psl)
                    378:        POPR; 
                    379:        REST_FPSTAT
                    380:        rei
                    381: 
                    382: /*
                    383:  * Trap and fault vector routines
                    384:  */ 
                    385: #define        TRAP(a) pushl $T_/**/a; jbr alltraps
                    386: 
                    387: /*
                    388:  * Ast delivery (profiling and/or reschedule)
                    389:  */
                    390: /*
                    391:  * When we want to reschedule we will force a memory fault by setting the m.s.b
                    392:  *  of P0LR. Then , on memory fault if m.s.b of P0LR is on we will clear it and
                    393:  *  TRAP(astflt).
                    394:  *
                    395:  */
                    396:  
                    397:                                        # if this bit is on it is an ast.
                    398: #define        ASTBIT  0x00100000      
                    399: #define                P0MASK  0xc0000000
                    400: 
                    401: SCBVEC(kspnotval):
                    402:        CHECK_SFE(4)
                    403:        pushl $0;
                    404:        SAVE_FPSTAT(8)
                    405:        TRAP(KSPNOTVAL)
                    406: SCBVEC(privinflt):
                    407:        CHECK_SFE(4)
                    408:        pushl $0;
                    409:        SAVE_FPSTAT(8)
                    410:        TRAP(PRIVINFLT)
                    411: SCBVEC(resopflt):
                    412:        CHECK_SFE(4)
                    413:        pushl $0;
                    414:        SAVE_FPSTAT(8)
                    415:        TRAP(RESOPFLT)
                    416: SCBVEC(resadflt):
                    417:        CHECK_SFE(4)
                    418:        pushl $0;
                    419:        SAVE_FPSTAT(8)
                    420:        TRAP(RESADFLT)
                    421: SCBVEC(bptflt):
                    422:        CHECK_SFE(4)
                    423:        pushl $0;
                    424:        SAVE_FPSTAT(8)
                    425:        TRAP(BPTFLT)
                    426: SCBVEC(tracep):
                    427:        CHECK_SFE(4)
                    428:        pushl $0;
                    429:        SAVE_FPSTAT(8)
                    430:        TRAP(TRCTRAP)
                    431: SCBVEC(alignflt):
                    432:        CHECK_SFE(4)
                    433:        pushl $0;
                    434:        SAVE_FPSTAT(8)
                    435:        TRAP(ALIGNFLT)
                    436: SCBVEC(arithtrap):
                    437:        CHECK_SFE(8)
                    438:        SAVE_FPSTAT(8)
                    439:        TRAP(ARITHTRAP)
                    440: 
                    441: SCBVEC(protflt):
                    442:        CHECK_SFE(12)
                    443:        bitl    $1,(sp)+
                    444:        jneq    segflt
                    445:        SAVE_FPSTAT(8)
                    446:        TRAP(PROTFLT)
                    447: segflt:
                    448:        SAVE_FPSTAT(8)
                    449:        TRAP(SEGFLT)
                    450: 
                    451: SCBVEC(fpm):                   # Floating Point eMulation
                    452:        .globl  _fpemulate
                    453:        CHECK_SFE(16)
                    454:        SAVE_FPSTAT(16)
                    455:        callf   $4,_fpemulate
                    456:        REST_FPSTAT
                    457:        moval   8(sp),sp        # Pop operand
                    458:        tstl    (sp)            # Stack= PSL, PC, return_code
                    459:        jneq    _Xarithtrap     # If not OK, emulate F.P. exception
                    460:        movab   4(sp),sp        # Else remove return_code and
                    461:        rei
                    462: 
                    463: SCBVEC(sfexcep):
                    464:        CHECK_SFE(4)
                    465:        pushl $0
                    466:        SAVE_FPSTAT(8)
                    467:        TRAP(ASTFLT)
                    468: 
                    469: SCBVEC(transflt):
                    470:        CHECK_SFE(12)
                    471:        bitl    $1,(sp)+
                    472:        bneq    tableflt
                    473: pageflt:
                    474:        SAVE_FPSTAT(8)
                    475:        TRAP(PAGEFLT)
                    476: tableflt:
                    477:        SAVE_FPSTAT(8)
                    478:        TRAP(TABLEFLT)
                    479: 
                    480: #define REST_STACK     movab 4(sp), sp; REST_FPSTAT; movab 4(sp), sp
                    481: 
                    482: alltraps:
                    483:        mfpr    $USP,-(sp); 
                    484:        callf $4,_trap; mtpr (sp)+,$USP
                    485:        incl    _cnt+V_TRAP
                    486:        REST_STACK                      # pop type, code, an fp stuff
                    487:        mtpr    $HIGH,$IPL              ## dont go to a higher IPL (GROT)
                    488:        rei
                    489: 
                    490: SCBVEC(syscall):
                    491:        CHECK_SFE(8)
                    492:        SAVE_FPSTAT(8)
                    493:        pushl   $T_SYSCALL
                    494:        mfpr    $USP,-(sp); callf $4,_syscall; mtpr (sp)+,$USP
                    495:        incl    _cnt+V_SYSCALL
                    496:        REST_STACK                      # pop type, code, an fp stuff
                    497:        mtpr    $HIGH,$IPL              ## dont go to a higher IPL (GROT)
                    498:        rei
                    499: 
                    500: /*
                    501:  * System page table
                    502:  */ 
                    503: #define        vaddr(x)        ((((x)-_Sysmap)/4)*NBPG+SYSTEM)
                    504: #define        SYSMAP(mname, vname, npte)                      \
                    505: _/**/mname:    .globl  _/**/mname;             \
                    506:        .space  npte*4;                         \
                    507:        .globl  _/**/vname;                     \
                    508:        .set    _/**/vname,vaddr(_/**/mname)
                    509: 
                    510:        .data
                    511:        .align  2
                    512:        SYSMAP(Sysmap   ,Sysbase        ,SYSPTSIZE      )
                    513:        SYSMAP(VMEMbeg  ,vmembeg        ,0              )
                    514:        SYSMAP(VMEMmap  ,vmem           ,IOSIZE         )
                    515:        SYSMAP(ACE0map  ,ace0utl        ,(ACEBPTE+1)    )
                    516:        SYSMAP(ACE1map  ,ace1utl        ,(ACEBPTE+1)    )
                    517:        SYSMAP(VMEMend  ,vmemend        ,0              )
                    518:        SYSMAP(Usrptmap ,usrpt          ,USRPTSIZE      )
                    519:        SYSMAP(Forkmap  ,forkutl        ,UPAGES         )
                    520:        SYSMAP(Xswapmap ,xswaputl       ,UPAGES         )
                    521:        SYSMAP(Xswap2map,xswap2utl      ,UPAGES         )
                    522:        SYSMAP(Swapmap  ,swaputl        ,UPAGES         )
                    523:        SYSMAP(Pushmap  ,pushutl        ,UPAGES         )
                    524:        SYSMAP(Vfmap    ,vfutl          ,UPAGES         )
                    525:        SYSMAP(VD0map   ,vd0utl         ,(MAXBPTE+1)    )
                    526:        SYSMAP(VD1map   ,vd1utl         ,(MAXBPTE+1)    )
                    527:        SYSMAP(VD2map   ,vd2utl         ,(MAXBPTE+1)    )
                    528:        SYSMAP(VD3map   ,vd3utl         ,(MAXBPTE+1)    )
                    529:        SYSMAP(CY0map   ,cy0utl         ,(TBUFSIZ+1)    )
                    530:        SYSMAP(CY1map   ,cy1utl         ,(TBUFSIZ+1)    )
                    531:        SYSMAP(CMAP1    ,CADDR1         ,1              )
                    532:        SYSMAP(CMAP2    ,CADDR2         ,1              )
                    533:        SYSMAP(mmap     ,vmmap          ,1              )
                    534:        SYSMAP(msgbufmap,msgbuf         ,MSGBUFPTECNT   )
                    535:        SYSMAP(camap    ,cabase         ,16*CLSIZE      )
                    536:        SYSMAP(ecamap   ,calimit        ,0              )
                    537:        SYSMAP(Mbmap    ,mbutl          ,NMBCLUSTERS*CLSIZE)
                    538:        SYSMAP(Msgmap   ,msgutl         ,MSGMAPPTE)
                    539: eSysmap:
                    540:        .globl  _Syssize
                    541:        .set    _Syssize,(eSysmap-_Sysmap)/4
                    542: 
                    543:        .text
                    544: /*
                    545:  * Initialization
                    546:  *
                    547:  * IPL 0x1f; MME 0; scbb, pcbb, sbr, slr, isp, ksp not set
                    548:  *
                    549:  */
                    550: 
                    551:        .align  2
                    552:        .globl  start
                    553: start:
                    554:        .word   0
                    555: 
                    556: /* set system control block base and system page table params */
                    557: 
                    558:        mtpr    $_scb-SYSTEM,$SCBB
                    559:        mtpr    $_Sysmap-SYSTEM,$SBR
                    560:        mtpr    $_Syssize,$SLR
                    561: 
                    562: /* double map the kernel into the virtual user addresses of phys mem */
                    563: /* (to be on the safe side.This is supposed to run in system sace. )  */
                    564:        mtpr    $_Sysmap,$P0BR
                    565:        mtpr    $_Syssize,$P0LR
                    566: 
                    567:        mtpr    $_Sysmap,$P1BR          # Against Murphy
                    568:        mtpr    $_Syssize,$P1LR
                    569: 
                    570: /* set ISP */
                    571:        movl    $_intstack-SYSTEM+NISP*NBPG,sp  # Still physical !
                    572:        mtpr    $_intstack+NISP*NBPG,$ISP
                    573: 
                    574: /* count up memory */
                    575: 
                    576:        clrl    r7
                    577: 1:     pushl   $1; pushl r7; callf $12,_badaddr; tstl r0; bneq 9f
                    578:        addl2   $MEMUNIT,r7
                    579:        brb     1b
                    580: 9:
                    581: /* clear memory from kernel bss and pages for proc 0 u. and page table */
                    582:        movab   _edata,r6
                    583:        movab   _end,r5
                    584:        andl2   $0!SYSTEM,r6
                    585:        andl2   $0!SYSTEM,r5
                    586:        addl2   $(UPAGES*NBPG)+NBPG+NBPG,r5
                    587: 1:     clrl    (r6); ACBL( r5,$4,r6,1b)
                    588: 
                    589: /* trap() and syscall() save r0-r13 in the entry mask (per ../h/reg.h) */
                    590: /* For floating point emulation, we do same for 'fpemulate' */
                    591:        orw2    $0x01fff,_trap
                    592:        orw2    $0x01fff,_syscall
                    593:        orw2    $0x01fff,_fpemulate
                    594: 
                    595: /* initialize system page table: scb and int stack writeable */
                    596:        clrl    r2
                    597:        movab   eintstack,r1 
                    598:        andl2   $0!SYSTEM,r1
                    599:        shrl    $PGSHIFT,r1,r1          # r1-page number of eintstack.
                    600: 
                    601: /* Start by making the processor storage read/only */
                    602: 
                    603:        orl3    $PG_V|PG_KR,r2,_Sysmap[r2]; incl r2;
                    604:        orl3    $PG_V|PG_KR,r2,_Sysmap[r2]; incl r2;
                    605: 
                    606: /* Other parts of the system are read/write for kernel */
                    607: 
                    608: 1:     orl3    $PG_V|PG_KW,r2,_Sysmap[r2]; # data:kernel write + phys=virtual
                    609:        aoblss r1,r2,1b
                    610: 
                    611: /* make rsstk read-only as red zone for interrupt stack */
                    612:        andl2   $0!PG_PROT,_rsstkmap
                    613:        orl2    $PG_V|PG_KR,_rsstkmap           # Make dump stack r/w
                    614: 
                    615: /* make kernel text space read-only */
                    616: /*
                    617:  * HAVE TO CHECK ALL THE MAGIC CONSTANTS USED HERE : $xxxxxx */
                    618: 
                    619:        movab   _etext+NBPG-1,r1
                    620:        andl2   $0!SYSTEM,r1
                    621:        shrl    $PGSHIFT,r1,r1
                    622: 1:     orl3    $PG_V|PG_KR,r2,_Sysmap[r2]
                    623:        aoblss r1,r2,1b
                    624: 
                    625: /* make kernel data, bss, read-write */
                    626:        movab   _end+NBPG-1,r1
                    627:        andl2   $0!SYSTEM,r1
                    628:        shrl    $PGSHIFT,r1,r1
                    629: 1:     orl3    $PG_V|PG_KW,r2,_Sysmap[r2]
                    630:        aoblss r1,r2,1b
                    631: 
                    632: /* now go to mapped mode */
                    633: /* Have to change both PC and SP to system addresses */
                    634:        mtpr    $1,$TBIA
                    635:        mtpr    $1,$PADC        /* needed by HW parity & ECC logic */
                    636:        mtpr    $1,$PACC        /* just in case */
                    637:        mtpr    $1,$MME
                    638:        movab   SYSTEM(sp),sp
                    639:        .globl  go_virt
                    640: go_virt:       
                    641:        jmp     *$0f
                    642: 0:
                    643: 
                    644: /* disable any interrupts */
                    645:        movl    $0,_intenable
                    646: /* init mem sizes */
                    647:        shrl    $PGSHIFT,r7,_maxmem
                    648:        movl    _maxmem,_physmem
                    649:        movl    _maxmem,_freemem
                    650: 
                    651: /* setup context for proc[0] == Scheduler */
                    652:        movab   _end-SYSTEM+NBPG-1,r6
                    653:        andl2   $0!(NBPG-1),r6          # make page boundary
                    654: 
                    655: /* setup page table for proc[0] */
                    656:        shrl    $PGSHIFT,r6,r3                  # r3 = btoc(r6)
                    657:        orl3    $PG_V|PG_KW,r3,_Usrptmap        # init first upt entry
                    658:        incl    r3                              # r3 - next page
                    659:        movab   _usrpt,r0                       # r0 - first user page
                    660:        mtpr    r0,$TBIS
                    661: 
                    662: /* init p0br, p0lr */
                    663:        mtpr    r0,$P0BR        # No P0 for proc[0]
                    664:        mtpr    $0,$P0LR
                    665: 
                    666:        mtpr    r0,$P1BR        # No P1 either
                    667:        mtpr    $0,$P1LR
                    668: 
                    669: 
                    670: /* init p2br, p2lr */
                    671:        movab   NBPG(r0),r0
                    672:        movl    $PPAGES-UPAGES,r1
                    673:        mtpr    r1,$P2LR
                    674:        moval   -4*PPAGES(r0),r2
                    675:        mtpr    r2,$P2BR
                    676: 
                    677: /* setup mapping for UPAGES of _u */
                    678:        clrl    r2; 
                    679:        movl    $SYSTEM,r1
                    680:        addl2   $UPAGES,r3
                    681:        jbr 2f
                    682: 1:     decl    r3
                    683:        moval   -NBPG(r1),r1;   # r1 = virtual add of next (downward) _u page
                    684:        subl2   $4,r0           # r0 = pte address
                    685:        orl3    $PG_V|PG_URKW,r3,(r0)
                    686:        mtpr    r1,$TBIS
                    687: 2:     aobleq  $UPAGES,r2,1b
                    688: 
                    689: /* initialize (slightly) the pcb */
                    690:        movab   UPAGES*NBPG(r1),PCB_KSP(r1)     # KSP starts at end of _u
                    691:        movl    r1,PCB_USP(r1)                  # USP starts just below _u
                    692:        mfpr    $P0BR,PCB_P0BR(r1)
                    693:        mfpr    $P0LR,PCB_P0LR(r1)
                    694:        mfpr    $P1BR,PCB_P1BR(r1)
                    695:        mfpr    $P1LR,PCB_P1LR(r1)
                    696:        mfpr    $P2BR,PCB_P2BR(r1)
                    697:        mfpr    $P2LR,PCB_P2LR(r1)
                    698:        movl    $CLSIZE,PCB_SZPT(r1)            # init u.u_pcb.pcb_szpt
                    699:        movl    r11,PCB_R11(r1)                 # r11 obtained from CP on boot
                    700:        movab   1f,PCB_PC(r1)                   # initial pc
                    701:        clrl    PCB_PSL(r1)                     # kernel mode, ipl=0
                    702:        shll    $PGSHIFT,r3,r3
                    703:        mtpr    r3,$PCBB                        # first pcbb (physical ! )
                    704: 
                    705: /* Go to a 'normal' process mode (kernel) */
                    706: 
                    707:        ldpctx
                    708:        rei             # Actually 'returns' to the next instruction:
                    709: 
                    710: /* put signal trampoline code in u. area */
                    711: 1:     movab   _u,r0
                    712:        movl    sigcode+0,PCB_SIGC+0(r0)
                    713:        movl    sigcode+4,PCB_SIGC+4(r0)
                    714:        movl    sigcode+8,PCB_SIGC+8(r0)
                    715:        movl    sigcode+12,PCB_SIGC+12(r0)
                    716: 
                    717: /* save reboot flags in global _boothowto */
                    718:        movl    r11,_boothowto
                    719: 
                    720: /* calculate firstaddr, and call main() */
                    721:        movab   _end-SYSTEM+NBPG-1,r0
                    722:        shrl    $PGSHIFT,r0,-(sp)
                    723:        addl2   $UPAGES+1,(sp)          # First physical unused page number
                    724:        callf   $8,_main
                    725: 
                    726: /* proc[1] == /etc/init now running here in kernel mode; run icode */
                    727:        pushl   $PSL_CURMOD             # User mode PSL
                    728:        pushl $0                        # PC = 0 (virtual now)
                    729:        rei
                    730: 
                    731: /* signal trampoline code: it is known that this code takes up to 16    */
                    732: /* bytes in pcb.h and in the code above                                */
                    733: /*  The following user stack layout was set up by machdep.c/sendsig    */
                    734: /*     routine:                                                        */
                    735: /*                                                                     */
                    736: /*     +---------------+                                               */
                    737: /*     |  Last PSL     |\                                              */
                    738: /*     +---------------+ > for rei                                     */
                    739: /*  :-->|  Last PC     |/                                              */
                    740: /*  |  +---------------+                                               */
                    741: /*  :___|__*   SP      |\                                              */
                    742: /*     +---------------+ |                                             */
                    743: /*     |  sigmask      | |                                             */
                    744: /*     +---------------+  > cleaned by kcall $139 (sigcleanup)         */
                    745: /*  :-->|  u.u_onstack | |                                             */
                    746: /*  |  +---------------+ |                                             */
                    747: /*  :___|_* copy of SCP        |/                                              */
                    748: /*  |  +---------------+                                               */
                    749: /*  |  |  Process' r0  |                                               */
                    750: /*  |  +---------------+                                               */
                    751: /*  |  |  Process' r1  |                                               */
                    752: /*  |  +---------------+                                               */
                    753: /*  |  | Handler addr. |\                                              */
                    754: /*  |  +---------------+ |                                             */
                    755: /*  :___|_*   SCP      | |                                             */
                    756: /*     +---------------+  > cleaned by ret from calls                  */
                    757: /*     |  u.u_code     | |                                             */
                    758: /*     +---------------+ |                                             */
                    759: /*     |  signal number|/                                              */
                    760: /*     +---------------+                                               */
                    761: /*                                                                     */
                    762: /*   * Stack when entering sigcode; setup by sendsig();                        */
                    763: /*                                                                     */
                    764:        .align  2
                    765: sigcode:                       # When the process executes this code
                    766:                                #  (located in its u. structure), it
                    767:                                #  is in user mode !
                    768:        calls   $4*4+4,*12(sp)  # 4 words popped from stack when this call returns
                    769:        movl    (sp)+,r1
                    770:        movl    (sp)+,r0
                    771:        kcall   $139            # Signal cleanup
                    772:        rei                     # From user mode to user mode !
                    773: 
                    774: /*
                    775:  * Primitives
                    776:  */ 
                    777: 
                    778: /*
                    779:  * badaddr(addr, len)
                    780:  *     see if access addr with a len type instruction causes a machine check
                    781:  *     len is length of access (1=byte, 2=short, 4=long)
                    782:  *     r0 = 0 means good(exists); r0 =1 means does not exist.
                    783:  */
                    784:        .globl  _badaddr
                    785: _badaddr:
                    786:        .word   0x1c    # Keep r4,r3,r2
                    787:        mfpr    $IPL,r1
                    788:        mtpr    $HIGH,$IPL
                    789:        movl    _scb+BERVEC,r2
                    790:        movl    4(fp),r3
                    791:        movl    8(fp),r4
                    792:        movab   9f,_scb+BERVEC
                    793:        bbc     $0,r4,1f; tstb  (r3)
                    794: 1:     bbc     $1,r4,1f; tstw  (r3)
                    795: 1:     bbc     $2,r4,1f; tstl  (r3)
                    796: 1:     clrl    r0                      # made it w/o machine checks
                    797: 2:     movl    r2,_scb+BERVEC
                    798:        mtpr    r1,$IPL
                    799:        ret
                    800: 
                    801:        .align  2
                    802: 9:                     # Here we catch buss error (if it comes)
                    803:        andl3   4(sp),$ERRCD,r0
                    804:        cmpl    r0,$APE
                    805:        jneq    1f
                    806:        halt                    # Address parity error !!!
                    807: 1:     cmpl    r0,$VBE
                    808:        jneq    1f
                    809:        halt                    # Versabus error
                    810: 1:
                    811:        movl    $1,r0           # Anything else = bad address
                    812:        movab   8(sp),sp        # discard buss error trash
                    813:        movab   2b,(sp)         # new program counter on stack.
                    814:        rei
                    815: 
                    816: 
                    817: /*
                    818:  * badcyaddr(addr)
                    819:  *     see if access tape master controller addr causes a bus error
                    820:  *     r0 = 0: no error; r0 = 1: timeout error.
                    821:  */
                    822:        .globl  _badcyaddr
                    823: _badcyaddr:
                    824:        .word   0x0c    # Keep r3,r2
                    825:        mfpr    $IPL,r1
                    826:        mtpr    $HIGH,$IPL
                    827:        movl    _scb+BERVEC,r2
                    828:        clrl    r3
                    829:        movab   9f,_scb+BERVEC
                    830:        movob   $-1, *4(fp)
                    831: 1:     aobleq  $1000, r3, 1b
                    832:        clrl    r0                      # made it w/o machine checks
                    833: 2:     movl    r2,_scb+BERVEC
                    834:        mtpr    r1,$IPL
                    835:        ret
                    836: 
                    837:        .align  2
                    838: 9:                     # Here we catch buss error (if it comes)
                    839:        andl3   4(sp),$ERRCD,r0
                    840:        cmpl    r0,$APE
                    841:        jneq    1f
                    842:        halt                    # Address parity error !!!
                    843: 1:     cmpl    r0,$VBE
                    844:        jneq    1f
                    845:        halt                    # Versabus error
                    846: 1:
                    847:        movl    $1,r0           # Anything else = timeout
                    848:        movab   8(sp),sp        # discard buss error trash
                    849:        movab   2b,(sp)         # new program counter on stack.
                    850:        rei
                    851: 
                    852: _bcopy:        .globl  _bcopy
                    853:        .word   0x4             # save r2
                    854:                                # Called by ovbcopy(from,dst,len)
                    855:        movl    4(fp),r0
                    856:        movl    8(fp),r1
                    857:        movl    12(fp),r2
                    858:        movblk
                    859:        ret
                    860: 
                    861: _ovbcopy:      .globl  _ovbcopy
                    862:        .word   0x001c
                    863:        movl    4(fp),r0
                    864:        movl    8(fp),r1
                    865:        movl    12(fp),r2
                    866:        cmpl    r0,r1
                    867:        bgtru   1f              # normal forward case
                    868:        beql    2f              # equal, nothing to do
                    869:        addl2   r2,r0           # may be overlapping
                    870:        cmpl    r0,r1
                    871:        bgtru   3f
                    872:        subl2   r2,r0           # normal forward case
                    873: 1:
                    874:        movblk
                    875: 2:
                    876:        ret
                    877: 3:
                    878:        addl2   r2,r1           # overlapping, must do backwards
                    879:        subl3   r0,r1,r3
                    880:        movl    r2,r4
                    881:        jbr     5f
                    882: 4:
                    883:        subl2   r3,r0
                    884:        subl2   r3,r1
                    885:        movl    r3,r2
                    886:        movblk
                    887:        subl2   r3,r0
                    888:        subl2   r3,r1
                    889:        subl2   r3,r4
                    890: 5:
                    891:        cmpl    r4,r3
                    892:        jgtr    4b
                    893:        movl    r4,r2
                    894:        subl2   r2,r0
                    895:        subl2   r2,r1
                    896:        movblk
                    897:        ret
                    898: 
                    899: /*
                    900:  * bzero (base, count)
                    901:  * zero out a block starting at 'base', size 'count'.
                    902:  */
                    903: _bzero:        
                    904:        .globl  _bzero
                    905:        .word   0x4
                    906:        movl    $1f,r0                          # r0 = null source string
                    907:        movl    4(fp),r1                        # r1 = destination address
                    908:        movl    8(fp),r2                        # r2 = count
                    909:        movs3
                    910:        ret
                    911: 1:
                    912:        .byte 0
                    913: 
                    914: 
                    915: _copyin:       .globl  _copyin         # the _Copyin subroutine in VAX
                    916:                                        # became _copyin procedure for TAHOE
                    917:        .word   0x0004
                    918:        movl    12(fp),r0               # copy length
                    919:        blss    ersb
                    920:        movl    4(fp),r1                # copy user address
                    921:        cmpl    $NBPG,r0                # probing one page or less ?
                    922:        bgeq    cishort                 # yes
                    923: ciloop:
                    924:        prober  $1,(r1),$NBPG           # bytes accessible ?
                    925:        beql    ersb                    # no
                    926:        addl2   $NBPG,r1                # incr user address ptr
                    927:        _ACBL   ($NBPG+1,$-NBPG,r0,ciloop)      # reduce count and loop
                    928: cishort:
                    929:        prober  $1,(r1),r0              # bytes accessible ?
                    930:        beql    ersb                    # no
                    931:        MOVC3   (12(fp),4(fp),8(fp))
                    932:        clrl    r0
                    933:        ret
                    934: 
                    935: ersb:
                    936:        movl    $EFAULT,r0
                    937:        ret
                    938: 
                    939: _copyout:      .globl  _copyout        # the _Copyout subroutine in VAX
                    940:                                        # became _copyout procedure for TAHOE
                    941:        .word   0x04
                    942:        movl    12(fp),r0               # get count
                    943:        blss    ersb
                    944:        movl    8(fp),r1                # get user address
                    945:        cmpl    $NBPG,r0                # can do in one probew?
                    946:        bgeq    coshort                 # yes
                    947: coloop:
                    948:        probew  $1,(r1),$NBPG           # bytes accessible?
                    949:        beql    ersb                    # no 
                    950:        addl2   $NBPG,r1                # increment user address
                    951:        _ACBL   ($NBPG+1,$-NBPG,r0,coloop)      # reduce count and loop
                    952: coshort:
                    953:        probew  $1,(r1),r0              # bytes accessible?
                    954:        beql    ersb                    # no
                    955:        MOVC3   (12(fp),4(fp),8(fp))
                    956:        clrl    r0
                    957:        ret
                    958: 
                    959: /*
                    960:  * non-local goto's
                    961:  */
                    962:        .globl  _setjmp                 # the _Setjmp subroutine in VAX
                    963:                                        # became _setjmp procedure for TAHOE
                    964: _setjmp:
                    965:        .word   0x0
                    966:        movl    4(fp),r2
                    967:        storer  $0x1ff8,(r2)
                    968:        addl2   $40,r2
                    969:        movl    (fp),(r2)
                    970:        addl2   $4,r2
                    971:        movab   8(fp),(r2)
                    972:        addl2   $4,r2
                    973:        movl    -8(fp),(r2)
                    974:        clrl    r0
                    975:        ret
                    976: 
                    977:        .globl  _longjmp                # the _Longjmp subroutine in VAX
                    978:                                        # became _longjmp procedure for TAHOE
                    979: _longjmp:
                    980:        .word   0x0000
                    981:        movl    4(fp),r2
                    982: _Longjmp:                      # called from swtch
                    983:        loadr   $0x3ff8,(r2)
                    984:        addl2   $44,r2
                    985:        movl    (r2),r1
                    986:        addl2   $4,r2
                    987:        movab   (sp),r0
                    988:        cmpl    r1,r0                           # must be a pop
                    989:        bgequ   lj2
                    990:        pushab  lj1
                    991:        callf   $8,_panic
                    992: lj2:
                    993:        movl    r1,sp
                    994:        jmp     *(r2)
                    995: 
                    996: lj1:   .asciz  "longjmp"
                    997: 
                    998: 
                    999:        .globl  _whichqs
                   1000:        .globl  _qs
                   1001:        .globl  _cnt
                   1002: 
                   1003:        .globl  _noproc
                   1004:        .comm   _noproc,4
                   1005:        .globl  _runrun
                   1006:        .comm   _runrun,4
                   1007: 
                   1008: /*
                   1009:  * The following primitives use the fancy TAHOE instructions.
                   1010:  * _whichqs tells which of the 32 queues _qs
                   1011:  * have processes in them.  setrq puts processes into queues, remrq
                   1012:  * removes them from queues.  The running process is on no queue,
                   1013:  * other processes are on a queue related to p->p_pri, divided by 4
                   1014:  * actually to shrink the 0-127 range of priorities into the 32 available
                   1015:  * queues.
                   1016:  */
                   1017: 
                   1018: /*
                   1019:  * setrq(p), using fancy TAHOE instructions.
                   1020:  *
                   1021:  * Call should be made at spl8(), and p->p_stat should be SRUN
                   1022:  */
                   1023:        .globl  _setrq
                   1024: _setrq:
                   1025:        .word   0x4
                   1026:        movl    4(fp),r0
                   1027:        tstl    P_RLINK(r0)             ## firewall: p->p_rlink must be 0
                   1028:        beql    set1                    ##
                   1029:        pushab  set3                    ##
                   1030:        callf   $8,_panic               ##
                   1031: set1:
                   1032:        movzbl  P_PRI(r0),r1            # put on queue which is p->p_pri / 4
                   1033:        shar    $2,r1,r1
                   1034:        shal    $1,r1,r2
                   1035:        moval   _qs[r2],r2
                   1036:        insque  (r0),*4(r2)             # at end of queue
                   1037:        shal    r1,$1,r1
                   1038:        orl2    r1,_whichqs             # mark queue non-empty
                   1039:        ret
                   1040: 
                   1041: set3:  .asciz  "setrq"
                   1042: 
                   1043: /*
                   1044:  * remrq(p), using fancy TAHOE instructions
                   1045:  *
                   1046:  * Call should be made at spl8().
                   1047:  */
                   1048:        .globl  _remrq
                   1049: _remrq:
                   1050:        .word   0x0
                   1051:        movl    4(fp),r0
                   1052:        movzbl  P_PRI(r0),r1
                   1053:        shar    $2,r1,r1
                   1054:        bbs     r1,_whichqs,rem1
                   1055:        pushab  rem3                    # it wasn't recorded to be on its q
                   1056:        callf   $8,_panic
                   1057: rem1:
                   1058:        remque  (r0)
                   1059:        bneq    rem2                    # q not empty yet
                   1060:        shal    r1,$1,r1
                   1061:        mcoml   r1,r1
                   1062:        andl2   r1,_whichqs             # mark queue empty
                   1063: rem2:
                   1064:        clrl    P_RLINK(r0)             ## for firewall checking
                   1065:        ret
                   1066: 
                   1067: rem3:  .asciz  "remrq"
                   1068: 
                   1069:        .globl __insque
                   1070: __insque:
                   1071:        .word 0
                   1072:        insque  *4(fp), *8(fp)
                   1073:        ret
                   1074: 
                   1075: 
                   1076:        .globl __remque
                   1077: __remque:
                   1078:        .word 0
                   1079:        remque  *4(fp)
                   1080:        ret
                   1081: 
                   1082: /*
                   1083:  * Masterpaddr is the p->p_addr of the running process on the master
                   1084:  * processor.  When a multiprocessor system, the slave processors will have
                   1085:  * an array of slavepaddr's.
                   1086:  */
                   1087:        .globl  _masterpaddr
                   1088:        .data
                   1089: _masterpaddr:
                   1090:        .long   0
                   1091: 
                   1092:        .text
                   1093: sw0:   .asciz  "swtch"
                   1094: /*
                   1095:  * swtch(), using fancy TAHOE instructions
                   1096:  */
                   1097:        .globl  _swtch
                   1098: _swtch:
                   1099:        .word   0x0
                   1100:        movl    (fp),fp                 # prepare for rei
                   1101:        movl    (sp),4(sp)              # saved pc
                   1102:        tstl    (sp)+
                   1103:        movpsl  4(sp)
                   1104:        movl    $1,_noproc
                   1105:        clrl    _runrun
                   1106: mtpr0: mtpr    $0,$IPL                 # must allow interrupts here
                   1107: sw1:   ffs     _whichqs,r0             # look for non-empty queue
                   1108:        bgeq    sw1a
                   1109:        brb     sw1                     # this is an idle loop!
                   1110: sw1a:  mtpr    $0x18,$IPL              # lock out all so _whichqs==_qs
                   1111:        bbc     r0,_whichqs,mtpr0       # proc moved via lbolt interrupt
                   1112:        shal    $1,r0,r1
                   1113:        moval   _qs[r1],r1
                   1114:        movl    (r1),r2                 # r2 = p = highest pri process
                   1115:        remque  *(r1)
                   1116:        bvc     sw2                     # make sure something was there
                   1117: sw1b:  pushab  sw0
                   1118:        callf   $8,_panic
                   1119: sw2:   bneq    sw3
                   1120:        shal    r0,$1,r1
                   1121:        mcoml   r1,r1
                   1122:        andl2   r1,_whichqs             # no more procs in this queue
                   1123: sw3:
                   1124:        clrl    _noproc
                   1125:        tstl    P_WCHAN(r2)             ## firewalls
                   1126:        bneq    sw1b                    ##
                   1127:        movzbl  P_STAT(r2),r3           ##
                   1128:        cmpl    $SRUN,r3                ##
                   1129:        bneq    sw1b                    ##
                   1130:        clrl    P_RLINK(r2)             ##
                   1131:        movl    *P_ADDR(r2),r0
                   1132:        movl    r0,_masterpaddr
                   1133:        shal    $PGSHIFT,r0,r0          # r0 = pcbb(p)
                   1134: /*     mfpr    $PCBB,r1                # resume of current proc is easy
                   1135:  *     cmpl    r0,r1
                   1136:  */    beql    res0
                   1137:        incl    _cnt+V_SWTCH
                   1138:        brb     swresume
                   1139: /* fall into... */
                   1140: 
                   1141:        .data
                   1142:        .globl  _prevpcb
                   1143: _prevpcb:
                   1144:        .long   0
                   1145:        .text
                   1146: /*
                   1147:  * resume(pf)
                   1148:  */
                   1149:        .globl  _resume
                   1150: _resume:
                   1151:        .word   0x0
                   1152:        shal    $PGSHIFT,4(fp),r0       # r0 = pcbb(p)
                   1153:        movl    (fp),fp                 # prepare for rei
                   1154:        movl    (sp)+,4(sp)             # saved pc
                   1155:        tstl    (sp)+
                   1156:        movpsl  4(sp)
                   1157: swresume:
                   1158:        mtpr    $0x18,$IPL                      # no interrupts, please
                   1159:        movl    _CMAP2,_u+PCB_CMAP2     # yech
                   1160:        REST_ACC                        # restore original accumulator
                   1161:        svpctx
                   1162:        mtpr    r0,$PCBB
                   1163:        ldpctx
                   1164:        movl    _u+PCB_CMAP2,_CMAP2     # yech
                   1165:        mtpr    $_CADDR2,$TBIS
                   1166: res0:
                   1167:        tstl    _u+PCB_SSWAP
                   1168:        beql    res1
                   1169:        movl    _u+PCB_SSWAP,r2
                   1170:        clrl    _u+PCB_SSWAP
                   1171:        movab   _Longjmp,(sp)
                   1172:        clrl    4(sp)                   # PSL = kernel mode, IPL=0
                   1173: res1:
                   1174: /*
                   1175:  * Now we have to care about code and data keys.
                   1176:  * 2 functions may be called, so r0 and r1 must be
                   1177:  * saved across the 'callf'. Also, r2 is used as index
                   1178:  * since r1 may be changed by the functions (just a
                   1179:  * precaution).
                   1180:  */
                   1181:        PUSHR                           # ro and r1
                   1182:        pushl   r2
                   1183:        movl    _u+U_PROCP,r2           # r2 = & proc[?]
                   1184:        tstl    P_CKEY(r2)              # does he have a code key ?
                   1185:        bneq    ckey_ok
                   1186:        callf   $4,_getcodekey          # no, we have to give him one.
                   1187:        movl    r0,P_CKEY(r2)
                   1188: ckey_ok:
                   1189:        tstl    P_DKEY(r2)              # same stuff for data key
                   1190:        bneq    dkey_ok
                   1191:        callf   $4,_getdatakey
                   1192:        movl    r0,P_DKEY(r2)
                   1193: dkey_ok:
                   1194:        mtpr    P_CKEY(r2),$CCK
                   1195:        mtpr    P_DKEY(r2),$DCK
                   1196:        movl    (sp)+,r2                # restore his registers
                   1197:        POPR
                   1198:        rei
                   1199: 
                   1200: /*
                   1201:  * {fu,su},{byte,word}
                   1202:  */
                   1203:        .globl  _fuiword
                   1204:        .globl  _fuword
                   1205: _fuiword:
                   1206: _fuword:
                   1207:        .word   0x0
                   1208:        bitl    $3,4(fp)                # Check against alignment problems
                   1209:        bneq    fserr                   #
                   1210:        prober  $1,*4(fp),$4
                   1211:        beql    fserr
                   1212:        movl    *4(fp),r0
                   1213:        ret
                   1214: fserr:
                   1215:        mnegl   $1,r0
                   1216:        ret
                   1217: 
                   1218:        .globl  _fuibyte
                   1219:        .globl  _fubyte
                   1220: _fuibyte:
                   1221: _fubyte:
                   1222:        .word   0x0
                   1223:        prober  $1,*4(fp),$1
                   1224:        beql    fserr
                   1225:        movzbl  *4(fp),r0
                   1226:        ret
                   1227: 
                   1228:        .globl  _suiword
                   1229:        .globl  _suword
                   1230: _suiword:
                   1231: _suword:
                   1232:        .word   0x0
                   1233:        bitl    $3,4(fp)                # Check against alignment problems
                   1234:        bneq    fserr                   #
                   1235:        probew  $1,*4(fp),$4
                   1236:        beql    fserr
                   1237:        movl    8(fp),*4(fp)
                   1238:        clrl    r0
                   1239:        ret
                   1240: 
                   1241:        .globl  _suibyte
                   1242:        .globl  _subyte
                   1243: _suibyte:
                   1244: _subyte:
                   1245:        .word   0x0
                   1246:        probew  $1,*4(fp),$1
                   1247:        beql    fserr
                   1248:        movb    11(fp),*4(fp)
                   1249:        clrl    r0
                   1250:        ret
                   1251: 
                   1252: /*
                   1253:  * Copy 1 relocation unit (NBPG bytes)
                   1254:  * from user virtual address to physical address
                   1255:  */
                   1256: _copyseg:      .globl  _copyseg
                   1257:        .word   0x4
                   1258:        orl3    $PG_V|PG_KW,8(fp),_CMAP2
                   1259:        mtpr    $_CADDR2,$TBIS  # invalidate entry for copy 
                   1260:        MOVC3   ($NBPG,4(fp),$_CADDR2)
                   1261:        ret
                   1262: 
                   1263: /*
                   1264:  * clearseg(physical_page_number);
                   1265:  *
                   1266:  * zero out physical memory
                   1267:  * specified in relocation units (NBPG bytes)
                   1268:  * This routine was optimized for speed on Tahoe.
                   1269:  */
                   1270: _clearseg:     .globl  _clearseg
                   1271:        .word   0
                   1272:        orl3    $PG_V|PG_KW,4(fp),_CMAP1        # Maps to virtual addr CADDR1
                   1273:        mtpr    $_CADDR1,$TBIS
                   1274:        movl    $255,r0                         # r0 = limit
                   1275:        clrl    r1                              # r1 = index of cleared long
                   1276: 1:
                   1277:        clrl    _CADDR1[r1]
                   1278:        aobleq  r0,r1,1b
                   1279:        ret
                   1280: 
                   1281: /*
                   1282:  * if ( useracc(address, count, mode) ) ....
                   1283:  * Check address.
                   1284:  * Given virtual address, byte count, and rw flag
                   1285:  * returns 0 on no access.
                   1286:  * Note : it is assumed that on all calls to this routine,
                   1287:  *  mode=0 means write access, mode=1 means read access.
                   1288:  */
                   1289: _useracc:      .globl  _useracc
                   1290:        .word   0x4
                   1291:        movl    $1,r2                   # r2 = 'user mode' for probew/probew
                   1292: probes:
                   1293:        movl    4(fp),r0                # get va
                   1294:        movl    8(fp),r1                # count
                   1295:        tstl    12(fp)                  # test for read access ?
                   1296:        bneq    userar                  # yes
                   1297:        cmpl    $NBPG,r1                        # can we do it in one probe ?
                   1298:        bgeq    uaw2                    # yes
                   1299: uaw1:
                   1300:        probew  r2,(r0),$NBPG
                   1301:        beql    uaerr                   # no access
                   1302:        addl2   $NBPG,r0
                   1303:        _ACBL($NBPG+1,$-NBPG,r1,uaw1)
                   1304: uaw2:
                   1305:        probew  r2,(r0),r1
                   1306:        beql    uaerr
                   1307:        movl    $1,r0
                   1308:        ret
                   1309: 
                   1310: userar:
                   1311:        cmpl    $NBPG,r1
                   1312:        bgeq    uar2
                   1313: uar1:
                   1314:        prober  r2,(r0),$NBPG
                   1315:        beql    uaerr
                   1316:        addl2   $NBPG,r0
                   1317:        _ACBL($NBPG+1,$-NBPG,r1,uar1)
                   1318: uar2:
                   1319:        prober  r2,(r0),r1
                   1320:        beql    uaerr
                   1321:        movl    $1,r0
                   1322:        ret
                   1323: uaerr:
                   1324:        clrl    r0
                   1325:        ret
                   1326: 
                   1327: /*
                   1328:  * if ( kernacc(address, count, mode) ) ....
                   1329:  * Check address.
                   1330:  * Given virtual address, byte count, and rw flag
                   1331:  * returns 0 on no access.
                   1332:  * Same as useracc routine but checks for kernel access rights.
                   1333:  */
                   1334: 
                   1335: _kernacc:      .globl  _kernacc
                   1336:        .word   0x4
                   1337:        clrl    r2              # r2 = 0 means kernel mode probe.
                   1338:        jbr     probes          # Dijkstra would get gastric distress here.
                   1339: 
                   1340: /*
                   1341:  * addupc - increment some histogram counter
                   1342:  *     in the profiling buffer
                   1343:  *
                   1344:  * addupc(pc, prof, counts)
                   1345:  * long        pc , counts;    Only least significant word of 'counts' is added.
                   1346:  * struct      uprof *prof;
                   1347:  * 
                   1348:  * struct uprof {              # profile arguments 
                   1349:  *     short   *r_base;        # buffer base 
                   1350:  *     unsigned pr_size;       # buffer size 
                   1351:  *     unsigned pr_off;        # pc offset 
                   1352:  *     unsigned pr_scale;      # pc scaling 
                   1353:  * }
                   1354:  */
                   1355:        .globl  _addupc
                   1356: _addupc:
                   1357:        .word   4
                   1358:        movl    8(fp),r2        # r2 points to structure
                   1359:        subl3   8(r2),4(fp),r0  # r0 = PC - lowpc
                   1360:        jlss    9f              # PC < lowpc , out of range !
                   1361:        shrl    $1,r0,r0        # the unit is words
                   1362:        shrl    $1,12(r2),r1    # ditto for scale
                   1363:        emul    r1,r0,$0,r0
                   1364:        shrq    $14,r0,r0
                   1365:        tstl    r0              # too big
                   1366:        jneq    9f
                   1367:        cmpl    r1,4(r2)        # Check buffer overflow
                   1368:        jgequ   9f
                   1369:        probew  $1,*0(r2)[r1],$2        # counter accessible?
                   1370:        jeql    9f
                   1371:        shrl    $1,r1,r1        # make r1 word index
                   1372:        addw2   14(fp),*0(r2)[r1]
                   1373: 9:     ret
                   1374: SCBVEC(udintr0):
                   1375: SCBVEC(xpintr0):
                   1376:        jbr     _Xstray

unix.superglobalmegacorp.com

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