# 2.11BSD#431 - /usr/src/sys/pdpstand/tmscp.c

##### Functions

    tmscpclose        X
    tmscpcmd          X
    tmscpopen         X
    tmscpseek         X
    tmscpstrategy     X

##### Variables

    TMScsr            X
    tms_offline       X
    tmscp             X
    tmsoffline        X

##### Macros

    NCMDL2            X
    NRSPL2            X
    NTMS              X
    STEP1GOOD         X
    STEP1MASK         X
    STEP2GOOD         X
    STEP2MASK         X
    STEP3GOOD         X
    STEP3MASK         X

       1: /*	@(#)tmscp.c	7.1.5 (2.11BSD GTE) 1998/1/30 */
       2:
       3: /****************************************************************
       4:  *        Licensed from Digital Equipment Corporation           *
       5:  *                       Copyright (c)                          *
       6:  *               Digital Equipment Corporation                  *
       7:  *                   Maynard, Massachusetts                     *
       8:  *                         1985, 1986                           *
       9:  *                    All rights reserved.                      *
      10:  *                                                              *
      11:  *        The Information in this software is subject to change *
      12:  *   without notice and should not be construed as a commitment *
      13:  *   by  Digital  Equipment  Corporation.   Digital   makes  no *
      14:  *   representations about the suitability of this software for *
      15:  *   any purpose.  It is supplied "As Is" without expressed  or *
      16:  *   implied  warranty.                                         *
      17:  *                                                              *
      18:  *        If the Regents of the University of California or its *
      19:  *   licensees modify the software in a manner creating         *
      20:  *   deriviative copyright rights, appropriate copyright        *
      21:  *   legends may be placed on  the drivative work in addition   *
      22:  *   to that set forth above.                                   *
      23:  ***************************************************************/
      24: /*
      25:  * tmscp.c - TMSCP (TK50/TU81) standalone driver
      26:  */
      27:
      28: /* static char *sccsid = "@(#)tmscp.c	1.5	(ULTRIX) 4/18/86"; */
      29:
      30: /* ------------------------------------------------------------------------
      31:  * Modification History: /sys/pdpstand/tmscp.c
      32:  *
      33:  * 5-30-95 sms - new iob structure.
      34:  * 4-20-91 sms - add multi controller and unit support (sms)
      35:  * 8-20-90 steven m. schultz (sms@wlv.iipo.gtegsc.com)
      36:  *	Port from 4.3BSD to 2.11BSD
      37:  * 3-15-85  afd
      38:  *	Don't ask for an interrupt when commands are issued and
      39:  *	check ownership bit in the response descriptor to detect when a
      40:  *	command is complete.  Necessary due to the TU81's failure to set
      41:  *	the response interrupt field in the communications area.
      42:  *
      43:  * ------------------------------------------------------------------------
      44:  */
      45:
      46: #include "../h/param.h"
      47: #include "saio.h"
      48:
      49: /*
      50:  * Parameters for the communications area
      51:  * (Only 1 cmd & 1 rsp packet)
      52:  */
      53: #define NRSPL2  0           /* Define these before including */
      54: #define NCMDL2  0           /*   tmscpreg.h and tmscp.h below */
      55:
      56: #include "sys/buf.h"
      57: #include "../pdpuba/tmscpreg.h"
      58: #include "../pdp/tmscp.h"
      59:
      60: #define NTMS    2
      61:
      62:     struct  tmscpdevice *TMScsr[NTMS + 1] =
      63:         {
      64:         (struct tmscpdevice *)0174500,
      65:         (struct tmscpdevice *)0,
      66:         (struct tmscpdevice *)-1
      67:         };
      68:
      69: struct tmscp tmscp[NTMS];
      70:
      71: u_char tmsoffline[NTMS] = {1, 1};   /* Flag to prevent multiple STCON */
      72: u_char tms_offline[NTMS][4] = {{1,1,1,1},
      73:                    {1,1,1,1}}; /* Flag to prevent multiple ONLIN */
      74: static char opnmsg[] = "tms%d: step %d failed sa=0%o\n";
      75:
      76: extern int tapemark;        /* flag to indicate tapemark encountered
      77: 				   (see sys.c as to how it's used) */
      78:
      79: /*
      80:  * Open a tmscp device. Initialize the controller and set the unit online.
      81:  */
      82: tmscpopen(io)
      83:     register struct iob *io;
      84: {
      85:     register struct tmscpdevice *tmscpaddr;
      86:     int ctlr = io->i_ctlr;
      87:     int unit = io->i_unit, bae, lo16;
      88:     register struct tmscp *tms = &tmscp[ctlr];
      89:
      90:     if (genopen(NTMS, io) < 0)
      91:         return(-1);
      92:     io->i_flgs |= F_TAPE;
      93:     tmscpaddr = TMScsr[ctlr];
      94:
      95:     /*
      96: 	 * Have the tmscp controller characteristics already been set up
      97: 	 * (STCON)?
      98: 	 */
      99:     if (tmsoffline[ctlr])
     100:         {
     101:         /*
     102: 		 * Initialize the tmscp device and wait for the 4 steps
     103: 		 * to complete.
     104: 		 */
     105:         tmscpaddr->tmscpip = 0;
     106:         while ((tmscpaddr->tmscpsa & TMSCP_STEP1) == 0)
     107:             ;
     108:         tmscpaddr->tmscpsa =TMSCP_ERR|(NCMDL2<<11)|(NRSPL2<<8);
     109:
     110:         while ((tmscpaddr->tmscpsa & TMSCP_STEP2) == 0)
     111:             ;
     112: #define STEP1MASK 0174377
     113: #define STEP1GOOD (TMSCP_STEP2|TMSCP_IE|(NCMDL2<<3)|NRSPL2)
     114:         iomapadr(&tms->tmscp_ca.ca_ringbase, &bae, &lo16);
     115:         if ((tmscpaddr->tmscpsa&STEP1MASK) != STEP1GOOD)
     116:             printf(opnmsg, ctlr, 1, tmscpaddr->tmscpsa);
     117:         tmscpaddr->tmscpsa = lo16;
     118:
     119:         while ((tmscpaddr->tmscpsa & TMSCP_STEP3) == 0)
     120:             ;
     121: #define STEP2MASK 0174377
     122: #define STEP2GOOD (TMSCP_STEP3)
     123:         if ((tmscpaddr->tmscpsa&STEP2MASK) != STEP2GOOD)
     124:             printf(opnmsg, ctlr, 2, tmscpaddr->tmscpsa);
     125:         tmscpaddr->tmscpsa = bae;
     126:
     127:         while ((tmscpaddr->tmscpsa & TMSCP_STEP4) == 0)
     128:             ;
     129: #define STEP3MASK 0174000
     130: #define STEP3GOOD TMSCP_STEP4
     131:         if ((tmscpaddr->tmscpsa&STEP3MASK) != STEP3GOOD)
     132:             printf(opnmsg, ctlr, 3, tmscpaddr->tmscpsa);
     133:         tmscpaddr->tmscpsa = TMSCP_GO;
     134:         if (tmscpcmd(io, M_OP_STCON, 0) == 0)
     135:             {
     136:             printf("%s STCON", devname(io));
     137:             return(-1);
     138:             }
     139:         tmsoffline[ctlr] = 0;
     140:         }
     141:     tms->tmscp_cmd[0].mscp_unit = unit;
     142:     /*
     143: 	 * Has this unit been issued an ONLIN?
     144: 	 */
     145:     if (tms_offline[ctlr][unit])
     146:         {
     147:         if (tmscpcmd(io, M_OP_ONLIN, 0) == 0)
     148:             {
     149:             printf("%s ONLIN", devname(io));
     150:             return(-1);
     151:             }
     152:         tms_offline[ctlr][unit] = 0;
     153:         }
     154:     tmscpclose(io);     /* close just does a rewind */
     155:     if  (io->i_part > 0)
     156:         /*
     157: 		 * Skip forward the appropriate number of files on the tape.
     158: 		 */
     159:         {
     160:         tms->tmscp_cmd[0].mscp_tmkcnt = io->i_part;
     161:         tms->tmscp_cmd[0].mscp_buffer_h = 0;
     162:         tms->tmscp_cmd[0].mscp_bytecnt = 0;
     163:         tmscpcmd(io, M_OP_REPOS, 0);
     164:         tms->tmscp_cmd[0].mscp_tmkcnt = 0;
     165:         }
     166:     return(0);
     167: }
     168:
     169: /*
     170:  * Close the device (rewind it to BOT)
     171:  */
     172: tmscpclose(io)
     173:     register struct iob *io;
     174: {
     175:     register struct tmscp *tms = &tmscp[io->i_ctlr];
     176:
     177:     tms->tmscp_cmd[0].mscp_buffer_l = 0;    /* tmkcnt */
     178:     tms->tmscp_cmd[0].mscp_buffer_h = 0;
     179:     tms->tmscp_cmd[0].mscp_bytecnt = 0;
     180:     tms->tmscp_cmd[0].mscp_unit = io->i_unit;
     181:     tmscpcmd(io, M_OP_REPOS, M_MD_REWND | M_MD_CLSEX);
     182: }
     183:
     184: /*
     185:  * Set up tmscp command packet.  Cause the controller to poll to pick up
     186:  * the command.
     187:  */
     188: tmscpcmd(io, op,mod)
     189:     struct  iob *io;
     190:     int op, mod;        /* opcode and modifier (usu 0) */
     191: {
     192:     int ctlr = io->i_ctlr;
     193:     register struct tmscp *tms = &tmscp[ctlr];
     194:     register struct mscp *mp;   /* ptr to cmd packet */
     195:     int i;              /* read into to init polling */
     196:     int bae, lo16;
     197:
     198:     /*
     199: 	 * Init cmd & rsp area
     200: 	 */
     201:     iomapadr(&tms->tmscp_cmd[0].mscp_cmdref, &bae, &lo16);
     202:     tms->tmscp_ca.ca_cmddsc[0].lsh = lo16;
     203:     tms->tmscp_ca.ca_cmddsc[0].hsh = bae;
     204:     tms->tmscp_cmd[0].mscp_dscptr = (long *)tms->tmscp_ca.ca_cmddsc;
     205:     tms->tmscp_cmd[0].mscp_header.mscp_vcid = 1;    /* for tape */
     206:
     207:     iomapadr(&tms->tmscp_rsp[0].mscp_cmdref, &bae, &lo16);
     208:     tms->tmscp_ca.ca_rspdsc[0].lsh = lo16;
     209:     tms->tmscp_ca.ca_rspdsc[0].hsh = bae;
     210:     tms->tmscp_rsp[0].mscp_dscptr = (long *)tms->tmscp_ca.ca_rspdsc;
     211:     tms->tmscp_cmd[0].mscp_cntflgs = 0;
     212:
     213:     tms->tmscp_cmd[0].mscp_opcode = op;
     214:     tms->tmscp_cmd[0].mscp_modifier = mod;
     215:     tms->tmscp_cmd[0].mscp_header.mscp_msglen = sizeof (struct tmscp);
     216:     tms->tmscp_ca.ca_cmddsc[0].hsh |= TMSCP_OWN;    /* | TMSCP_INT */
     217:     tms->tmscp_rsp[0].mscp_header.mscp_msglen = sizeof (struct tmscp);
     218:     tms->tmscp_ca.ca_rspdsc[0].hsh |= TMSCP_OWN;    /* | TMSCP_INT */
     219:     tms->tmscp_cmd[0].mscp_zzz2 = 0;
     220:
     221:     i = TMScsr[ctlr]->tmscpip;
     222:     for (;;)
     223:         {
     224:         if (TMScsr[ctlr]->tmscpsa & TMSCP_ERR) {
     225:             printf("%s Fatal err sa=%o\n",
     226:                 devname(io), TMScsr[ctlr]->tmscpsa);
     227:             return(0);
     228:         }
     229:
     230:         if (tms->tmscp_ca.ca_cmdint)
     231:             tms->tmscp_ca.ca_cmdint = 0;
     232:         /*
     233: 		 * This is to handle the case of devices not setting the
     234: 		 * interrupt field in the communications area. Some
     235: 		 * devices (early TU81's) only clear the ownership field
     236: 		 * in the Response Descriptor.
     237: 		 */
     238: /*
     239: 		if (tms->tmscp_ca.ca_rspint)
     240: 			break;
     241: */
     242:         if (!(tms->tmscp_ca.ca_rspdsc[0].hsh & TMSCP_OWN))
     243:             break;
     244:         }
     245:     tms->tmscp_ca.ca_rspint = 0;
     246:     mp = &tms->tmscp_rsp[0];
     247:     if (mp->mscp_opcode != (op|M_OP_END) ||
     248:        (mp->mscp_status&M_ST_MASK) != M_ST_SUCC) {
     249:         /* Detect hitting tape mark.  This signifies the end of the
     250: 		 * tape mini-root file.  We don't want to return an error
     251: 		 * condition to the strategy routine.  Set tapemark flag
     252: 		 * for sys.c
     253: 		 */
     254:         if ((mp->mscp_status & M_ST_MASK) == M_ST_TAPEM) {
     255:             tapemark = 1;
     256:             return(1);
     257:         }
     258:         printf("%s I/O err 0%o op=0%o mod=0%o\n", devname(io),
     259:             mp->mscp_status, op, mod);
     260:         return(0);
     261:     }
     262:     return(1);
     263: }
     264:
     265: /*
     266:  * Set up to do reads and writes; call tmscpcmd to issue the cmd.
     267:  */
     268: tmscpstrategy(io, func)
     269:     register struct iob *io;
     270:     int func;
     271: {
     272:     int ctlr = io->i_ctlr, unit = io->i_unit;
     273:     int bae, lo16;
     274:     register struct tmscp *tms = &tmscp[ctlr];
     275:     register struct mscp *mp;
     276:
     277:     mp = &tms->tmscp_cmd[0];
     278:     mp->mscp_lbn_l = loint(io->i_bn);
     279:     mp->mscp_lbn_h = hiint(io->i_bn);
     280:     mp->mscp_unit = unit;
     281:     mp->mscp_bytecnt = io->i_cc;
     282:     iomapadr(io->i_ma, &bae, &lo16);
     283:     mp->mscp_buffer_l = lo16;
     284:     mp->mscp_buffer_h = bae;
     285:     if  (tmscpcmd(io, func == READ ? M_OP_READ : M_OP_WRITE, 0) ==0)
     286:         return(-1);
     287:     /*
     288: 	 * Detect hitting tape mark so we do it gracefully and return a
     289: 	 * character count of 0 to signify end of copy.
     290: 	 */
     291:     if (tapemark)
     292:         return(0);
     293:     return(io->i_cc);
     294: }
     295:
     296: tmscpseek(io, space)
     297:     register struct iob *io;
     298:     int space;
     299:     {
     300:     register struct tmscp *tms = &tmscp[io->i_ctlr];
     301:     int mod;
     302:
     303:     if  (space == 0)
     304:         return(0);
     305:     if  (space < 0)
     306:         {
     307:         mod = M_MD_REVRS;
     308:         space = -space;
     309:         }
     310:     else
     311:         mod = 0;
     312:     tms->tmscp_cmd[0].mscp_buffer_l = 0;
     313:     tms->tmscp_cmd[0].mscp_buffer_h = 0;
     314:     tms->tmscp_cmd[0].mscp_unit = io->i_unit;
     315:     tms->tmscp_cmd[0].mscp_reccnt = space;
     316:     tmscpcmd(io, M_OP_REPOS, mod | M_MD_OBJCT);
     317:     return(0);
     318:     }

#### Defined functions

tmscpclose defined in line 172; used 3 times

- in line 154
- in /usr/src/sys/pdpstand/conf.c line 25, 60

tmscpcmd defined in line 188; used 6 times

- in line 134, 147, 163, 181, 285, 316

tmscpopen defined in line 82; used 2 times

- in /usr/src/sys/pdpstand/conf.c line 25, 60

tmscpseek defined in line 296; used 2 times

- in /usr/src/sys/pdpstand/conf.c line 25, 61

tmscpstrategy defined in line 268; used 2 times

- in /usr/src/sys/pdpstand/conf.c line 25, 60

#### Defined variables

TMScsr defined in line 62; used 5 times

- in line 93, 221-226(3)
- in /usr/src/sys/pdpstand/conf.c line 60

opnmsg defined in line 74; used 3 times

- in line 116, 124, 132

tms_offline defined in line 72; used 2 times

- in line 145, 152

tmscp defined in line 69; used 5 times

- in line 88, 175, 193, 274, 300

tmsoffline defined in line 71; used 2 times

- in line 99, 139

#### Defined macros

NCMDL2 defined in line 54; used 2 times

- in line 108-113(2)

NRSPL2 defined in line 53; used 2 times

- in line 108-113(2)

NTMS defined in line 60; used 5 times

- in line 62, 69-72(3), 90

STEP1GOOD defined in line 113; used 1 times

- in line 115

STEP1MASK defined in line 112; used 1 times

- in line 115

STEP2GOOD defined in line 122; used 1 times

- in line 123

STEP2MASK defined in line 121; used 1 times

- in line 123

STEP3GOOD defined in line 130; used 1 times

- in line 131

STEP3MASK defined in line 129; used 1 times

- in line 131

Last modified: 1998-01-31 Generated: 2016-12-26 | Generated by src2html V0.67 page hit count: 1750 |