|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1982, 1986, 1988 Regents of the University of California. ! 3: * All rights reserved. The Berkeley software License Agreement ! 4: * specifies the terms and conditions for redistribution. ! 5: * ! 6: * @(#)uda.c 7.10 (Berkeley) 4/4/90 ! 7: */ ! 8: ! 9: /* ! 10: * UDA50/RAxx disk device driver ! 11: */ ! 12: ! 13: #include "param.h" ! 14: #include "buf.h" ! 15: #include "disklabel.h" ! 16: ! 17: #include "../vax/pte.h" ! 18: ! 19: #include "saio.h" ! 20: #include "savax.h" ! 21: ! 22: /* ! 23: * Unused, but needed in udareg.h ! 24: */ ! 25: #define NRSP 1 ! 26: #define NCMD 1 ! 27: ! 28: #include "../vaxuba/udareg.h" ! 29: #include "../vaxuba/ubareg.h" ! 30: #include "../vaxuba/ubavar.h" ! 31: #include "../vax/mscp.h" ! 32: ! 33: #define NRA 8 /* max. unit number on controller */ ! 34: #define SECTSIZ 512 /* sector size in bytes */ ! 35: ! 36: #define MAXCTLR 1 /* all addresses must be specified */ ! 37: u_short udastd[MAXCTLR] = { 0772150 }; ! 38: ! 39: struct udadevice *udaddr[MAXNUBA][MAXCTLR]; ! 40: ! 41: struct uda1 { ! 42: struct uda1ca uda1_ca; /* communications area */ ! 43: struct mscp uda1_rsp; /* response packet */ ! 44: struct mscp uda1_cmd; /* command packet */ ! 45: } uda1; ! 46: ! 47: /* Unibus address of uda structure */ ! 48: struct uda1 *ud_ubaddr[MAXNUBA][MAXCTLR]; ! 49: struct disklabel ralabel[MAXNUBA][MAXCTLR][NRA]; ! 50: static u_long ramedia[MAXNUBA][MAXCTLR][NRA]; ! 51: char lbuf[SECTSIZ]; ! 52: ! 53: raopen(io) ! 54: register struct iob *io; ! 55: { ! 56: register struct disklabel *lp; ! 57: register struct udadevice *addr; ! 58: register struct uda1 *ubaaddr; ! 59: register int uba, unit; ! 60: static int udainit[MAXNUBA][MAXCTLR]; ! 61: struct iob tio; ! 62: ! 63: if ((u_int)(uba = io->i_adapt) >= nuba) ! 64: return (EADAPT); ! 65: if ((u_int)io->i_ctlr >= MAXCTLR) ! 66: return (ECTLR); ! 67: if ((u_int)(unit = io->i_unit) >= NRA) ! 68: return (EUNIT); ! 69: addr = udaddr[uba][io->i_ctlr] = ! 70: (struct udadevice *)ubamem(uba, udastd[io->i_ctlr]); ! 71: if (badaddr((char *)addr, sizeof(short))) ! 72: return (ENXIO); ! 73: if ((ubaaddr = ud_ubaddr[uba][io->i_ctlr]) == 0) { ! 74: tio = *io; ! 75: tio.i_ma = (caddr_t)&uda1; ! 76: tio.i_cc = sizeof(uda1); ! 77: ud_ubaddr[uba][io->i_ctlr] = ubaaddr = ! 78: (struct uda1 *)ubasetup(&tio, 2); ! 79: } ! 80: if (udainit[uba][io->i_ctlr] == 0) { ! 81: addr->udaip = 0; ! 82: while ((addr->udasa & UDA_STEP1) == 0); ! 83: addr->udasa = UDA_ERR; ! 84: while ((addr->udasa & UDA_STEP2) == 0); ! 85: addr->udasa = (int)&ubaaddr->uda1_ca.ca_rspdsc; ! 86: while ((addr->udasa & UDA_STEP3) == 0); ! 87: addr->udasa = (int)&ubaaddr->uda1_ca.ca_rspdsc >> 16; ! 88: while ((addr->udasa & UDA_STEP4) == 0); ! 89: addr->udasa = UDA_GO; ! 90: uda1.uda1_ca.ca_rspdsc = (long)&ubaaddr->uda1_rsp.mscp_cmdref; ! 91: uda1.uda1_ca.ca_cmddsc = (long)&ubaaddr->uda1_cmd.mscp_cmdref; ! 92: /* uda1.uda1_cmd.mscp_cntflgs = 0; */ ! 93: if (udcmd(M_OP_SETCTLRC, io)) { ! 94: printf("ra: open error, SETCTLRC\n"); ! 95: return (ENXIO); ! 96: } ! 97: udainit[uba][io->i_ctlr] = 1; ! 98: } ! 99: lp = &ralabel[uba][io->i_ctlr][unit]; ! 100: if (ramedia[uba][io->i_ctlr][unit] == 0) { ! 101: uda1.uda1_cmd.mscp_unit = unit; ! 102: if (udcmd(M_OP_ONLINE, io)) { ! 103: printf("ra: open error, ONLINE\n"); ! 104: return (ENXIO); ! 105: } ! 106: ramedia[uba][io->i_ctlr][unit] = ! 107: uda1.uda1_rsp.mscp_onle.onle_mediaid; ! 108: tio = *io; ! 109: tio.i_bn = LABELSECTOR; ! 110: tio.i_ma = lbuf; ! 111: tio.i_cc = SECTSIZ; ! 112: tio.i_flgs |= F_RDDATA; ! 113: if (rastrategy(&tio, READ) != SECTSIZ) ! 114: return (ERDLAB); ! 115: *lp = *(struct disklabel *)(lbuf + LABELOFFSET); ! 116: if (lp->d_magic != DISKMAGIC || lp->d_magic2 != DISKMAGIC) { ! 117: #ifdef COMPAT_42 ! 118: printf("ra%d: unlabeled\n", unit); ! 119: ramaptype(io, lp); ! 120: #else ! 121: return (EUNLAB); ! 122: #endif ! 123: } ! 124: } ! 125: if ((u_int)io->i_part >= lp->d_npartitions || ! 126: (io->i_boff = lp->d_partitions[io->i_part].p_offset) == -1) ! 127: return (EPART); ! 128: return (0); ! 129: } ! 130: ! 131: int ! 132: udcmd(op, io) ! 133: int op; ! 134: register struct iob *io; ! 135: { ! 136: register struct uda1 *u = &uda1; ! 137: register struct mscp *mp; ! 138: register int i; ! 139: ! 140: u->uda1_cmd.mscp_opcode = op; ! 141: u->uda1_cmd.mscp_msglen = MSCP_MSGLEN; ! 142: u->uda1_rsp.mscp_msglen = MSCP_MSGLEN; ! 143: u->uda1_ca.ca_rspdsc |= MSCP_OWN|MSCP_INT; ! 144: u->uda1_ca.ca_cmddsc |= MSCP_OWN|MSCP_INT; ! 145: i = udaddr[io->i_adapt][io->i_ctlr]->udaip; /* start uda polling */ ! 146: #ifdef lint ! 147: i = i; ! 148: #endif ! 149: mp = &u->uda1_rsp; ! 150: for (;;) { ! 151: if (u->uda1_ca.ca_cmdint) ! 152: u->uda1_ca.ca_cmdint = 0; ! 153: if (u->uda1_ca.ca_rspint == 0) ! 154: continue; ! 155: u->uda1_ca.ca_rspint = 0; ! 156: if (mp->mscp_opcode == (op | M_OP_END)) ! 157: break; ! 158: printf("unexpected rsp type %x op %x ignored\n", ! 159: MSCP_MSGTYPE(mp->mscp_msgtc), mp->mscp_opcode); ! 160: u->uda1_ca.ca_rspdsc |= MSCP_OWN | MSCP_INT; ! 161: } ! 162: if ((mp->mscp_status&M_ST_MASK) != M_ST_SUCCESS) ! 163: return (-1); ! 164: return (0); ! 165: } ! 166: ! 167: rastrategy(io, func) ! 168: register struct iob *io; ! 169: int func; ! 170: { ! 171: register struct mscp *mp; ! 172: register int ubinfo; ! 173: ! 174: ubinfo = ubasetup(io, 1); ! 175: mp = &uda1.uda1_cmd; ! 176: mp->mscp_unit = io->i_unit; ! 177: mp->mscp_seq.seq_lbn = io->i_bn; ! 178: mp->mscp_seq.seq_bytecount = io->i_cc; ! 179: mp->mscp_seq.seq_buffer = UBAI_ADDR(ubinfo) | (UBAI_BDP(ubinfo) << 24); ! 180: if (udcmd(func == READ ? M_OP_READ : M_OP_WRITE, io)) { ! 181: printf("ra: I/O error\n"); ! 182: ubafree(io, ubinfo); ! 183: return (-1); ! 184: } ! 185: ubafree(io, ubinfo); ! 186: return (io->i_cc); ! 187: } ! 188: ! 189: #ifdef COMPAT_42 ! 190: u_long rc25_off[] = { 0, 15884, 0, -1, -1, -1, 25916, -1 }; ! 191: u_long rx50_off[] = { 0, 0, 0, 0, 0, 0, 0, 0 }; ! 192: u_long rd52_off[] = { 0, 15884, 0, 0, 0, 0, 25650, 0 }; ! 193: u_long rd53_off[] = { 0, 15884, 0, 0, 0, 33440, 49324, 15884 }; ! 194: u_long ra60_off[] = { 0, 15884, 0, 49324, 131404, 49324, 242606, 49324 }; ! 195: #define ra70_off ra60_off ! 196: u_long ra80_off[] = { 0, 15884, 0, -1, 49324, 49324, 49910, 131404 }; ! 197: #ifndef UCBRA ! 198: #ifdef RA_COMPAT ! 199: u_long ra81_off[] = { 0, 16422, 0, 49324, 131404, 412490, 375564, 83538 }; ! 200: #else ! 201: u_long ra81_off[] = { 0, 16422, 0, 375564, 391986, 699720, 375564, 83538 }; ! 202: #endif ! 203: #else ! 204: u_long ra81_off[] = { 0, 15884, 0, 242606, 258490, 565690, 242606, 49324 }; ! 205: #endif ! 206: u_long ra82_off[] = { 0, 15884, 0, 375345, 391590, 699390, 375345, 83790 }; ! 207: ! 208: struct mediamap { ! 209: u_long id; /* media ID */ ! 210: u_long *off; /* offsets */ ! 211: } ra_map[] = { ! 212: { MSCP_MKDRIVE2('R', 'A', 60), ra60_off }, ! 213: { MSCP_MKDRIVE2('R', 'A', 70), ra70_off }, ! 214: { MSCP_MKDRIVE2('R', 'A', 80), ra80_off }, ! 215: { MSCP_MKDRIVE2('R', 'A', 81), ra81_off }, ! 216: { MSCP_MKDRIVE2('R', 'A', 82), ra82_off }, ! 217: { MSCP_MKDRIVE2('R', 'C', 25), rc25_off }, ! 218: { MSCP_MKDRIVE3('R', 'C', 'F', 25), rc25_off }, ! 219: { MSCP_MKDRIVE2('R', 'D', 52), rd52_off }, ! 220: { MSCP_MKDRIVE2('R', 'D', 53), rd53_off }, ! 221: { MSCP_MKDRIVE2('R', 'X', 50), rx50_off }, ! 222: 0 ! 223: }; ! 224: ! 225: ramaptype(io, lp) ! 226: register struct iob *io; ! 227: register struct disklabel *lp; ! 228: { ! 229: register struct partition *pp; ! 230: register u_long i; ! 231: register struct mediamap *map; ! 232: ! 233: i = MSCP_MEDIA_DRIVE(ramedia[io->i_adapt][io->i_ctlr][io->i_unit]); ! 234: for (map = ra_map; map->id != 0; map++) { ! 235: if (map->id == i) { ! 236: lp->d_npartitions = 8; ! 237: for (pp = lp->d_partitions, i = 0; i < 8; pp++, i++) ! 238: pp->p_offset = map->off[i]; ! 239: return; ! 240: } ! 241: } ! 242: printf("ra%d: media type 0x%x unsupported\n", io->i_unit, i); ! 243: lp->d_npartitions = 0; ! 244: } ! 245: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.