|
|
1.1 root 1: /*
2: * Copyright (c) 1990 The Regents of the University of California.
3: * All rights reserved.
4: *
5: * This code is derived from software contributed to Berkeley by
6: * Van Jacobson of Lawrence Berkeley Laboratory.
7: *
8: * Redistribution and use in source and binary forms, with or without
9: * modification, are permitted provided that the following conditions
10: * are met:
11: * 1. Redistributions of source code must retain the above copyright
12: * notice, this list of conditions and the following disclaimer.
13: * 2. Redistributions in binary form must reproduce the above copyright
14: * notice, this list of conditions and the following disclaimer in the
15: * documentation and/or other materials provided with the distribution.
16: * 3. All advertising materials mentioning features or use of this software
17: * must display the following acknowledgement:
18: * This product includes software developed by the University of
19: * California, Berkeley and its contributors.
20: * 4. Neither the name of the University nor the names of its contributors
21: * may be used to endorse or promote products derived from this software
22: * without specific prior written permission.
23: *
24: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34: * SUCH DAMAGE.
35: *
36: * @(#)scsi.c 7.5 (Berkeley) 5/4/91
37: */
38:
39: /*
40: * HP9000/3xx 98658 SCSI host adaptor driver.
41: */
42: #include "scsi.h"
43: #if NSCSI > 0
44:
45: #ifndef lint
46: static char rcsid[] = "$Header: scsi.c,v 1.4 91/01/17 12:50:18 mike Exp $";
47: #endif
48:
49: #include "sys/param.h"
50: #include "sys/systm.h"
51: #include "sys/buf.h"
52: #include "device.h"
53:
54: #include "scsivar.h"
55: #include "scsireg.h"
56: #include "dmavar.h"
57:
58: #include "../include/cpu.h"
59: #include "../hp300/isr.h"
60:
61: /*
62: * SCSI delays
63: * In u-seconds, primarily for state changes on the SPC.
64: */
65: #define SCSI_CMD_WAIT 1000 /* wait per step of 'immediate' cmds */
66: #define SCSI_DATA_WAIT 1000 /* wait per data in/out step */
67: #define SCSI_INIT_WAIT 50000 /* wait per step (both) during init */
68:
69: extern void isrlink();
70: extern void _insque();
71: extern void _remque();
72:
73: int scsiinit(), scsigo(), scsiintr(), scsixfer();
74: void scsistart(), scsidone(), scsifree(), scsireset();
75: struct driver scsidriver = {
76: scsiinit, "scsi", (int (*)())scsistart, scsigo, scsiintr,
77: (int (*)())scsidone,
78: };
79:
80: struct scsi_softc scsi_softc[NSCSI];
81: struct isr scsi_isr[NSCSI];
82:
83: int scsi_cmd_wait = SCSI_CMD_WAIT;
84: int scsi_data_wait = SCSI_DATA_WAIT;
85: int scsi_init_wait = SCSI_INIT_WAIT;
86:
87: int scsi_nosync = 1; /* inhibit sync xfers if 1 */
88: int scsi_pridma = 0; /* use "priority" dma */
89:
90: #ifdef DEBUG
91: int scsi_debug = 0;
92: #define WAITHIST
93: #endif
94:
95: #ifdef WAITHIST
96: #define MAXWAIT 1022
97: u_int ixstart_wait[MAXWAIT+2];
98: u_int ixin_wait[MAXWAIT+2];
99: u_int ixout_wait[MAXWAIT+2];
100: u_int mxin_wait[MAXWAIT+2];
101: u_int mxin2_wait[MAXWAIT+2];
102: u_int cxin_wait[MAXWAIT+2];
103: u_int fxfr_wait[MAXWAIT+2];
104: u_int sgo_wait[MAXWAIT+2];
105: #define HIST(h,w) (++h[((w)>MAXWAIT? MAXWAIT : ((w) < 0 ? -1 : (w))) + 1]);
106: #else
107: #define HIST(h,w)
108: #endif
109:
110: #define b_cylin b_resid
111:
112: static void
113: scsiabort(hs, hd, where)
114: register struct scsi_softc *hs;
115: volatile register struct scsidevice *hd;
116: char *where;
117: {
118: int len;
119: u_char junk;
120:
121: printf("scsi%d: abort from %s: phase=0x%x, ssts=0x%x, ints=0x%x\n",
122: hs->sc_hc->hp_unit, where, hd->scsi_psns, hd->scsi_ssts,
123: hd->scsi_ints);
124:
125: hd->scsi_ints = hd->scsi_ints;
126: hd->scsi_csr = 0;
127: if (hd->scsi_psns == 0 || (hd->scsi_ssts & SSTS_INITIATOR) == 0)
128: /* no longer connected to scsi target */
129: return;
130:
131: /* get the number of bytes remaining in current xfer + fudge */
132: len = (hd->scsi_tch << 16) | (hd->scsi_tcm << 8) | hd->scsi_tcl;
133:
134: /* for that many bus cycles, try to send an abort msg */
135: for (len += 1024; (hd->scsi_ssts & SSTS_INITIATOR) && --len >= 0; ) {
136: hd->scsi_scmd = SCMD_SET_ATN;
137: while ((hd->scsi_psns & PSNS_REQ) == 0) {
138: if (! (hd->scsi_ssts & SSTS_INITIATOR))
139: goto out;
140: DELAY(1);
141: }
142: if ((hd->scsi_psns & PHASE) == MESG_OUT_PHASE)
143: hd->scsi_scmd = SCMD_RST_ATN;
144: hd->scsi_pctl = hd->scsi_psns & PHASE;
145: if (hd->scsi_psns & PHASE_IO) {
146: /* one of the input phases - read & discard a byte */
147: hd->scsi_scmd = SCMD_SET_ACK;
148: if (hd->scsi_tmod == 0)
149: while (hd->scsi_psns & PSNS_REQ)
150: DELAY(1);
151: junk = hd->scsi_temp;
152: } else {
153: /* one of the output phases - send an abort msg */
154: hd->scsi_temp = MSG_ABORT;
155: hd->scsi_scmd = SCMD_SET_ACK;
156: if (hd->scsi_tmod == 0)
157: while (hd->scsi_psns & PSNS_REQ)
158: DELAY(1);
159: }
160: hd->scsi_scmd = SCMD_RST_ACK;
161: }
162: out:
163: /*
164: * Either the abort was successful & the bus is disconnected or
165: * the device didn't listen. If the latter, announce the problem.
166: * Either way, reset the card & the SPC.
167: */
168: if (len < 0 && hs)
169: printf("scsi%d: abort failed. phase=0x%x, ssts=0x%x\n",
170: hs->sc_hc->hp_unit, hd->scsi_psns, hd->scsi_ssts);
171:
172: if (! ((junk = hd->scsi_ints) & INTS_RESEL)) {
173: hd->scsi_sctl |= SCTL_CTRLRST;
174: DELAY(1);
175: hd->scsi_sctl &=~ SCTL_CTRLRST;
176: hd->scsi_hconf = 0;
177: hd->scsi_ints = hd->scsi_ints;
178: }
179: }
180:
181: /*
182: * XXX Set/reset long delays.
183: *
184: * if delay == 0, reset default delays
185: * if delay < 0, set both delays to default long initialization values
186: * if delay > 0, set both delays to this value
187: *
188: * Used when a devices is expected to respond slowly (e.g. during
189: * initialization).
190: */
191: void
192: scsi_delay(delay)
193: int delay;
194: {
195: static int saved_cmd_wait, saved_data_wait;
196:
197: if (delay) {
198: saved_cmd_wait = scsi_cmd_wait;
199: saved_data_wait = scsi_data_wait;
200: if (delay > 0)
201: scsi_cmd_wait = scsi_data_wait = delay;
202: else
203: scsi_cmd_wait = scsi_data_wait = scsi_init_wait;
204: } else {
205: scsi_cmd_wait = saved_cmd_wait;
206: scsi_data_wait = saved_data_wait;
207: }
208: }
209:
210: int
211: scsiinit(hc)
212: register struct hp_ctlr *hc;
213: {
214: register struct scsi_softc *hs = &scsi_softc[hc->hp_unit];
215: register struct scsidevice *hd = (struct scsidevice *)hc->hp_addr;
216:
217: if ((hd->scsi_id & ID_MASK) != SCSI_ID)
218: return(0);
219: hc->hp_ipl = SCSI_IPL(hd->scsi_csr);
220: hs->sc_hc = hc;
221: hs->sc_dq.dq_unit = hc->hp_unit;
222: hs->sc_dq.dq_driver = &scsidriver;
223: hs->sc_sq.dq_forw = hs->sc_sq.dq_back = &hs->sc_sq;
224: scsi_isr[hc->hp_unit].isr_intr = scsiintr;
225: scsi_isr[hc->hp_unit].isr_ipl = hc->hp_ipl;
226: scsi_isr[hc->hp_unit].isr_arg = hc->hp_unit;
227: isrlink(&scsi_isr[hc->hp_unit]);
228: scsireset(hc->hp_unit);
229: return(1);
230: }
231:
232: void
233: scsireset(unit)
234: register int unit;
235: {
236: register struct scsi_softc *hs = &scsi_softc[unit];
237: volatile register struct scsidevice *hd =
238: (struct scsidevice *)hs->sc_hc->hp_addr;
239: u_int i;
240:
241: if (hs->sc_flags & SCSI_ALIVE)
242: scsiabort(hs, hd, "reset");
243:
244: printf("scsi%d: ", unit);
245:
246: hd->scsi_id = 0xFF;
247: DELAY(100);
248: /*
249: * Disable interrupts then reset the FUJI chip.
250: */
251: hd->scsi_csr = 0;
252: hd->scsi_sctl = SCTL_DISABLE | SCTL_CTRLRST;
253: hd->scsi_scmd = 0;
254: hd->scsi_tmod = 0;
255: hd->scsi_pctl = 0;
256: hd->scsi_temp = 0;
257: hd->scsi_tch = 0;
258: hd->scsi_tcm = 0;
259: hd->scsi_tcl = 0;
260: hd->scsi_ints = 0;
261:
262: if ((hd->scsi_id & ID_WORD_DMA) == 0) {
263: hs->sc_flags |= SCSI_DMA32;
264: printf("32 bit dma, ");
265: }
266:
267: /* Determine Max Synchronous Transfer Rate */
268: if (scsi_nosync)
269: i = 3;
270: else
271: i = SCSI_SYNC_XFER(hd->scsi_hconf);
272: switch (i) {
273: case 0:
274: hs->sc_sync = TMOD_SYNC | 0x3e; /* 250 nsecs */
275: printf("250ns sync");
276: break;
277: case 1:
278: hs->sc_sync = TMOD_SYNC | 0x5e; /* 375 nsecs */
279: printf("375ns sync");
280: break;
281: case 2:
282: hs->sc_sync = TMOD_SYNC | 0x7d; /* 500 nsecs */
283: printf("500ns sync");
284: break;
285: case 3:
286: hs->sc_sync = 0;
287: printf("async");
288: break;
289: }
290:
291: /*
292: * Configure the FUJI chip with its SCSI address, all
293: * interrupts enabled & appropriate parity.
294: */
295: i = (~hd->scsi_hconf) & 0x7;
296: hs->sc_scsi_addr = 1 << i;
297: hd->scsi_bdid = i;
298: if (hd->scsi_hconf & HCONF_PARITY)
299: hd->scsi_sctl = SCTL_DISABLE | SCTL_ABRT_ENAB |
300: SCTL_SEL_ENAB | SCTL_RESEL_ENAB |
301: SCTL_INTR_ENAB | SCTL_PARITY_ENAB;
302: else {
303: hd->scsi_sctl = SCTL_DISABLE | SCTL_ABRT_ENAB |
304: SCTL_SEL_ENAB | SCTL_RESEL_ENAB |
305: SCTL_INTR_ENAB;
306: printf(", no parity");
307: }
308: hd->scsi_sctl &=~ SCTL_DISABLE;
309:
310: printf(", scsi id %d\n", i);
311: hs->sc_flags |= SCSI_ALIVE;
312: }
313:
314: static void
315: scsierror(hs, hd, ints)
316: register struct scsi_softc *hs;
317: volatile register struct scsidevice *hd;
318: u_char ints;
319: {
320: int unit = hs->sc_hc->hp_unit;
321: char *sep = "";
322:
323: printf("scsi%d: ", unit);
324: if (ints & INTS_RST) {
325: DELAY(100);
326: if (hd->scsi_hconf & HCONF_SD)
327: printf("spurious RST interrupt");
328: else
329: printf("hardware error - check fuse");
330: sep = ", ";
331: }
332: if ((ints & INTS_HARD_ERR) || hd->scsi_serr) {
333: if (hd->scsi_serr & SERR_SCSI_PAR) {
334: printf("%sparity err", sep);
335: sep = ", ";
336: }
337: if (hd->scsi_serr & SERR_SPC_PAR) {
338: printf("%sSPC parity err", sep);
339: sep = ", ";
340: }
341: if (hd->scsi_serr & SERR_TC_PAR) {
342: printf("%sTC parity err", sep);
343: sep = ", ";
344: }
345: if (hd->scsi_serr & SERR_PHASE_ERR) {
346: printf("%sphase err", sep);
347: sep = ", ";
348: }
349: if (hd->scsi_serr & SERR_SHORT_XFR) {
350: printf("%ssync short transfer err", sep);
351: sep = ", ";
352: }
353: if (hd->scsi_serr & SERR_OFFSET) {
354: printf("%ssync offset error", sep);
355: sep = ", ";
356: }
357: }
358: if (ints & INTS_TIMEOUT)
359: printf("%sSPC select timeout error", sep);
360: if (ints & INTS_SRV_REQ)
361: printf("%sspurious SRV_REQ interrupt", sep);
362: if (ints & INTS_CMD_DONE)
363: printf("%sspurious CMD_DONE interrupt", sep);
364: if (ints & INTS_DISCON)
365: printf("%sspurious disconnect interrupt", sep);
366: if (ints & INTS_RESEL)
367: printf("%sspurious reselect interrupt", sep);
368: if (ints & INTS_SEL)
369: printf("%sspurious select interrupt", sep);
370: printf("\n");
371: }
372:
373: static int
374: issue_select(hd, target, our_addr)
375: volatile register struct scsidevice *hd;
376: u_char target, our_addr;
377: {
378: if (hd->scsi_ssts & (SSTS_INITIATOR|SSTS_TARGET|SSTS_BUSY))
379: return (1);
380:
381: if (hd->scsi_ints & INTS_DISCON)
382: hd->scsi_ints = INTS_DISCON;
383:
384: hd->scsi_pctl = 0;
385: hd->scsi_temp = (1 << target) | our_addr;
386: /* select timeout is hardcoded to 2ms */
387: hd->scsi_tch = 0;
388: hd->scsi_tcm = 32;
389: hd->scsi_tcl = 4;
390:
391: hd->scsi_scmd = SCMD_SELECT;
392: return (0);
393: }
394:
395: static int
396: wait_for_select(hd)
397: volatile register struct scsidevice *hd;
398: {
399: u_char ints;
400:
401: while ((ints = hd->scsi_ints) == 0)
402: DELAY(1);
403: hd->scsi_ints = ints;
404: return (!(hd->scsi_ssts & SSTS_INITIATOR));
405: }
406:
407: static int
408: ixfer_start(hd, len, phase, wait)
409: volatile register struct scsidevice *hd;
410: int len;
411: u_char phase;
412: register int wait;
413: {
414:
415: hd->scsi_tch = len >> 16;
416: hd->scsi_tcm = len >> 8;
417: hd->scsi_tcl = len;
418: hd->scsi_pctl = phase;
419: hd->scsi_tmod = 0; /*XXX*/
420: hd->scsi_scmd = SCMD_XFR | SCMD_PROG_XFR;
421:
422: /* wait for xfer to start or svc_req interrupt */
423: while ((hd->scsi_ssts & SSTS_BUSY) == 0) {
424: if (hd->scsi_ints || --wait < 0) {
425: #ifdef DEBUG
426: if (scsi_debug)
427: printf("ixfer_start fail: i%x, w%d\n",
428: hd->scsi_ints, wait);
429: #endif
430: HIST(ixstart_wait, wait)
431: return (0);
432: }
433: DELAY(1);
434: }
435: HIST(ixstart_wait, wait)
436: return (1);
437: }
438:
439: static int
440: ixfer_out(hd, len, buf)
441: volatile register struct scsidevice *hd;
442: int len;
443: register u_char *buf;
444: {
445: register int wait = scsi_data_wait;
446:
447: for (; len > 0; --len) {
448: while (hd->scsi_ssts & SSTS_DREG_FULL) {
449: if (hd->scsi_ints || --wait < 0) {
450: #ifdef DEBUG
451: if (scsi_debug)
452: printf("ixfer_out fail: l%d i%x w%d\n",
453: len, hd->scsi_ints, wait);
454: #endif
455: HIST(ixout_wait, wait)
456: return (len);
457: }
458: DELAY(1);
459: }
460: hd->scsi_dreg = *buf++;
461: }
462: HIST(ixout_wait, wait)
463: return (0);
464: }
465:
466: static void
467: ixfer_in(hd, len, buf)
468: volatile register struct scsidevice *hd;
469: int len;
470: register u_char *buf;
471: {
472: register int wait = scsi_data_wait;
473:
474: for (; len > 0; --len) {
475: while (hd->scsi_ssts & SSTS_DREG_EMPTY) {
476: if (hd->scsi_ints || --wait < 0) {
477: while (! (hd->scsi_ssts & SSTS_DREG_EMPTY)) {
478: *buf++ = hd->scsi_dreg;
479: --len;
480: }
481: #ifdef DEBUG
482: if (scsi_debug)
483: printf("ixfer_in fail: l%d i%x w%d\n",
484: len, hd->scsi_ints, wait);
485: #endif
486: HIST(ixin_wait, wait)
487: return;
488: }
489: DELAY(1);
490: }
491: *buf++ = hd->scsi_dreg;
492: }
493: HIST(ixin_wait, wait)
494: }
495:
496: static int
497: mxfer_in(hd, len, buf, phase)
498: volatile register struct scsidevice *hd;
499: register int len;
500: register u_char *buf;
501: register u_char phase;
502: {
503: register int wait = scsi_cmd_wait;
504: register int i;
505:
506: hd->scsi_tmod = 0;
507: for (i = 0; i < len; ++i) {
508: /*
509: * manual sez: reset ATN before ACK is sent.
510: */
511: if (hd->scsi_psns & PSNS_ATN)
512: hd->scsi_scmd = SCMD_RST_ATN;
513: /*
514: * wait for the request line (which says the target
515: * wants to give us data). If the phase changes while
516: * we're waiting, we're done.
517: */
518: while ((hd->scsi_psns & PSNS_REQ) == 0) {
519: if (--wait < 0) {
520: HIST(mxin_wait, wait)
521: return (-1);
522: }
523: if ((hd->scsi_psns & PHASE) != phase ||
524: (hd->scsi_ssts & SSTS_INITIATOR) == 0)
525: goto out;
526:
527: DELAY(1);
528: }
529: /*
530: * set ack (which says we're ready for the data, wait for
531: * req to go away (target says data is available), grab the
532: * data, then reset ack (say we've got the data).
533: */
534: hd->scsi_pctl = phase;
535: hd->scsi_scmd = SCMD_SET_ACK;
536: while (hd->scsi_psns & PSNS_REQ) {
537: if (--wait < 0) {
538: HIST(mxin_wait, wait)
539: return (-2);
540: }
541: DELAY(1);
542: }
543: *buf++ = hd->scsi_temp;
544: hd->scsi_scmd = SCMD_RST_ACK;
545: }
546: out:
547: HIST(mxin_wait, wait)
548: /*
549: * Wait for manual transfer to finish.
550: * Avoids occasional "unexpected phase" errors in finishxfer
551: * formerly addressed by per-slave delays.
552: */
553: wait = scsi_cmd_wait;
554: while ((hd->scsi_ssts & SSTS_ACTIVE) == SSTS_INITIATOR) {
555: if (--wait < 0)
556: break;
557: DELAY(1);
558: }
559: HIST(mxin2_wait, wait)
560: return (i);
561: }
562:
563: /*
564: * SCSI 'immediate' command: issue a command to some SCSI device
565: * and get back an 'immediate' response (i.e., do programmed xfer
566: * to get the response data). 'cbuf' is a buffer containing a scsi
567: * command of length clen bytes. 'buf' is a buffer of length 'len'
568: * bytes for data. The transfer direction is determined by the device
569: * (i.e., by the scsi bus data xfer phase). If 'len' is zero, the
570: * command must supply no data. 'xferphase' is the bus phase the
571: * caller expects to happen after the command is issued. It should
572: * be one of DATA_IN_PHASE, DATA_OUT_PHASE or STATUS_PHASE.
573: */
574: static int
575: scsiicmd(hs, target, cbuf, clen, buf, len, xferphase)
576: struct scsi_softc *hs;
577: int target;
578: u_char *cbuf;
579: int clen;
580: u_char *buf;
581: int len;
582: u_char xferphase;
583: {
584: volatile register struct scsidevice *hd =
585: (struct scsidevice *)hs->sc_hc->hp_addr;
586: u_char phase, ints;
587: register int wait;
588:
589: /* select the SCSI bus (it's an error if bus isn't free) */
590: if (issue_select(hd, target, hs->sc_scsi_addr))
591: return (-1);
592: if (wait_for_select(hd))
593: return (-1);
594: /*
595: * Wait for a phase change (or error) then let the device
596: * sequence us through the various SCSI phases.
597: */
598: hs->sc_stat[0] = 0xff;
599: hs->sc_msg[0] = 0xff;
600: phase = CMD_PHASE;
601: while (1) {
602: wait = scsi_cmd_wait;
603: switch (phase) {
604:
605: case CMD_PHASE:
606: if (ixfer_start(hd, clen, phase, wait))
607: if (ixfer_out(hd, clen, cbuf))
608: goto abort;
609: phase = xferphase;
610: break;
611:
612: case DATA_IN_PHASE:
613: if (len <= 0)
614: goto abort;
615: wait = scsi_data_wait;
616: if (ixfer_start(hd, len, phase, wait) ||
617: !(hd->scsi_ssts & SSTS_DREG_EMPTY))
618: ixfer_in(hd, len, buf);
619: phase = STATUS_PHASE;
620: break;
621:
622: case DATA_OUT_PHASE:
623: if (len <= 0)
624: goto abort;
625: wait = scsi_data_wait;
626: if (ixfer_start(hd, len, phase, wait)) {
627: if (ixfer_out(hd, len, buf))
628: goto abort;
629: }
630: phase = STATUS_PHASE;
631: break;
632:
633: case STATUS_PHASE:
634: wait = scsi_data_wait;
635: if (ixfer_start(hd, sizeof(hs->sc_stat), phase, wait) ||
636: !(hd->scsi_ssts & SSTS_DREG_EMPTY))
637: ixfer_in(hd, sizeof(hs->sc_stat), hs->sc_stat);
638: phase = MESG_IN_PHASE;
639: break;
640:
641: case MESG_IN_PHASE:
642: if (ixfer_start(hd, sizeof(hs->sc_msg), phase, wait) ||
643: !(hd->scsi_ssts & SSTS_DREG_EMPTY)) {
644: ixfer_in(hd, sizeof(hs->sc_msg), hs->sc_msg);
645: hd->scsi_scmd = SCMD_RST_ACK;
646: }
647: phase = BUS_FREE_PHASE;
648: break;
649:
650: case BUS_FREE_PHASE:
651: goto out;
652:
653: default:
654: printf("scsi%d: unexpected phase %d in icmd from %d\n",
655: hs->sc_hc->hp_unit, phase, target);
656: goto abort;
657: }
658: /* wait for last command to complete */
659: while ((ints = hd->scsi_ints) == 0) {
660: if (--wait < 0) {
661: HIST(cxin_wait, wait)
662: goto abort;
663: }
664: DELAY(1);
665: }
666: HIST(cxin_wait, wait)
667: hd->scsi_ints = ints;
668: if (ints & INTS_SRV_REQ)
669: phase = hd->scsi_psns & PHASE;
670: else if (ints & INTS_DISCON)
671: goto out;
672: else if ((ints & INTS_CMD_DONE) == 0) {
673: scsierror(hs, hd, ints);
674: goto abort;
675: }
676: }
677: abort:
678: scsiabort(hs, hd, "icmd");
679: out:
680: return (hs->sc_stat[0]);
681: }
682:
683: /*
684: * Finish SCSI xfer command: After the completion interrupt from
685: * a read/write operation, sequence through the final phases in
686: * programmed i/o. This routine is a lot like scsiicmd except we
687: * skip (and don't allow) the select, cmd out and data in/out phases.
688: */
689: static void
690: finishxfer(hs, hd, target)
691: struct scsi_softc *hs;
692: volatile register struct scsidevice *hd;
693: int target;
694: {
695: u_char phase, ints;
696:
697: /*
698: * We specified padding xfer so we ended with either a phase
699: * change interrupt (normal case) or an error interrupt (handled
700: * elsewhere). Reset the board dma logic then try to get the
701: * completion status & command done msg. The reset confuses
702: * the SPC REQ/ACK logic so we have to do any status/msg input
703: * operations via 'manual xfer'.
704: */
705: if (hd->scsi_ssts & SSTS_BUSY) {
706: int wait = scsi_cmd_wait;
707:
708: /* wait for dma operation to finish */
709: while (hd->scsi_ssts & SSTS_BUSY) {
710: if (--wait < 0) {
711: #ifdef DEBUG
712: if (scsi_debug)
713: printf("finishxfer fail: ssts %x\n",
714: hd->scsi_ssts);
715: #endif
716: HIST(fxfr_wait, wait)
717: goto abort;
718: }
719: }
720: HIST(fxfr_wait, wait)
721: }
722: hd->scsi_scmd |= SCMD_PROG_XFR;
723: hd->scsi_sctl |= SCTL_CTRLRST;
724: DELAY(1);
725: hd->scsi_sctl &=~ SCTL_CTRLRST;
726: hd->scsi_hconf = 0;
727: hs->sc_stat[0] = 0xff;
728: hs->sc_msg[0] = 0xff;
729: hd->scsi_csr = 0;
730: hd->scsi_ints = ints = hd->scsi_ints;
731: while (1) {
732: phase = hd->scsi_psns & PHASE;
733: switch (phase) {
734:
735: case STATUS_PHASE:
736: if (mxfer_in(hd, sizeof(hs->sc_stat), hs->sc_stat,
737: phase) <= 0)
738: goto abort;
739: break;
740:
741: case MESG_IN_PHASE:
742: if (mxfer_in(hd, sizeof(hs->sc_msg), hs->sc_msg,
743: phase) < 0)
744: goto abort;
745: break;
746:
747: case BUS_FREE_PHASE:
748: return;
749:
750: default:
751: printf("scsi%d: unexpected phase %d in finishxfer from %d\n",
752: hs->sc_hc->hp_unit, phase, target);
753: goto abort;
754: }
755: if (ints = hd->scsi_ints) {
756: hd->scsi_ints = ints;
757: if (ints & INTS_DISCON)
758: return;
759: else if (ints & ~(INTS_SRV_REQ|INTS_CMD_DONE)) {
760: scsierror(hs, hd, ints);
761: break;
762: }
763: }
764: if ((hd->scsi_ssts & SSTS_INITIATOR) == 0)
765: return;
766: }
767: abort:
768: scsiabort(hs, hd, "finishxfer");
769: hs->sc_stat[0] = 0xfe;
770: }
771:
772: int
773: scsi_test_unit_rdy(ctlr, slave, unit)
774: int ctlr, slave, unit;
775: {
776: register struct scsi_softc *hs = &scsi_softc[ctlr];
777: static struct scsi_cdb6 cdb = { CMD_TEST_UNIT_READY };
778:
779: cdb.lun = unit;
780: return (scsiicmd(hs, slave, &cdb, sizeof(cdb), (u_char *)0, 0,
781: STATUS_PHASE));
782: }
783:
784: int
785: scsi_request_sense(ctlr, slave, unit, buf, len)
786: int ctlr, slave, unit;
787: u_char *buf;
788: unsigned len;
789: {
790: register struct scsi_softc *hs = &scsi_softc[ctlr];
791: static struct scsi_cdb6 cdb = { CMD_REQUEST_SENSE };
792:
793: cdb.lun = unit;
794: cdb.len = len;
795: return (scsiicmd(hs, slave, &cdb, sizeof(cdb), buf, len, DATA_IN_PHASE));
796: }
797:
798: int
799: scsi_immed_command(ctlr, slave, unit, cdb, buf, len, rd)
800: int ctlr, slave, unit;
801: struct scsi_fmt_cdb *cdb;
802: u_char *buf;
803: unsigned len;
804: {
805: register struct scsi_softc *hs = &scsi_softc[ctlr];
806:
807: cdb->cdb[1] |= unit << 5;
808: return (scsiicmd(hs, slave, cdb->cdb, cdb->len, buf, len,
809: rd != 0? DATA_IN_PHASE : DATA_OUT_PHASE));
810: }
811:
812: /*
813: * The following routines are test-and-transfer i/o versions of read/write
814: * for things like reading disk labels and writing core dumps. The
815: * routine scsigo should be used for normal data transfers, NOT these
816: * routines.
817: */
818: int
819: scsi_tt_read(ctlr, slave, unit, buf, len, blk, bshift)
820: int ctlr, slave, unit;
821: u_char *buf;
822: u_int len;
823: daddr_t blk;
824: int bshift;
825: {
826: register struct scsi_softc *hs = &scsi_softc[ctlr];
827: struct scsi_cdb10 cdb;
828: int stat;
829: int old_wait = scsi_data_wait;
830:
831: scsi_data_wait = 300000;
832: bzero(&cdb, sizeof(cdb));
833: cdb.cmd = CMD_READ_EXT;
834: cdb.lun = unit;
835: blk >>= bshift;
836: cdb.lbah = blk >> 24;
837: cdb.lbahm = blk >> 16;
838: cdb.lbalm = blk >> 8;
839: cdb.lbal = blk;
840: cdb.lenh = len >> (8 + DEV_BSHIFT + bshift);
841: cdb.lenl = len >> (DEV_BSHIFT + bshift);
842: stat = scsiicmd(hs, slave, &cdb, sizeof(cdb), buf, len, DATA_IN_PHASE);
843: scsi_data_wait = old_wait;
844: return (stat);
845: }
846:
847: int
848: scsi_tt_write(ctlr, slave, unit, buf, len, blk, bshift)
849: int ctlr, slave, unit;
850: u_char *buf;
851: u_int len;
852: daddr_t blk;
853: int bshift;
854: {
855: register struct scsi_softc *hs = &scsi_softc[ctlr];
856: struct scsi_cdb10 cdb;
857: int stat;
858: int old_wait = scsi_data_wait;
859:
860: scsi_data_wait = 300000;
861:
862: bzero(&cdb, sizeof(cdb));
863: cdb.cmd = CMD_WRITE_EXT;
864: cdb.lun = unit;
865: blk >>= bshift;
866: cdb.lbah = blk >> 24;
867: cdb.lbahm = blk >> 16;
868: cdb.lbalm = blk >> 8;
869: cdb.lbal = blk;
870: cdb.lenh = len >> (8 + DEV_BSHIFT + bshift);
871: cdb.lenl = len >> (DEV_BSHIFT + bshift);
872: stat = scsiicmd(hs, slave, &cdb, sizeof(cdb), buf, len, DATA_OUT_PHASE);
873: scsi_data_wait = old_wait;
874: return (stat);
875: }
876:
877: int
878: scsireq(dq)
879: register struct devqueue *dq;
880: {
881: register struct devqueue *hq;
882:
883: hq = &scsi_softc[dq->dq_ctlr].sc_sq;
884: insque(dq, hq->dq_back);
885: if (dq->dq_back == hq)
886: return(1);
887: return(0);
888: }
889:
890: int
891: scsiustart(unit)
892: int unit;
893: {
894: register struct scsi_softc *hs = &scsi_softc[unit];
895:
896: hs->sc_dq.dq_ctlr = DMA0 | DMA1;
897: if (dmareq(&hs->sc_dq))
898: return(1);
899: return(0);
900: }
901:
902: void
903: scsistart(unit)
904: int unit;
905: {
906: register struct devqueue *dq;
907:
908: dq = scsi_softc[unit].sc_sq.dq_forw;
909: (dq->dq_driver->d_go)(dq->dq_unit);
910: }
911:
912: int
913: scsigo(ctlr, slave, unit, bp, cdb, pad)
914: int ctlr, slave, unit;
915: struct buf *bp;
916: struct scsi_fmt_cdb *cdb;
917: int pad;
918: {
919: register struct scsi_softc *hs = &scsi_softc[ctlr];
920: volatile register struct scsidevice *hd =
921: (struct scsidevice *)hs->sc_hc->hp_addr;
922: int i, dmaflags;
923: u_char phase, ints, cmd;
924:
925: cdb->cdb[1] |= unit << 5;
926:
927: /* select the SCSI bus (it's an error if bus isn't free) */
928: if (issue_select(hd, slave, hs->sc_scsi_addr) || wait_for_select(hd)) {
929: dmafree(&hs->sc_dq);
930: return (1);
931: }
932: /*
933: * Wait for a phase change (or error) then let the device
934: * sequence us through command phase (we may have to take
935: * a msg in/out before doing the command). If the disk has
936: * to do a seek, it may be a long time until we get a change
937: * to data phase so, in the absense of an explicit phase
938: * change, we assume data phase will be coming up and tell
939: * the SPC to start a transfer whenever it does. We'll get
940: * a service required interrupt later if this assumption is
941: * wrong. Otherwise we'll get a service required int when
942: * the transfer changes to status phase.
943: */
944: phase = CMD_PHASE;
945: while (1) {
946: register int wait = scsi_cmd_wait;
947:
948: switch (phase) {
949:
950: case CMD_PHASE:
951: if (ixfer_start(hd, cdb->len, phase, wait))
952: if (ixfer_out(hd, cdb->len, cdb->cdb))
953: goto abort;
954: break;
955:
956: case MESG_IN_PHASE:
957: if (ixfer_start(hd, sizeof(hs->sc_msg), phase, wait)||
958: !(hd->scsi_ssts & SSTS_DREG_EMPTY)) {
959: ixfer_in(hd, sizeof(hs->sc_msg), hs->sc_msg);
960: hd->scsi_scmd = SCMD_RST_ACK;
961: }
962: phase = BUS_FREE_PHASE;
963: break;
964:
965: case DATA_IN_PHASE:
966: case DATA_OUT_PHASE:
967: goto out;
968:
969: default:
970: printf("scsi%d: unexpected phase %d in go from %d\n",
971: hs->sc_hc->hp_unit, phase, slave);
972: goto abort;
973: }
974: while ((ints = hd->scsi_ints) == 0) {
975: if (--wait < 0) {
976: HIST(sgo_wait, wait)
977: goto abort;
978: }
979: DELAY(1);
980: }
981: HIST(sgo_wait, wait)
982: hd->scsi_ints = ints;
983: if (ints & INTS_SRV_REQ)
984: phase = hd->scsi_psns & PHASE;
985: else if (ints & INTS_CMD_DONE)
986: goto out;
987: else {
988: scsierror(hs, hd, ints);
989: goto abort;
990: }
991: }
992: out:
993: /*
994: * Reset the card dma logic, setup the dma channel then
995: * get the dio part of the card set for a dma xfer.
996: */
997: hd->scsi_hconf = 0;
998: cmd = CSR_IE;
999: dmaflags = DMAGO_NOINT;
1000: if (scsi_pridma)
1001: dmaflags |= DMAGO_PRI;
1002: if (bp->b_flags & B_READ)
1003: dmaflags |= DMAGO_READ;
1004: if ((hs->sc_flags & SCSI_DMA32) &&
1005: ((int)bp->b_un.b_addr & 3) == 0 && (bp->b_bcount & 3) == 0) {
1006: cmd |= CSR_DMA32;
1007: dmaflags |= DMAGO_LWORD;
1008: } else
1009: dmaflags |= DMAGO_WORD;
1010: dmago(hs->sc_dq.dq_ctlr, bp->b_un.b_addr, bp->b_bcount, dmaflags);
1011:
1012: if (bp->b_flags & B_READ) {
1013: cmd |= CSR_DMAIN;
1014: phase = DATA_IN_PHASE;
1015: } else
1016: phase = DATA_OUT_PHASE;
1017: /*
1018: * DMA enable bits must be set after size and direction bits.
1019: */
1020: hd->scsi_csr = cmd;
1021: hd->scsi_csr |= (CSR_DE0 << hs->sc_dq.dq_ctlr);
1022: /*
1023: * Setup the SPC for the transfer. We don't want to take
1024: * first a command complete then a service required interrupt
1025: * at the end of the transfer so we try to disable the cmd
1026: * complete by setting the transfer counter to more bytes
1027: * than we expect. (XXX - This strategy may have to be
1028: * modified to deal with devices that return variable length
1029: * blocks, e.g., some tape drives.)
1030: */
1031: cmd = SCMD_XFR;
1032: i = (unsigned)bp->b_bcount;
1033: if (pad) {
1034: cmd |= SCMD_PAD;
1035: /*
1036: * XXX - If we don't do this, the last 2 or 4 bytes
1037: * (depending on word/lword DMA) of a read get trashed.
1038: * It looks like it is necessary for the DMA to complete
1039: * before the SPC goes into "pad mode"??? Note: if we
1040: * also do this on a write, the request never completes.
1041: */
1042: if (bp->b_flags & B_READ)
1043: i += 2;
1044: #ifdef DEBUG
1045: hs->sc_flags |= SCSI_PAD;
1046: if (i & 1)
1047: printf("scsi%d: odd byte count: %d bytes @ %d\n",
1048: ctlr, i, bp->b_cylin);
1049: #endif
1050: } else
1051: i += 4;
1052: hd->scsi_tch = i >> 16;
1053: hd->scsi_tcm = i >> 8;
1054: hd->scsi_tcl = i;
1055: hd->scsi_pctl = phase;
1056: hd->scsi_tmod = 0;
1057: hd->scsi_scmd = cmd;
1058: hs->sc_flags |= SCSI_IO;
1059: return (0);
1060: abort:
1061: scsiabort(hs, hd, "go");
1062: dmafree(&hs->sc_dq);
1063: return (1);
1064: }
1065:
1066: void
1067: scsidone(unit)
1068: register int unit;
1069: {
1070: volatile register struct scsidevice *hd =
1071: (struct scsidevice *)scsi_softc[unit].sc_hc->hp_addr;
1072:
1073: #ifdef DEBUG
1074: if (scsi_debug)
1075: printf("scsi%d: done called!\n");
1076: #endif
1077: /* dma operation is done -- turn off card dma */
1078: hd->scsi_csr &=~ (CSR_DE1|CSR_DE0);
1079: }
1080:
1081: int
1082: scsiintr(unit)
1083: register int unit;
1084: {
1085: register struct scsi_softc *hs = &scsi_softc[unit];
1086: volatile register struct scsidevice *hd =
1087: (struct scsidevice *)hs->sc_hc->hp_addr;
1088: register u_char ints;
1089: register struct devqueue *dq;
1090:
1091: if ((hd->scsi_csr & (CSR_IE|CSR_IR)) != (CSR_IE|CSR_IR))
1092: return (0);
1093:
1094: ints = hd->scsi_ints;
1095: if ((ints & INTS_SRV_REQ) && (hs->sc_flags & SCSI_IO)) {
1096: /*
1097: * this should be the normal i/o completion case.
1098: * get the status & cmd complete msg then let the
1099: * device driver look at what happened.
1100: */
1101: #ifdef DEBUG
1102: int len = (hd->scsi_tch << 16) | (hd->scsi_tcm << 8) |
1103: hd->scsi_tcl;
1104: if (!(hs->sc_flags & SCSI_PAD))
1105: len -= 4;
1106: hs->sc_flags &=~ SCSI_PAD;
1107: #endif
1108: dq = hs->sc_sq.dq_forw;
1109: finishxfer(hs, hd, dq->dq_slave);
1110: hs->sc_flags &=~ SCSI_IO;
1111: dmafree(&hs->sc_dq);
1112: (dq->dq_driver->d_intr)(dq->dq_unit, hs->sc_stat[0]);
1113: } else {
1114: /* Something unexpected happened -- deal with it. */
1115: hd->scsi_ints = ints;
1116: hd->scsi_csr = 0;
1117: scsierror(hs, hd, ints);
1118: scsiabort(hs, hd, "intr");
1119: if (hs->sc_flags & SCSI_IO) {
1120: hs->sc_flags &=~ SCSI_IO;
1121: dmafree(&hs->sc_dq);
1122: dq = hs->sc_sq.dq_forw;
1123: (dq->dq_driver->d_intr)(dq->dq_unit, -1);
1124: }
1125: }
1126: return(1);
1127: }
1128:
1129: void
1130: scsifree(dq)
1131: register struct devqueue *dq;
1132: {
1133: register struct devqueue *hq;
1134:
1135: hq = &scsi_softc[dq->dq_ctlr].sc_sq;
1136: remque(dq);
1137: if ((dq = hq->dq_forw) != hq)
1138: (dq->dq_driver->d_start)(dq->dq_unit);
1139: }
1140:
1141: /*
1142: * (XXX) The following routine is needed for the SCSI tape driver
1143: * to read odd-size records.
1144: */
1145:
1146: #include "st.h"
1147: #if NST > 0
1148: int
1149: scsi_tt_oddio(ctlr, slave, unit, buf, len, b_flags, freedma)
1150: int ctlr, slave, unit, b_flags;
1151: u_char *buf;
1152: u_int len;
1153: {
1154: register struct scsi_softc *hs = &scsi_softc[ctlr];
1155: struct scsi_cdb6 cdb;
1156: u_char iphase;
1157: int stat;
1158:
1159: /*
1160: * First free any DMA channel that was allocated.
1161: * We can't use DMA to do this transfer.
1162: */
1163: if (freedma)
1164: dmafree(hs->sc_dq);
1165: /*
1166: * Initialize command block
1167: */
1168: bzero(&cdb, sizeof(cdb));
1169: cdb.lun = unit;
1170: cdb.lbam = (len >> 16) & 0xff;
1171: cdb.lbal = (len >> 8) & 0xff;
1172: cdb.len = len & 0xff;
1173: if (buf == 0) {
1174: cdb.cmd = CMD_SPACE;
1175: cdb.lun |= 0x00;
1176: len = 0;
1177: iphase = MESG_IN_PHASE;
1178: } else if (b_flags & B_READ) {
1179: cdb.cmd = CMD_READ;
1180: iphase = DATA_IN_PHASE;
1181: } else {
1182: cdb.cmd = CMD_WRITE;
1183: iphase = DATA_OUT_PHASE;
1184: }
1185: /*
1186: * Perform command (with very long delays)
1187: */
1188: scsi_delay(30000000);
1189: stat = scsiicmd(hs, slave, &cdb, sizeof(cdb), buf, len, iphase);
1190: scsi_delay(0);
1191: return (stat);
1192: }
1193: #endif
1194: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.