1/* $NetBSD: sci.c,v 1.33 2005/11/26 13:54:18 tsutsui Exp $ */ 2 3/* 4 * Copyright (c) 1990 The Regents of the University of California. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to Berkeley by 8 * Van Jacobson of Lawrence Berkeley Laboratory. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 3. Neither the name of the University nor the names of its contributors 19 * may be used to endorse or promote products derived from this software 20 * without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 25 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 32 * SUCH DAMAGE. 33 * 34 * @(#)scsi.c 7.5 (Berkeley) 5/4/91 35 */ 36 37/* 38 * Copyright (c) 1994 Michael L. Hitch 39 * 40 * This code is derived from software contributed to Berkeley by 41 * Van Jacobson of Lawrence Berkeley Laboratory. 42 * 43 * Redistribution and use in source and binary forms, with or without 44 * modification, are permitted provided that the following conditions 45 * are met: 46 * 1. Redistributions of source code must retain the above copyright 47 * notice, this list of conditions and the following disclaimer. 48 * 2. Redistributions in binary form must reproduce the above copyright 49 * notice, this list of conditions and the following disclaimer in the 50 * documentation and/or other materials provided with the distribution. 51 * 52 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 53 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 54 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 55 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 56 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 57 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 58 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 59 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 60 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 61 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 62 * 63 * @(#)scsi.c 7.5 (Berkeley) 5/4/91 64 */ 65 66/* 67 * AMIGA NCR 5380 scsi adaptor driver 68 */ 69 70#include <sys/cdefs.h> 71__KERNEL_RCSID(0, "$NetBSD: sci.c,v 1.33 2005/11/26 13:54:18 tsutsui Exp $"); 72 73#include <sys/param.h> 74#include <sys/systm.h> 75#include <sys/device.h> 76#include <sys/disklabel.h> 77#include <sys/buf.h> 78#include <dev/scsipi/scsi_all.h> 79#include <dev/scsipi/scsipi_all.h> 80#include <dev/scsipi/scsiconf.h> 81#include <machine/cpu.h> 82#include <amiga/amiga/device.h> 83#include <amiga/amiga/custom.h> 84#include <amiga/amiga/isr.h> 85#include <amiga/dev/scireg.h> 86#include <amiga/dev/scivar.h> 87 88/* 89 * SCSI delays 90 * In u-seconds, primarily for state changes on the SPC. 91 */ 92#define SCI_CMD_WAIT 50000 /* wait per step of 'immediate' cmds */ 93#define SCI_DATA_WAIT 50000 /* wait per data in/out step */ 94#define SCI_INIT_WAIT 50000 /* wait per step (both) during init */ 95 96int sciicmd(struct sci_softc *, int, void *, int, void *, int,u_char); 97int scigo(struct sci_softc *, struct scsipi_xfer *); 98int sciselectbus(struct sci_softc *, u_char, u_char); 99void sciabort(struct sci_softc *, const char *); 100void scierror(struct sci_softc *, u_char); 101void scisetdelay(int); 102void sci_scsidone(struct sci_softc *, int); 103void sci_donextcmd(struct sci_softc *); 104int sci_ixfer_out(struct sci_softc *, int, register u_char *, int); 105void sci_ixfer_in(struct sci_softc *, int, register u_char *, int); 106 107int sci_cmd_wait = SCI_CMD_WAIT; 108int sci_data_wait = SCI_DATA_WAIT; 109int sci_init_wait = SCI_INIT_WAIT; 110 111int sci_no_dma = 0; 112 113#ifdef DEBUG 114#define QPRINTF(a) if (sci_debug > 1) printf a 115int sci_debug = 0; 116#else 117#define QPRINTF(a) 118#endif 119 120/* 121 * default minphys routine for sci based controllers 122 */ 123void 124sci_minphys(struct buf *bp) 125{ 126 127 /* 128 * No max transfer at this level. 129 */ 130 minphys(bp); 131} 132 133/* 134 * used by specific sci controller 135 * 136 * it appears that the higher level code does nothing with LUN's 137 * so I will too. I could plug it in, however so could they 138 * in scsi_scsipi_cmd(). 139 */ 140void 141sci_scsipi_request(struct scsipi_channel *chan, scsipi_adapter_req_t req, 142 void *arg) 143{ 144 struct scsipi_xfer *xs; 145 struct scsipi_periph *periph; 146 struct sci_softc *dev = (void *)chan->chan_adapter->adapt_dev; 147 int flags, s; 148 149 switch (req) { 150 case ADAPTER_REQ_RUN_XFER: 151 xs = arg; 152 periph = xs->xs_periph; 153 flags = xs->xs_control; 154 155 if (flags & XS_CTL_DATA_UIO) 156 panic("sci: scsi data uio requested"); 157 158 s = splbio(); 159 160 if (dev->sc_xs && flags & XS_CTL_POLL) 161 panic("sci_scsicmd: busy"); 162 163#ifdef DIAGNOSTIC 164 /* 165 * This should never happen as we track the resources 166 * in the mid-layer. 167 */ 168 if (dev->sc_xs) { 169 scsipi_printaddr(periph); 170 printf("unable to allocate scb\n"); 171 panic("sea_scsipi_request"); 172 } 173#endif 174 175 dev->sc_xs = xs; 176 splx(s); 177 178 /* 179 * nothing is pending do it now. 180 */ 181 sci_donextcmd(dev); 182 183 return; 184 185 case ADAPTER_REQ_GROW_RESOURCES: 186 return; 187 188 case ADAPTER_REQ_SET_XFER_MODE: 189 return; 190 } 191} 192 193/* 194 * entered with dev->sc_xs pointing to the next xfer to perform 195 */ 196void 197sci_donextcmd(struct sci_softc *dev) 198{ 199 struct scsipi_xfer *xs; 200 struct scsipi_periph *periph; 201 int flags, phase, stat; 202 203 xs = dev->sc_xs; 204 periph = xs->xs_periph; 205 flags = xs->xs_control; 206 207 if (flags & XS_CTL_DATA_IN) 208 phase = DATA_IN_PHASE; 209 else if (flags & XS_CTL_DATA_OUT) 210 phase = DATA_OUT_PHASE; 211 else 212 phase = STATUS_PHASE; 213 214 if (flags & XS_CTL_RESET) 215 scireset(dev); 216 217 dev->sc_stat[0] = -1; 218 xs->cmd->bytes[0] |= periph->periph_lun << 5; 219 if (phase == STATUS_PHASE || flags & XS_CTL_POLL) 220 stat = sciicmd(dev, periph->periph_target, xs->cmd, xs->cmdlen, 221 xs->data, xs->datalen, phase); 222 else if (scigo(dev, xs) == 0) 223 return; 224 else 225 stat = dev->sc_stat[0]; 226 227 sci_scsidone(dev, stat); 228} 229 230void 231sci_scsidone(struct sci_softc *dev, int stat) 232{ 233 struct scsipi_xfer *xs; 234 235 xs = dev->sc_xs; 236#ifdef DIAGNOSTIC 237 if (xs == NULL) 238 panic("sci_scsidone"); 239#endif 240 xs->status = stat; 241 if (stat == 0) 242 xs->resid = 0; 243 else { 244 switch(stat) { 245 case SCSI_CHECK: 246 xs->resid = 0; 247 /* FALLTHROUGH */ 248 case SCSI_BUSY: 249 xs->error = XS_BUSY; 250 break; 251 default: 252 xs->error = XS_DRIVER_STUFFUP; 253 QPRINTF(("sci_scsicmd() bad %x\n", stat)); 254 break; 255 } 256 } 257 258 scsipi_done(xs); 259 260} 261 262void 263sciabort(struct sci_softc *dev, const char *where) 264{ 265 printf ("%s: abort %s: csr = 0x%02x, bus = 0x%02x\n", 266 dev->sc_dev.dv_xname, where, *dev->sci_csr, *dev->sci_bus_csr); 267 268 if (dev->sc_flags & SCI_SELECTED) { 269 270 /* lets just hope it worked.. */ 271 dev->sc_flags &= ~SCI_SELECTED; 272 /* XXX */ 273 scireset (dev); 274 } 275} 276 277/* 278 * XXX Set/reset long delays. 279 * 280 * if delay == 0, reset default delays 281 * if delay < 0, set both delays to default long initialization values 282 * if delay > 0, set both delays to this value 283 * 284 * Used when a devices is expected to respond slowly (e.g. during 285 * initialization). 286 */ 287void 288scisetdelay(int del) 289{ 290 static int saved_cmd_wait, saved_data_wait; 291 292 if (del) { 293 saved_cmd_wait = sci_cmd_wait; 294 saved_data_wait = sci_data_wait; 295 if (del > 0) 296 sci_cmd_wait = sci_data_wait = del; 297 else 298 sci_cmd_wait = sci_data_wait = sci_init_wait; 299 } else { 300 sci_cmd_wait = saved_cmd_wait; 301 sci_data_wait = saved_data_wait; 302 } 303} 304 305void 306scireset(struct sci_softc *dev) 307{ 308 u_int s; 309 u_char my_id; 310 311 dev->sc_flags &= ~SCI_SELECTED; 312 if (dev->sc_flags & SCI_ALIVE) 313 sciabort(dev, "reset"); 314 315 printf("%s: ", dev->sc_dev.dv_xname); 316 317 s = splbio(); 318 /* preserve our ID for now */ 319 my_id = 7; 320 321 /* 322 * Reset the chip 323 */ 324 *dev->sci_icmd = SCI_ICMD_TEST; 325 *dev->sci_icmd = SCI_ICMD_TEST | SCI_ICMD_RST; 326 delay (25); 327 *dev->sci_icmd = 0; 328 329 /* 330 * Set up various chip parameters 331 */ 332 *dev->sci_icmd = 0; 333 *dev->sci_tcmd = 0; 334 *dev->sci_sel_enb = 0; 335 336 /* anything else was zeroed by reset */ 337 338 splx (s); 339 340 printf("sci id %d\n", my_id); 341 dev->sc_flags |= SCI_ALIVE; 342} 343 344void 345scierror(struct sci_softc *dev, u_char csr) 346{ 347 struct scsipi_xfer *xs; 348 349 xs = dev->sc_xs; 350 351#ifdef DIAGNOSTIC 352 if (xs == NULL) 353 panic("scierror"); 354#endif 355 if (xs->xs_control & XS_CTL_SILENT) 356 return; 357 358 printf("%s: ", dev->sc_dev.dv_xname); 359 printf("csr == 0x%02i\n", csr); /* XXX */ 360} 361 362/* 363 * select the bus, return when selected or error. 364 */ 365int 366sciselectbus(struct sci_softc *dev, u_char target, u_char our_addr) 367{ 368 register int timeo = 2500; 369 370 QPRINTF (("sciselectbus %d\n", target)); 371 372 /* if we're already selected, return */ 373 if (dev->sc_flags & SCI_SELECTED) /* XXXX */ 374 return 1; 375 376 if ((*dev->sci_bus_csr & (SCI_BUS_BSY|SCI_BUS_SEL)) && 377 (*dev->sci_bus_csr & (SCI_BUS_BSY|SCI_BUS_SEL)) && 378 (*dev->sci_bus_csr & (SCI_BUS_BSY|SCI_BUS_SEL))) 379 return 1; 380 381 *dev->sci_tcmd = 0; 382 *dev->sci_odata = 0x80 + (1 << target); 383 *dev->sci_icmd = SCI_ICMD_DATA|SCI_ICMD_SEL; 384 while ((*dev->sci_bus_csr & SCI_BUS_BSY) == 0) { 385 if (--timeo > 0) { 386 delay(100); 387 } else { 388 break; 389 } 390 } 391 if (timeo) { 392 *dev->sci_icmd = 0; 393 dev->sc_flags |= SCI_SELECTED; 394 return (0); 395 } 396 *dev->sci_icmd = 0; 397 return (1); 398} 399 400int 401sci_ixfer_out(register struct sci_softc *dev, int len, register u_char *buf, 402 int phase) 403{ 404 register int wait = sci_data_wait; 405 u_char csr; 406 407 QPRINTF(("sci_ixfer_out {%d} %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x\n", 408 len, buf[0], buf[1], buf[2], buf[3], buf[4], buf[5], 409 buf[6], buf[7], buf[8], buf[9])); 410 411 *dev->sci_tcmd = phase; 412 *dev->sci_icmd = SCI_ICMD_DATA; 413 for (;len > 0; len--) { 414 csr = *dev->sci_bus_csr; 415 while (!(csr & SCI_BUS_REQ)) { 416 if ((csr & SCI_BUS_BSY) == 0 || --wait < 0) { 417#ifdef DEBUG 418 if (sci_debug) 419 printf("sci_ixfer_out fail: l%d i%x w%d\n", 420 len, csr, wait); 421#endif 422 return (len); 423 } 424 delay(1); 425 csr = *dev->sci_bus_csr; 426 } 427 428 if (!(*dev->sci_csr & SCI_CSR_PHASE_MATCH)) 429 break; 430 *dev->sci_odata = *buf; 431 *dev->sci_icmd = SCI_ICMD_DATA|SCI_ICMD_ACK; 432 buf++; 433 while (*dev->sci_bus_csr & SCI_BUS_REQ); 434 *dev->sci_icmd = SCI_ICMD_DATA; 435 } 436 437 QPRINTF(("sci_ixfer_out done\n")); 438 return (0); 439} 440 441void 442sci_ixfer_in(struct sci_softc *dev, int len, register u_char *buf, int phase) 443{ 444 int wait = sci_data_wait; 445 u_char csr; 446 volatile register u_char *sci_bus_csr = dev->sci_bus_csr; 447 volatile register u_char *sci_data = dev->sci_data; 448 volatile register u_char *sci_icmd = dev->sci_icmd; 449#ifdef DEBUG 450 u_char *obp = buf; 451#endif 452 453 csr = *sci_bus_csr; 454 455 QPRINTF(("sci_ixfer_in %d, csr=%02x\n", len, csr)); 456 457 *dev->sci_tcmd = phase; 458 *sci_icmd = 0; 459 for (;len > 0; len--) { 460 csr = *sci_bus_csr; 461 while (!(csr & SCI_BUS_REQ)) { 462 if (!(csr & SCI_BUS_BSY) || --wait < 0) { 463#ifdef DEBUG 464 if (sci_debug) 465 printf("sci_ixfer_in fail: l%d i%x w%d\n", 466 len, csr, wait); 467#endif 468 return; 469 } 470 471 delay(1); 472 csr = *sci_bus_csr; 473 } 474 475 if (!(*dev->sci_csr & SCI_CSR_PHASE_MATCH)) 476 break; 477 *buf = *sci_data; 478 *sci_icmd = SCI_ICMD_ACK; 479 buf++; 480 while (*sci_bus_csr & SCI_BUS_REQ); 481 *sci_icmd = 0; 482 } 483 484 QPRINTF(("sci_ixfer_in {%d} %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x\n", 485 len, obp[0], obp[1], obp[2], obp[3], obp[4], obp[5], 486 obp[6], obp[7], obp[8], obp[9])); 487} 488 489/* 490 * SCSI 'immediate' command: issue a command to some SCSI device 491 * and get back an 'immediate' response (i.e., do programmed xfer 492 * to get the response data). 'cbuf' is a buffer containing a scsi 493 * command of length clen bytes. 'buf' is a buffer of length 'len' 494 * bytes for data. The transfer direction is determined by the device 495 * (i.e., by the scsi bus data xfer phase). If 'len' is zero, the 496 * command must supply no data. 'xferphase' is the bus phase the 497 * caller expects to happen after the command is issued. It should 498 * be one of DATA_IN_PHASE, DATA_OUT_PHASE or STATUS_PHASE. 499 */ 500int 501sciicmd(struct sci_softc *dev, int target, void *cbuf, int clen, void *buf, 502 int len, u_char xferphase) 503{ 504 u_char phase; 505 register int wait; 506 507 /* select the SCSI bus (it's an error if bus isn't free) */ 508 if (sciselectbus (dev, target, dev->sc_scsi_addr)) 509 return -1; 510 /* 511 * Wait for a phase change (or error) then let the device 512 * sequence us through the various SCSI phases. 513 */ 514 dev->sc_stat[0] = 0xff; 515 dev->sc_msg[0] = 0xff; 516 phase = CMD_PHASE; 517 while (1) { 518 wait = sci_cmd_wait; 519 520 while ((*dev->sci_bus_csr & (SCI_BUS_REQ|SCI_BUS_BSY)) == SCI_BUS_BSY); 521 522 QPRINTF((">CSR:%02x<", *dev->sci_bus_csr)); 523 if ((*dev->sci_bus_csr & SCI_BUS_REQ) == 0) { 524 return -1; 525 } 526 phase = SCI_PHASE(*dev->sci_bus_csr); 527 528 switch (phase) { 529 case CMD_PHASE: 530 if (sci_ixfer_out (dev, clen, cbuf, phase)) 531 goto abort; 532 phase = xferphase; 533 break; 534 535 case DATA_IN_PHASE: 536 if (len <= 0) 537 goto abort; 538 wait = sci_data_wait; 539 sci_ixfer_in (dev, len, buf, phase); 540 phase = STATUS_PHASE; 541 break; 542 543 case DATA_OUT_PHASE: 544 if (len <= 0) 545 goto abort; 546 wait = sci_data_wait; 547 if (sci_ixfer_out (dev, len, buf, phase)) 548 goto abort; 549 phase = STATUS_PHASE; 550 break; 551 552 case MESG_IN_PHASE: 553 dev->sc_msg[0] = 0xff; 554 sci_ixfer_in (dev, 1, dev->sc_msg,phase); 555 dev->sc_flags &= ~SCI_SELECTED; 556 while (*dev->sci_bus_csr & SCI_BUS_BSY); 557 goto out; 558 break; 559 560 case MESG_OUT_PHASE: 561 phase = STATUS_PHASE; 562 break; 563 564 case STATUS_PHASE: 565 sci_ixfer_in (dev, 1, dev->sc_stat, phase); 566 phase = MESG_IN_PHASE; 567 break; 568 569 case BUS_FREE_PHASE: 570 goto out; 571 572 default: 573 printf("sci: unexpected phase %d in icmd from %d\n", 574 phase, target); 575 goto abort; 576 } 577#if 0 578 if (wait <= 0) 579 goto abort; 580#endif 581 } 582 583abort: 584 sciabort(dev, "icmd"); 585out: 586 QPRINTF(("=STS:%02x=", dev->sc_stat[0])); 587 return (dev->sc_stat[0]); 588} 589 590int 591scigo(struct sci_softc *dev, struct scsipi_xfer *xs) 592{ 593 int count, target; 594 u_char phase, *addr; 595 596 target = xs->xs_periph->periph_target; 597 count = xs->datalen; 598 addr = xs->data; 599 600 if (sci_no_dma) { 601 sciicmd (dev, target, (u_char *) xs->cmd, xs->cmdlen, 602 addr, count, 603 xs->xs_control & XS_CTL_DATA_IN ? DATA_IN_PHASE : DATA_OUT_PHASE); 604 605 return (1); 606 } 607 608 /* select the SCSI bus (it's an error if bus isn't free) */ 609 if (sciselectbus (dev, target, dev->sc_scsi_addr)) 610 return -1; 611 /* 612 * Wait for a phase change (or error) then let the device 613 * sequence us through the various SCSI phases. 614 */ 615 dev->sc_stat[0] = 0xff; 616 dev->sc_msg[0] = 0xff; 617 phase = CMD_PHASE; 618 while (1) { 619 while ((*dev->sci_bus_csr & (SCI_BUS_REQ|SCI_BUS_BSY)) == 620 SCI_BUS_BSY); 621 622 QPRINTF((">CSR:%02x<", *dev->sci_bus_csr)); 623 if ((*dev->sci_bus_csr & SCI_BUS_REQ) == 0) { 624 goto abort; 625 } 626 phase = SCI_PHASE(*dev->sci_bus_csr); 627 628 switch (phase) { 629 case CMD_PHASE: 630 if (sci_ixfer_out (dev, xs->cmdlen, (u_char *) xs->cmd, phase)) 631 goto abort; 632 phase = xs->xs_control & XS_CTL_DATA_IN ? DATA_IN_PHASE : DATA_OUT_PHASE; 633 break; 634 635 case DATA_IN_PHASE: 636 if (count <= 0) 637 goto abort; 638 /* XXX use psuedo DMA if available */ 639 if (count >= 128 && dev->dma_xfer_in) 640 (*dev->dma_xfer_in)(dev, count, addr, phase); 641 else 642 sci_ixfer_in (dev, count, addr, phase); 643 phase = STATUS_PHASE; 644 break; 645 646 case DATA_OUT_PHASE: 647 if (count <= 0) 648 goto abort; 649 /* XXX use psuedo DMA if available */ 650 if (count >= 128 && dev->dma_xfer_out) 651 (*dev->dma_xfer_out)(dev, count, addr, phase); 652 else 653 if (sci_ixfer_out (dev, count, addr, phase)) 654 goto abort; 655 phase = STATUS_PHASE; 656 break; 657 658 case MESG_IN_PHASE: 659 dev->sc_msg[0] = 0xff; 660 sci_ixfer_in (dev, 1, dev->sc_msg,phase); 661 dev->sc_flags &= ~SCI_SELECTED; 662 while (*dev->sci_bus_csr & SCI_BUS_BSY); 663 goto out; 664 break; 665 666 case MESG_OUT_PHASE: 667 phase = STATUS_PHASE; 668 break; 669 670 case STATUS_PHASE: 671 sci_ixfer_in (dev, 1, dev->sc_stat, phase); 672 phase = MESG_IN_PHASE; 673 break; 674 675 case BUS_FREE_PHASE: 676 goto out; 677 678 default: 679 printf("sci: unexpected phase %d in icmd from %d\n", 680 phase, target); 681 goto abort; 682 } 683 } 684 685abort: 686 sciabort(dev, "go"); 687out: 688 QPRINTF(("=STS:%02x=", dev->sc_stat[0])); 689 return (1); 690} 691