Annotation of 43BSDReno/sys/hpstand/ct.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 1982, 1990 The Regents of the University of California.
                      3:  * All rights reserved.
                      4:  *
                      5:  * Redistribution is only permitted until one year after the first shipment
                      6:  * of 4.4BSD by the Regents.  Otherwise, redistribution and use in source and
                      7:  * binary forms are permitted provided that: (1) source distributions retain
                      8:  * this entire copyright notice and comment, and (2) distributions including
                      9:  * binaries display the following acknowledgement:  This product includes
                     10:  * software developed by the University of California, Berkeley and its
                     11:  * contributors'' in the documentation or other materials provided with the
                     12:  * distribution and in all advertising materials mentioning features or use
                     13:  * of this software.  Neither the name of the University nor the names of
                     14:  * its contributors may be used to endorse or promote products derived from
                     15:  * this software without specific prior written permission.
                     16:  * THIS SOFTWARE IS PROVIDED AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
                     17:  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
                     18:  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
                     19:  *
                     20:  *     @(#)ct.c        7.1 (Berkeley) 5/8/90
                     21:  */
                     22: 
                     23: /*
                     24:  * CS80 tape driver
                     25:  */
                     26: #include "../sys/types.h"
                     27: #include "../hpdev/ctreg.h"
                     28: 
                     29: #include "saio.h"
                     30: #include "samachdep.h"
                     31: 
                     32: struct ct_iocmd ct_ioc;
                     33: struct ct_rscmd ct_rsc;
                     34: struct ct_stat ct_stat;
                     35: struct ct_ssmcmd ct_ssmc;
                     36: 
                     37: struct ct_softc {
                     38:        char    sc_retry;
                     39:        char    sc_alive;
                     40:        short   sc_punit;
                     41:        int     sc_blkno;
                     42: } ct_softc[NCT];
                     43: 
                     44: #define        CTRETRY         5
                     45: #define        MTFSF           10
                     46: #define        MTREW           11
                     47: 
                     48: struct ctinfo {
                     49:        short   hwid;
                     50:        short   punit;
                     51: } ctinfo[] = {
                     52:        CT7946ID,       1,
                     53:        CT7912PID,      1,
                     54:        CT7914PID,      1,
                     55:        CT9144ID,       0,
                     56:        CT9145ID,       0,
                     57: };
                     58: int    nctinfo = sizeof(ctinfo) / sizeof(ctinfo[0]);
                     59: 
                     60: ctinit(unit)
                     61:        register int unit;
                     62: {
                     63:        register struct ct_softc *rs = &ct_softc[unit];
                     64:        u_char stat;
                     65:        register int type;
                     66: 
                     67:        if (hpibrecv(unit, C_QSTAT, &stat, 1) != 1 || stat)
                     68:                return (0);
                     69:        if (ctident(unit) < 0)
                     70:                return (0);
                     71:        ct_ssmc.unit = C_SUNIT(rs->sc_punit);
                     72:        ct_ssmc.cmd = C_SSM;
                     73:        ct_ssmc.fefm = FEF_MASK;
                     74:        ct_ssmc.refm = REF_MASK;
                     75:        ct_ssmc.aefm = AEF_MASK;
                     76:        ct_ssmc.iefm = IEF_MASK;
                     77:        hpibsend(unit, C_CMD, &ct_ssmc, sizeof(ct_ssmc));
                     78:        hpibswait(unit);
                     79:        hpibrecv(unit, C_QSTAT, &stat, 1);
                     80:        rs->sc_alive = 1;
                     81:        return (1);
                     82: }
                     83: 
                     84: ctident(unit)
                     85:        int unit;
                     86: {
                     87:        struct ct_describe desc;
                     88:        u_char stat, cmd[3];
                     89:        char name[7];
                     90:        int id, i;
                     91: 
                     92:        id = hpibid(unit);
                     93:        if ((id & 0x200) == 0)
                     94:                return(-1);
                     95:        for (i = 0; i < nctinfo; i++)
                     96:                if (id == ctinfo[i].hwid)
                     97:                        break;
                     98:        if (i == nctinfo)
                     99:                return(-1);
                    100:        ct_softc[unit].sc_punit = ctinfo[i].punit;
                    101:        id = i;
                    102: 
                    103:        /*
                    104:         * Collect device description.
                    105:         * Right now we only need this to differentiate 7945 from 7946.
                    106:         * Note that we always issue the describe command to unit 0.
                    107:         */
                    108:        cmd[0] = C_SUNIT(0);
                    109:        cmd[1] = C_SVOL(0);
                    110:        cmd[2] = C_DESC;
                    111:        hpibsend(unit, C_CMD, cmd, sizeof(cmd));
                    112:        hpibrecv(unit, C_EXEC, &desc, 37);
                    113:        hpibrecv(unit, C_QSTAT, &stat, sizeof(stat));
                    114:        bzero(name, sizeof(name));
                    115:        if (!stat) {
                    116:                register int n = desc.d_name;
                    117:                for (i = 5; i >= 0; i--) {
                    118:                        name[i] = (n & 0xf) + '0';
                    119:                        n >>= 4;
                    120:                }
                    121:        }
                    122:        switch (ctinfo[id].hwid) {
                    123:        case CT7946ID:
                    124:                if (bcmp(name, "079450", 6) == 0)
                    125:                        id = -1;                /* not really a 7946 */
                    126:                break;
                    127:        default:
                    128:                break;
                    129:        }
                    130:        return(id);
                    131: }
                    132: 
                    133: ctopen(io)
                    134:        struct iob *io;
                    135: {
                    136:        register int unit = io->i_unit;
                    137:        register struct ct_softc *rs = &ct_softc[unit];
                    138:        register int skip;
                    139: 
                    140:        if (hpibalive(unit) == 0)
                    141:                _stop("ct controller not configured");
                    142:        if (rs->sc_alive == 0)
                    143:                if (ctinit(unit) == 0)
                    144:                        _stop("ct init failed");
                    145:        ctstrategy(io, MTREW);
                    146:        skip = io->i_boff;
                    147:        while (skip--)
                    148:                ctstrategy(io, MTFSF);
                    149: }
                    150: 
                    151: ctclose(io)
                    152:        struct iob *io;
                    153: {
                    154:        ctstrategy(io, MTREW);
                    155: }
                    156: 
                    157: ctstrategy(io, func)
                    158:        register struct iob *io;
                    159:        register int func;
                    160: {
                    161:        register int unit = io->i_unit;
                    162:        register struct ct_softc *rs = &ct_softc[unit];
                    163:        char stat;
                    164: 
                    165:        rs->sc_retry = 0;
                    166:        ct_ioc.unit = C_SUNIT(rs->sc_punit);
                    167:        ct_ioc.saddr = C_SADDR;
                    168:        ct_ioc.nop2 = C_NOP;
                    169:        ct_ioc.slen = C_SLEN;
                    170:        ct_ioc.nop3 = C_NOP;
                    171: top:
                    172:        if (func == READ) {
                    173:                ct_ioc.cmd = C_READ;
                    174:                ct_ioc.addr = rs->sc_blkno;
                    175:                ct_ioc.len = io->i_cc;
                    176:        }
                    177:        else if (func == WRITE) {
                    178:                ct_ioc.cmd = C_WRITE;
                    179:                ct_ioc.addr = rs->sc_blkno;
                    180:                ct_ioc.len = io->i_cc;
                    181:        }
                    182:        else if (func == MTFSF) {
                    183:                ct_ioc.cmd = C_READ;
                    184:                ct_ioc.addr = rs->sc_blkno;
                    185:                ct_ioc.len = io->i_cc = MAXBSIZE;
                    186:                io->i_ma = io->i_buf;
                    187:        }
                    188:        else {
                    189:                ct_ioc.cmd = C_READ;
                    190:                ct_ioc.addr = 0;
                    191:                ct_ioc.len = 0;
                    192:                rs->sc_blkno = 0;
                    193:                io->i_cc = 0;
                    194:        }
                    195: retry:
                    196:        hpibsend(unit, C_CMD, &ct_ioc, sizeof(ct_ioc));
                    197:        if (func != MTREW) {
                    198:                hpibswait(unit);
                    199:                hpibgo(unit, C_EXEC, io->i_ma, io->i_cc,
                    200:                        func != WRITE ? READ : WRITE);
                    201:                hpibswait(unit);
                    202:        }
                    203:        else {
                    204:                while (hpibswait(unit) < 0)
                    205:                        ;
                    206:        }
                    207:        hpibrecv(unit, C_QSTAT, &stat, 1);
                    208:        if (stat) {
                    209:                stat = cterror(unit);
                    210:                if (stat == 0)
                    211:                        return (-1);
                    212:                if (stat == 2)
                    213:                        return (0);
                    214:                if (++rs->sc_retry > CTRETRY)
                    215:                        return (-1);
                    216:                else
                    217:                        goto retry;
                    218:        }
                    219:        rs->sc_blkno += CTBTOK(io->i_cc);
                    220:        if (func == MTFSF)
                    221:                goto top;
                    222:        return (io->i_cc);
                    223: }
                    224: 
                    225: cterror(unit)
                    226:        register int unit;
                    227: {
                    228:        register struct ct_softc *ct = &ct_softc[unit];
                    229:        char stat;
                    230: 
                    231:        ct_rsc.unit = C_SUNIT(ct->sc_punit);
                    232:        ct_rsc.cmd = C_STATUS;
                    233:        hpibsend(unit, C_CMD, &ct_rsc, sizeof(ct_rsc));
                    234:        hpibrecv(unit, C_EXEC, &ct_stat, sizeof(ct_stat));
                    235:        hpibrecv(unit, C_QSTAT, &stat, 1);
                    236:        if (stat) {
                    237:                printf("ct%d: request status fail %d\n", unit, stat);
                    238:                return(0);
                    239:        }
                    240:        if (ct_stat.c_aef & AEF_EOF) {
                    241:                /* 9145 drives don't increment block number at EOF */
                    242:                if ((ct_stat.c_blk - ct->sc_blkno) == 0)
                    243:                        ct->sc_blkno++;
                    244:                else
                    245:                        ct->sc_blkno = ct_stat.c_blk;
                    246:                return (2);
                    247:        }
                    248:        printf("ct%d err: vu 0x%x, pend 0x%x, bn%d", unit,
                    249:                ct_stat.c_vu, ct_stat.c_pend, ct_stat.c_blk);
                    250:        printf(", R 0x%x F 0x%x A 0x%x I 0x%x\n", ct_stat.c_ref,
                    251:                ct_stat.c_fef, ct_stat.c_aef, ct_stat.c_ief);
                    252:        return (1);
                    253: }

unix.superglobalmegacorp.com

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