xref: /original-bsd/sys/hp300/stand/sd.c (revision 68d9582f)
1 /*
2  * Copyright (c) 1988 University of Utah.
3  * Copyright (c) 1990 The Regents of the University of California.
4  * All rights reserved.
5  *
6  * This code is derived from software contributed to Berkeley by
7  * Van Jacobson of Lawrence Berkeley Laboratory and the Systems
8  * Programming Group of the University of Utah Computer Science Department.
9  *
10  * %sccs.include.redist.c%
11  *
12  * from: Utah $Hdr: sd.c 1.2 90/01/23$
13  *
14  *	@(#)sd.c	7.5 (Berkeley) 06/18/92
15  */
16 
17 /*
18  * SCSI CCS disk driver
19  */
20 
21 #include "sys/param.h"
22 #include "saio.h"
23 #include "samachdep.h"
24 
25 #include "../dev/scsireg.h"
26 
27 struct	sd_softc {
28 	char	sc_retry;
29 	char	sc_alive;
30 	short	sc_blkshift;
31 } sd_softc[NSCSI][NSD];
32 
33 int sdpartoff[] = {
34 	1024,	17408,	0,	17408,
35 	115712,	218112,	82944,	115712
36 };
37 
38 #define	SDRETRY		2
39 
40 sdinit(ctlr, unit)
41 	int ctlr, unit;
42 {
43 	register struct sd_softc *ss = &sd_softc[ctlr][unit];
44 	u_char stat;
45 	int capbuf[2];
46 
47 	/* NB: HP6300 won't boot if next printf is removed (???) - vj */
48 	printf("sd(%d,%d,0,0): ", ctlr, unit);
49 	stat = scsi_test_unit_rdy(ctlr, unit);
50 	if (stat) {
51 		/* drive may be doing RTZ - wait a bit */
52 		printf("not ready - ");
53 		if (stat == STS_CHECKCOND) {
54 			printf("retrying ... ");
55 			DELAY(1000000);
56 			stat = scsi_test_unit_rdy(ctlr, unit);
57 		}
58 		if (stat) {
59 			printf("giving up (stat=%x).\n", stat);
60 			return (0);
61 		}
62 	}
63 	printf("unit ready.\n");
64 	/*
65 	 * try to get the drive block size.
66 	 */
67 	capbuf[0] = 0;
68 	capbuf[1] = 0;
69 	stat = scsi_read_capacity(ctlr, unit,
70 				  (u_char *)capbuf, sizeof(capbuf));
71 	if (stat == 0) {
72 		if (capbuf[1] > DEV_BSIZE)
73 			for (; capbuf[1] > DEV_BSIZE; capbuf[1] >>= 1)
74 				++ss->sc_blkshift;
75 	}
76 	ss->sc_alive = 1;
77 	return (1);
78 }
79 
80 sdreset(ctlr, unit)
81 	int ctlr, unit;
82 {
83 }
84 
85 sdopen(io)
86 	struct iob *io;
87 {
88 	register struct sd_softc *ss;
89 	int ctlr, unit, part;
90 
91 	devconvert(io);
92 
93 	ctlr = io->i_adapt;
94 	if (ctlr >= NSCSI || scsialive(ctlr) == 0)
95 		return (EADAPT);
96 	unit = io->i_ctlr;
97 	if (unit >= NSD)
98 		return (ECTLR);
99 	ss = &sd_softc[ctlr][unit];
100 	if (ss->sc_alive == 0)
101 		if (sdinit(ctlr, unit) == 0)
102 			return (ENXIO);
103 	part = io->i_part;
104 	if (part >= 8)
105 		return (EPART);
106 	io->i_boff = sdpartoff[part];
107 	return (0);
108 }
109 
110 sdstrategy(io, func)
111 	register struct iob *io;
112 	int func;
113 {
114 	register int ctlr = io->i_adapt;
115 	register int unit = io->i_ctlr;
116 	register struct sd_softc *ss = &sd_softc[ctlr][unit];
117 	daddr_t blk = io->i_bn >> ss->sc_blkshift;
118 	u_int nblk = io->i_cc >> ss->sc_blkshift;
119 	char stat;
120 
121 	ss->sc_retry = 0;
122 retry:
123 	if (func == F_READ)
124 		stat = scsi_tt_read(ctlr, unit, io->i_ma, io->i_cc, blk, nblk);
125 	else
126 		stat = scsi_tt_write(ctlr, unit, io->i_ma, io->i_cc, blk, nblk);
127 	if (stat) {
128 		printf("sd(%d,%d,%d,%d): block=%x, error=0x%x\n",
129 		       ctlr, unit, io->i_unit, io->i_part, blk, stat);
130 		if (++ss->sc_retry > SDRETRY)
131 			return(-1);
132 		goto retry;
133 	}
134 	return(io->i_cc);
135 }
136