scsi_base.c revision 1.6 1 /*
2 * Written by Julian Elischer (julian (at) dialix.oz.au)
3 * $Id: scsi_base.c,v 1.6 1994/02/01 20:05:19 mycroft Exp $
4 */
5
6 #include <sys/types.h>
7 #include <sys/param.h>
8 #include <sys/buf.h>
9 #include <sys/uio.h>
10 #include <sys/malloc.h>
11 #include <sys/errno.h>
12 #include <sys/device.h>
13
14 #include <scsi/scsi_all.h>
15 #include <scsi/scsi_disk.h>
16 #include <scsi/scsiconf.h>
17
18 #ifdef DDB
19 int Debugger();
20 #else /* DDB */
21 #define Debugger()
22 #endif /* DDB */
23
24 void sc_print_addr __P((struct scsi_link *sc_link));
25
26 struct scsi_xfer *next_free_xs;
27
28 /*
29 * Get a scsi transfer structure for the caller. Charge the structure
30 * to the device that is referenced by the sc_link structure. If the
31 * sc_link structure has no 'credits' then the device already has the
32 * maximum number or outstanding operations under way. In this stage,
33 * wait on the structure so that when one is freed, we are awoken again
34 * If the SCSI_NOSLEEP flag is set, then do not wait, but rather, return
35 * a NULL pointer, signifying that no slots were available
36 * Note in the link structure, that we are waiting on it.
37 */
38
39 struct scsi_xfer *
40 get_xs(sc_link, flags)
41 struct scsi_link *sc_link; /* who to charge the xs to */
42 u_int32 flags; /* if this call can sleep */
43 {
44 struct scsi_xfer *xs;
45 u_int32 s;
46
47 SC_DEBUG(sc_link, SDEV_DB3, ("get_xs\n"));
48 s = splbio();
49 while (!sc_link->opennings) {
50 SC_DEBUG(sc_link, SDEV_DB3, ("sleeping\n"));
51 if (flags & SCSI_NOSLEEP) {
52 splx(s);
53 return 0;
54 }
55 sc_link->flags |= SDEV_WAITING;
56 (void) tsleep(sc_link, PRIBIO, "get_xs", 0);
57 }
58 sc_link->opennings--;
59 if (xs = next_free_xs) {
60 next_free_xs = xs->next;
61 splx(s);
62 } else {
63 splx(s);
64 SC_DEBUG(sc_link, SDEV_DB3, ("making\n"));
65 xs = malloc(sizeof(*xs), M_TEMP,
66 ((flags & SCSI_NOSLEEP) ? M_NOWAIT : M_WAITOK));
67 if (xs == NULL) {
68 sc_print_addr(sc_link);
69 printf("cannot allocate scsi xs\n");
70 return (NULL);
71 }
72 }
73 SC_DEBUG(sc_link, SDEV_DB3, ("returning\n"));
74 xs->sc_link = sc_link;
75 return (xs);
76 }
77
78 /*
79 * Given a scsi_xfer struct, and a device (referenced through sc_link)
80 * return the struct to the free pool and credit the device with it
81 * If another process is waiting for an xs, do a wakeup, let it proceed
82 */
83 void
84 free_xs(xs, sc_link, flags)
85 struct scsi_xfer *xs;
86 struct scsi_link *sc_link; /* who to credit for returning it */
87 u_int32 flags;
88 {
89 xs->next = next_free_xs;
90 next_free_xs = xs;
91
92 SC_DEBUG(sc_link, SDEV_DB3, ("free_xs\n"));
93 /* if was 0 and someone waits, wake them up */
94 if ((!sc_link->opennings++) && (sc_link->flags & SDEV_WAITING)) {
95 sc_link->flags &= ~SDEV_WAITING;
96 wakeup(sc_link); /* remember, it wakes them ALL up */
97 } else {
98 if (sc_link->device->start) {
99 SC_DEBUG(sc_link, SDEV_DB2, ("calling private start()\n"));
100 (*(sc_link->device->start)) (sc_link->dev_unit);
101 }
102 }
103 }
104
105 /*
106 * Find out from the device what its capacity is.
107 */
108 u_int32
109 scsi_size(sc_link, flags)
110 struct scsi_link *sc_link;
111 u_int32 flags;
112 {
113 struct scsi_read_cap_data rdcap;
114 struct scsi_read_capacity scsi_cmd;
115 u_int32 size;
116
117 /*
118 * make up a scsi command and ask the scsi driver to do
119 * it for you.
120 */
121 bzero(&scsi_cmd, sizeof(scsi_cmd));
122 scsi_cmd.op_code = READ_CAPACITY;
123
124 /*
125 * If the command works, interpret the result as a 4 byte
126 * number of blocks
127 */
128 if (scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
129 sizeof(scsi_cmd), (u_char *) & rdcap, sizeof(rdcap),
130 2, 20000, NULL, flags | SCSI_DATA_IN) != 0) {
131 sc_print_addr(sc_link);
132 printf("could not get size\n");
133 return (0);
134 } else {
135 size = rdcap.addr_0 + 1;
136 size += rdcap.addr_1 << 8;
137 size += rdcap.addr_2 << 16;
138 size += rdcap.addr_3 << 24;
139 }
140 return (size);
141 }
142
143 /*
144 * Get scsi driver to send a "are you ready?" command
145 */
146 int
147 scsi_test_unit_ready(sc_link, flags)
148 struct scsi_link *sc_link;
149 u_int32 flags;
150 {
151 struct scsi_test_unit_ready scsi_cmd;
152
153 bzero(&scsi_cmd, sizeof(scsi_cmd));
154 scsi_cmd.op_code = TEST_UNIT_READY;
155
156 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
157 sizeof(scsi_cmd), 0, 0, 2, 100000, NULL, flags);
158 }
159
160 /*
161 * Do a scsi operation, asking a device to run as SCSI-II if it can.
162 */
163 int
164 scsi_change_def(sc_link, flags)
165 struct scsi_link *sc_link;
166 u_int32 flags;
167 {
168 struct scsi_changedef scsi_cmd;
169
170 bzero(&scsi_cmd, sizeof(scsi_cmd));
171 scsi_cmd.op_code = CHANGE_DEFINITION;
172 scsi_cmd.how = SC_SCSI_2;
173
174 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
175 sizeof(scsi_cmd), 0, 0, 2, 100000, NULL, flags);
176 }
177
178 /*
179 * Do a scsi operation asking a device what it is
180 * Use the scsi_cmd routine in the switch table.
181 */
182 int
183 scsi_inquire(sc_link, inqbuf, flags)
184 struct scsi_link *sc_link;
185 struct scsi_inquiry_data *inqbuf;
186 u_int32 flags;
187 {
188 struct scsi_inquiry scsi_cmd;
189
190 bzero(&scsi_cmd, sizeof(scsi_cmd));
191 scsi_cmd.op_code = INQUIRY;
192 scsi_cmd.length = sizeof(struct scsi_inquiry_data);
193
194 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
195 sizeof(scsi_cmd), (u_char *) inqbuf,
196 sizeof(struct scsi_inquiry_data), 2, 100000, NULL,
197 SCSI_DATA_IN | flags);
198 }
199
200 /*
201 * Prevent or allow the user to remove the media
202 */
203 int
204 scsi_prevent(sc_link, type, flags)
205 struct scsi_link *sc_link;
206 u_int32 type, flags;
207 {
208 struct scsi_prevent scsi_cmd;
209
210 bzero(&scsi_cmd, sizeof(scsi_cmd));
211 scsi_cmd.op_code = PREVENT_ALLOW;
212 scsi_cmd.how = type;
213 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
214 sizeof(scsi_cmd), 0, 0, 2, 5000, NULL, flags);
215 }
216
217 /*
218 * Get scsi driver to send a "start up" command
219 */
220 int
221 scsi_start_unit(sc_link, flags)
222 struct scsi_link *sc_link;
223 u_int32 flags;
224 {
225 struct scsi_start_stop scsi_cmd;
226
227 bzero(&scsi_cmd, sizeof(scsi_cmd));
228 scsi_cmd.op_code = START_STOP;
229 scsi_cmd.how = SSS_START;
230
231 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
232 sizeof(scsi_cmd), 0, 0, 2, 2000, NULL, flags);
233 }
234
235 /*
236 * Get scsi driver to send a "stop" command
237 */
238 int
239 scsi_stop_unit(sc_link, eject, flags)
240 struct scsi_link *sc_link;
241 u_int32 eject;
242 u_int32 flags;
243 {
244 struct scsi_start_stop scsi_cmd;
245
246 bzero(&scsi_cmd, sizeof(scsi_cmd));
247 scsi_cmd.op_code = START_STOP;
248 if (eject)
249 scsi_cmd.how = SSS_LOEJ;
250 else
251 scsi_cmd.how = SSS_STOP;
252
253 return scsi_scsi_cmd(sc_link, (struct scsi_generic *) &scsi_cmd,
254 sizeof(scsi_cmd), 0, 0, 2, 2000, NULL, flags);
255 }
256
257 /*
258 * This routine is called by the scsi interrupt when the transfer is complete.
259 */
260 void
261 scsi_done(xs)
262 struct scsi_xfer *xs;
263 {
264 struct scsi_link *sc_link = xs->sc_link;
265 struct buf *bp = xs->bp;
266 int retval;
267
268 SC_DEBUG(sc_link, SDEV_DB2, ("scsi_done\n"));
269 #ifdef SCSIDEBUG
270 if (sc_link->flags & SDEV_DB1)
271 show_scsi_cmd(xs);
272 #endif /*SCSIDEBUG */
273 /*
274 * If it's a user level request, bypass all usual completion processing,
275 * let the user work it out.. We take reponsibility for freeing the
276 * xs when the user returns. (and restarting the device's queue).
277 */
278 if (xs->flags & SCSI_USER) {
279 biodone(xs->bp);
280 #ifdef NOTNOW
281 SC_DEBUG(sc_link, SDEV_DB3, ("calling user done()\n"));
282 scsi_user_done(xs); /* to take a copy of the sense etc. */
283 SC_DEBUG(sc_link, SDEV_DB3, ("returned from user done()\n "));
284 #endif
285 free_xs(xs, sc_link, SCSI_NOSLEEP); /* restarts queue too */
286 SC_DEBUG(sc_link, SDEV_DB3, ("returning to adapter\n"));
287 return;
288 }
289 /*
290 * If the device has it's own done routine, call it first.
291 * If it returns a legit error value, return that, otherwise
292 * it wants us to continue with normal processing.
293 */
294
295 if (sc_link->device->done) {
296 SC_DEBUG(sc_link, SDEV_DB2, ("calling private done()\n"));
297 retval = (*sc_link->device->done) (xs);
298 if (retval == -1) {
299 free_xs(xs, sc_link, SCSI_NOSLEEP); /*XXX */
300 return; /* it did it all, finish up */
301 }
302 if (retval == -2)
303 return; /* it did it all, finish up */
304 SC_DEBUG(sc_link, SDEV_DB3, ("continuing with generic done()\n"));
305 }
306 if ((bp = xs->bp) == NULL) {
307 /*
308 * if it's a normal upper level request, then ask
309 * the upper level code to handle error checking
310 * rather than doing it here at interrupt time
311 */
312 wakeup(xs);
313 return;
314 }
315 /*
316 * Go and handle errors now.
317 * If it returns -1 then we should RETRY
318 */
319 if ((retval = sc_err1(xs)) == -1) {
320 if ((*(sc_link->adapter->scsi_cmd)) (xs)
321 == SUCCESSFULLY_QUEUED) /* don't wake the job, ok? */
322 return;
323 xs->flags |= ITSDONE;
324 }
325 free_xs(xs, sc_link, SCSI_NOSLEEP); /* does a start if needed */
326 biodone(bp);
327 }
328
329 /*
330 * ask the scsi driver to perform a command for us.
331 * tell it where to read/write the data, and how
332 * long the data is supposed to be. If we have a buf
333 * to associate with the transfer, we need that too.
334 */
335 int
336 scsi_scsi_cmd(sc_link, scsi_cmd, cmdlen, data_addr, datalen,
337 retries, timeout, bp, flags)
338 struct scsi_link *sc_link;
339 struct scsi_generic *scsi_cmd;
340 u_int32 cmdlen;
341 u_char *data_addr;
342 u_int32 datalen;
343 u_int32 retries;
344 u_int32 timeout;
345 struct buf *bp;
346 u_int32 flags;
347 {
348 struct scsi_xfer *xs;
349 int retval;
350 u_int32 s;
351
352 if (bp)
353 flags |= SCSI_NOSLEEP;
354 SC_DEBUG(sc_link, SDEV_DB2, ("scsi_cmd\n"));
355
356 xs = get_xs(sc_link, flags); /* should wait unless booting */
357 if (!xs)
358 return (ENOMEM);
359 /*
360 * Fill out the scsi_xfer structure. We don't know whose context
361 * the cmd is in, so copy it.
362 */
363 bcopy(scsi_cmd, &(xs->cmdstore), cmdlen);
364 xs->flags = INUSE | flags;
365 xs->sc_link = sc_link;
366 xs->retries = retries;
367 xs->timeout = timeout;
368 xs->cmd = &xs->cmdstore;
369 xs->cmdlen = cmdlen;
370 xs->data = data_addr;
371 xs->datalen = datalen;
372 xs->resid = datalen;
373 xs->bp = bp;
374 /*XXX*/ /*use constant not magic number */
375 if (datalen && ((caddr_t) data_addr < (caddr_t) KERNBASE)) {
376 if (bp) {
377 printf("Data buffered space not in kernel context\n");
378 #ifdef SCSIDEBUG
379 show_scsi_cmd(xs);
380 #endif /* SCSIDEBUG */
381 retval = EFAULT;
382 goto bad;
383 }
384 xs->data = malloc(datalen, M_TEMP, M_WAITOK);
385 /* I think waiting is ok *//*XXX */
386 switch (flags & (SCSI_DATA_IN | SCSI_DATA_OUT)) {
387 case 0:
388 printf("No direction flags, assuming both\n");
389 #ifdef SCSIDEBUG
390 show_scsi_cmd(xs);
391 #endif /* SCSIDEBUG */
392 case SCSI_DATA_IN | SCSI_DATA_OUT: /* weird */
393 case SCSI_DATA_OUT:
394 bcopy(data_addr, xs->data, datalen);
395 break;
396 case SCSI_DATA_IN:
397 bzero(xs->data, datalen);
398 }
399 }
400 retry:
401 xs->error = XS_NOERROR;
402 #ifdef PARANOID
403 if (datalen && ((caddr_t) xs->data < (caddr_t) KERNBASE))
404 printf("It's still wrong!\n");
405 #endif /*PARANOID*/
406 #ifdef SCSIDEBUG
407 if (sc_link->flags & SDEV_DB3)
408 show_scsi_xs(xs);
409 #endif /* SCSIDEBUG */
410 /*
411 * Do the transfer. If we are polling we will return:
412 * COMPLETE, Was poll, and scsi_done has been called
413 * TRY_AGAIN_LATER, Adapter short resources, try again
414 *
415 * if under full steam (interrupts) it will return:
416 * SUCCESSFULLY_QUEUED, will do a wakeup when complete
417 * TRY_AGAIN_LATER, (as for polling)
418 * After the wakeup, we must still check if it succeeded
419 *
420 * If we have a bp however, all the error proccessing
421 * and the buffer code both expect us to return straight
422 * to them, so as soon as the command is queued, return
423 */
424
425 retval = (*(sc_link->adapter->scsi_cmd)) (xs);
426
427 switch (retval) {
428 case SUCCESSFULLY_QUEUED:
429 if (bp)
430 return retval; /* will sleep (or not) elsewhere */
431 s = splbio();
432 while (!(xs->flags & ITSDONE))
433 tsleep(xs, PRIBIO + 1, "scsi_scsi_cmd", 0);
434 splx(s);
435 /* fall through to check success of completed command */
436 case COMPLETE: /* Polling command completed ok */
437 /*XXX*/ case HAD_ERROR: /* Polling command completed with error */
438 SC_DEBUG(sc_link, SDEV_DB3, ("back in cmd()\n"));
439 if ((retval = sc_err1(xs)) == -1)
440 goto retry;
441 break;
442
443 case TRY_AGAIN_LATER: /* adapter resource shortage */
444 SC_DEBUG(sc_link, SDEV_DB3, ("will try again \n"));
445 /* should sleep 1 sec here */
446 if (xs->retries--) {
447 xs->flags &= ~ITSDONE;
448 goto retry;
449 }
450 default:
451 retval = EIO;
452 }
453 /*
454 * If we had to copy the data out of the user's context,
455 * then do the other half (copy it back or whatever)
456 * and free the memory buffer
457 */
458 if (datalen && (xs->data != data_addr)) {
459 switch (flags & (SCSI_DATA_IN | SCSI_DATA_OUT)) {
460 case 0:
461 case SCSI_DATA_IN | SCSI_DATA_OUT: /* weird */
462 case SCSI_DATA_IN:
463 bcopy(xs->data, data_addr, datalen);
464 break;
465 }
466 free(xs->data, M_TEMP);
467 }
468 /*
469 * we have finished with the xfer stuct, free it and
470 * check if anyone else needs to be started up.
471 */
472 bad:
473 free_xs(xs, sc_link, flags); /* includes the 'start' op */
474 if (bp && retval) {
475 bp->b_error = retval;
476 bp->b_flags |= B_ERROR;
477 biodone(bp);
478 }
479 return (retval);
480 }
481
482 int
483 sc_err1(xs)
484 struct scsi_xfer *xs;
485 {
486 struct buf *bp = xs->bp;
487 int retval;
488
489 SC_DEBUG(xs->sc_link, SDEV_DB3, ("sc_err1,err = 0x%x \n", xs->error));
490 /*
491 * If it has a buf, we might be working with
492 * a request from the buffer cache or some other
493 * piece of code that requires us to process
494 * errors at inetrrupt time. We have probably
495 * been called by scsi_done()
496 */
497 switch (xs->error) {
498 case XS_NOERROR: /* nearly always hit this one */
499 retval = 0;
500 if (bp) {
501 bp->b_error = 0;
502 bp->b_resid = 0;
503 }
504 break;
505
506 case XS_SENSE:
507 if (bp) {
508 bp->b_error = 0;
509 bp->b_resid = 0;
510 if (retval = (scsi_interpret_sense(xs))) {
511 bp->b_flags |= B_ERROR;
512 bp->b_error = retval;
513 bp->b_resid = bp->b_bcount;
514 }
515 SC_DEBUG(xs->sc_link, SDEV_DB3,
516 ("scsi_interpret_sense (bp) returned %d\n", retval));
517 } else {
518 retval = (scsi_interpret_sense(xs));
519 SC_DEBUG(xs->sc_link, SDEV_DB3,
520 ("scsi_interpret_sense (no bp) returned %d\n", retval));
521 }
522 break;
523
524 case XS_BUSY:
525 /*should somehow arange for a 1 sec delay here (how?) */
526 case XS_TIMEOUT:
527 /*
528 * If we can, resubmit it to the adapter.
529 */
530 if (xs->retries--) {
531 xs->error = XS_NOERROR;
532 xs->flags &= ~ITSDONE;
533 goto retry;
534 }
535 /* fall through */
536 case XS_DRIVER_STUFFUP:
537 if (bp) {
538 bp->b_flags |= B_ERROR;
539 bp->b_error = EIO;
540 }
541 retval = EIO;
542 break;
543 default:
544 retval = EIO;
545 sc_print_addr(xs->sc_link);
546 printf("unknown error category from scsi driver\n");
547 }
548 return retval;
549 retry:
550 return (-1);
551 }
552
553 /*
554 * Look at the returned sense and act on the error, determining
555 * the unix error number to pass back. (0 = report no error)
556 *
557 * THIS IS THE DEFAULT ERROR HANDLER
558 */
559 int
560 scsi_interpret_sense(xs)
561 struct scsi_xfer *xs;
562 {
563 struct scsi_sense_data *sense;
564 struct scsi_link *sc_link = xs->sc_link;
565 u_int32 key;
566 u_int32 silent;
567 u_int32 info;
568 int error;
569
570 static char *error_mes[] =
571 {"soft error (corrected)",
572 "not ready", "medium error",
573 "non-media hardware failure", "illegal request",
574 "unit attention", "readonly device",
575 "no data found", "vendor unique",
576 "copy aborted", "command aborted",
577 "search returned equal", "volume overflow",
578 "verify miscompare", "unknown error key"
579 };
580
581 /*
582 * If the flags say errs are ok, then always return ok.
583 */
584 if (xs->flags & SCSI_ERR_OK)
585 return (0);
586
587 sense = &(xs->sense);
588 #ifdef SCSIDEBUG
589 if (sc_link->flags & SDEV_DB1) {
590 u_int32 count = 0;
591 printf("code%x valid%x ",
592 sense->error_code & SSD_ERRCODE,
593 sense->error_code & SSD_ERRCODE_VALID ? 1 : 0);
594 printf("seg%x key%x ili%x eom%x fmark%x\n",
595 sense->ext.extended.segment,
596 sense->ext.extended.flags & SSD_KEY,
597 sense->ext.extended.flags & SSD_ILI ? 1 : 0,
598 sense->ext.extended.flags & SSD_EOM ? 1 : 0,
599 sense->ext.extended.flags & SSD_FILEMARK ? 1 : 0);
600 printf("info: %x %x %x %x followed by %d extra bytes\n",
601 sense->ext.extended.info[0],
602 sense->ext.extended.info[1],
603 sense->ext.extended.info[2],
604 sense->ext.extended.info[3],
605 sense->ext.extended.extra_len);
606 printf("extra: ");
607 while (count < sense->ext.extended.extra_len)
608 printf("%x ", sense->ext.extended.extra_bytes[count++]);
609 printf("\n");
610 }
611 #endif /*SCSIDEBUG */
612 /*
613 * If the device has it's own error handler, call it first.
614 * If it returns a legit error value, return that, otherwise
615 * it wants us to continue with normal error processing.
616 */
617 if (sc_link->device->err_handler) {
618 SC_DEBUG(sc_link, SDEV_DB2, ("calling private err_handler()\n"));
619 error = (*sc_link->device->err_handler) (xs);
620 if (error != -1)
621 return error; /* error >= 0 better ? */
622 }
623 /* otherwise use the default */
624 silent = (xs->flags & SCSI_SILENT);
625 switch (sense->error_code & SSD_ERRCODE) {
626 /*
627 * If it's code 70, use the extended stuff and interpret the key
628 */
629 case 0x71: /* delayed error */
630 sc_print_addr(sc_link);
631 key = sense->ext.extended.flags & SSD_KEY;
632 printf(" DELAYED ERROR, key = 0x%x\n", key);
633 case 0x70:
634 if (sense->error_code & SSD_ERRCODE_VALID)
635 info = ntohl(*((long *) sense->ext.extended.info));
636 else
637 info = 0;
638 key = sense->ext.extended.flags & SSD_KEY;
639
640 if (key && !silent) {
641 sc_print_addr(sc_link);
642 printf("%s", error_mes[key - 1]);
643 if (sense->error_code & SSD_ERRCODE_VALID) {
644 switch (key) {
645 case 0x2: /* NOT READY */
646 case 0x5: /* ILLEGAL REQUEST */
647 case 0x6: /* UNIT ATTENTION */
648 case 0x7: /* DATA PROTECT */
649 break;
650 case 0x8: /* BLANK CHECK */
651 printf(", requested size: %d (decimal)",
652 info);
653 break;
654 default:
655 printf(", info = %d (decimal)", info);
656 }
657 }
658 printf("\n");
659 }
660 switch (key) {
661 case 0x0: /* NO SENSE */
662 case 0x1: /* RECOVERED ERROR */
663 if (xs->resid == xs->datalen)
664 xs->resid = 0; /* not short read */
665 case 0xc: /* EQUAL */
666 return (0);
667 case 0x2: /* NOT READY */
668 sc_link->flags &= ~SDEV_MEDIA_LOADED;
669 return (EBUSY);
670 case 0x5: /* ILLEGAL REQUEST */
671 return (EINVAL);
672 case 0x6: /* UNIT ATTENTION */
673 sc_link->flags &= ~SDEV_MEDIA_LOADED;
674 if (sc_link->flags & SDEV_OPEN)
675 return (EIO);
676 else
677 return 0;
678 case 0x7: /* DATA PROTECT */
679 return (EACCES);
680 case 0xd: /* VOLUME OVERFLOW */
681 return (ENOSPC);
682 case 0x8: /* BLANK CHECK */
683 return (0);
684 default:
685 return (EIO);
686 }
687 /*
688 * Not code 70, just report it
689 */
690 default:
691 if (!silent) {
692 sc_print_addr(sc_link);
693 printf("error code %d",
694 sense->error_code & SSD_ERRCODE);
695 if (sense->error_code & SSD_ERRCODE_VALID) {
696 printf(" at block no. %d (decimal)",
697 (sense->ext.unextended.blockhi << 16) +
698 (sense->ext.unextended.blockmed << 8) +
699 (sense->ext.unextended.blocklow));
700 }
701 printf("\n");
702 }
703 return (EIO);
704 }
705 }
706
707 /*
708 * Utility routines often used in SCSI stuff
709 */
710
711 /*
712 * convert a physical address to 3 bytes,
713 * MSB at the lowest address,
714 * LSB at the highest.
715 */
716 void
717 lto3b(val, bytes)
718 int val;
719 u_char *bytes;
720 {
721 *bytes++ = (val & 0xff0000) >> 16;
722 *bytes++ = (val & 0xff00) >> 8;
723 *bytes = val & 0xff;
724 }
725
726 /*
727 * The reverse of lto3b
728 */
729 int
730 _3btol(bytes)
731 u_char *bytes;
732 {
733 u_int32 rc;
734 rc = (*bytes++ << 16);
735 rc += (*bytes++ << 8);
736 rc += *bytes;
737 return ((int) rc);
738 }
739
740 /*
741 * Print out the scsi_link structure's address info.
742 */
743 void
744 sc_print_addr(sc_link)
745 struct scsi_link *sc_link;
746 {
747
748 printf("%s%d(%s:%d:%d): ",
749 sc_link->device->name, sc_link->dev_unit,
750 ((struct device *)sc_link->adapter_softc)->dv_xname,
751 sc_link->target, sc_link->lun);
752 }
753
754 #ifdef SCSIDEBUG
755 /*
756 * Given a scsi_xfer, dump the request, in all it's glory
757 */
758 void
759 show_scsi_xs(xs)
760 struct scsi_xfer *xs;
761 {
762 printf("xs(0x%x): ", xs);
763 printf("flg(0x%x)", xs->flags);
764 printf("sc_link(0x%x)", xs->sc_link);
765 printf("retr(0x%x)", xs->retries);
766 printf("timo(0x%x)", xs->timeout);
767 printf("cmd(0x%x)", xs->cmd);
768 printf("len(0x%x)", xs->cmdlen);
769 printf("data(0x%x)", xs->data);
770 printf("len(0x%x)", xs->datalen);
771 printf("res(0x%x)", xs->resid);
772 printf("err(0x%x)", xs->error);
773 printf("bp(0x%x)", xs->bp);
774 show_scsi_cmd(xs);
775 }
776
777 void
778 show_scsi_cmd(struct scsi_xfer *xs)
779 {
780 u_char *b = (u_char *) xs->cmd;
781 int i = 0;
782
783 sc_print_addr(xs->sc_link);
784 printf("command: ");
785
786 if (!(xs->flags & SCSI_RESET)) {
787 while (i < xs->cmdlen) {
788 if (i)
789 printf(",");
790 printf("%x", b[i++]);
791 }
792 printf("-[%d bytes]\n", xs->datalen);
793 if (xs->datalen)
794 show_mem(xs->data, min(64, xs->datalen));
795 } else
796 printf("-RESET-\n");
797 }
798
799 void
800 show_mem(address, num)
801 unsigned char *address;
802 u_int32 num;
803 {
804 u_int32 x, y;
805 printf("------------------------------");
806 for (y = 0; y < num; y += 1) {
807 if (!(y % 16))
808 printf("\n%03d: ", y);
809 printf("%02x ", *address++);
810 }
811 printf("\n------------------------------\n");
812 }
813 #endif /*SCSIDEBUG */
814