1 /* $FreeBSD$ */ 2 /*- 3 * Copyright (c) 2008,2011 Hans Petter Selasky. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 15 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24 * SUCH DAMAGE. 25 */ 26 27 /* 28 * The following file contains code that will detect USB autoinstall 29 * disks. 30 * 31 * TODO: Potentially we could add code to automatically detect USB 32 * mass storage quirks for not supported SCSI commands! 33 */ 34 35 #ifdef USB_GLOBAL_INCLUDE_FILE 36 #include USB_GLOBAL_INCLUDE_FILE 37 #else 38 #include <sys/stdint.h> 39 #include <sys/stddef.h> 40 #include <sys/param.h> 41 #include <sys/queue.h> 42 #include <sys/types.h> 43 #include <sys/systm.h> 44 #include <sys/kernel.h> 45 #include <sys/bus.h> 46 #include <sys/module.h> 47 #include <sys/lock.h> 48 #include <sys/mutex.h> 49 #include <sys/condvar.h> 50 #include <sys/sysctl.h> 51 #include <sys/sx.h> 52 #include <sys/unistd.h> 53 #include <sys/callout.h> 54 #include <sys/malloc.h> 55 #include <sys/priv.h> 56 57 #include <dev/usb/usb.h> 58 #include <dev/usb/usbdi.h> 59 #include <dev/usb/usbdi_util.h> 60 61 #define USB_DEBUG_VAR usb_debug 62 63 #include <dev/usb/usb_busdma.h> 64 #include <dev/usb/usb_process.h> 65 #include <dev/usb/usb_transfer.h> 66 #include <dev/usb/usb_msctest.h> 67 #include <dev/usb/usb_debug.h> 68 #include <dev/usb/usb_device.h> 69 #include <dev/usb/usb_request.h> 70 #include <dev/usb/usb_util.h> 71 #include <dev/usb/quirk/usb_quirk.h> 72 #endif /* USB_GLOBAL_INCLUDE_FILE */ 73 74 enum { 75 ST_COMMAND, 76 ST_DATA_RD, 77 ST_DATA_RD_CS, 78 ST_DATA_WR, 79 ST_DATA_WR_CS, 80 ST_STATUS, 81 ST_MAX, 82 }; 83 84 enum { 85 DIR_IN, 86 DIR_OUT, 87 DIR_NONE, 88 }; 89 90 #define SCSI_MAX_LEN MAX(SCSI_FIXED_BLOCK_SIZE, USB_MSCTEST_BULK_SIZE) 91 #define SCSI_INQ_LEN 0x24 92 #define SCSI_SENSE_LEN 0xFF 93 #define SCSI_FIXED_BLOCK_SIZE 512 /* bytes */ 94 95 static uint8_t scsi_test_unit_ready[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; 96 static uint8_t scsi_inquiry[] = { 0x12, 0x00, 0x00, 0x00, SCSI_INQ_LEN, 0x00 }; 97 static uint8_t scsi_rezero_init[] = { 0x01, 0x00, 0x00, 0x00, 0x00, 0x00 }; 98 static uint8_t scsi_start_stop_unit[] = { 0x1b, 0x00, 0x00, 0x00, 0x02, 0x00 }; 99 static uint8_t scsi_ztestor_eject[] = { 0x85, 0x01, 0x01, 0x01, 0x18, 0x01, 100 0x01, 0x01, 0x01, 0x01, 0x00, 0x00 }; 101 static uint8_t scsi_cmotech_eject[] = { 0xff, 0x52, 0x44, 0x45, 0x56, 0x43, 102 0x48, 0x47 }; 103 static uint8_t scsi_huawei_eject[] = { 0x11, 0x06, 0x00, 0x00, 0x00, 0x00, 104 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 105 0x00, 0x00, 0x00, 0x00 }; 106 static uint8_t scsi_huawei_eject2[] = { 0x11, 0x06, 0x20, 0x00, 0x00, 0x01, 107 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 108 0x00, 0x00, 0x00, 0x00 }; 109 static uint8_t scsi_tct_eject[] = { 0x06, 0xf5, 0x04, 0x02, 0x52, 0x70 }; 110 static uint8_t scsi_sync_cache[] = { 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 111 0x00, 0x00, 0x00, 0x00 }; 112 static uint8_t scsi_request_sense[] = { 0x03, 0x00, 0x00, 0x00, 0x12, 0x00, 113 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; 114 static uint8_t scsi_read_capacity[] = { 0x25, 0x00, 0x00, 0x00, 0x00, 0x00, 115 0x00, 0x00, 0x00, 0x00 }; 116 117 #ifndef USB_MSCTEST_BULK_SIZE 118 #define USB_MSCTEST_BULK_SIZE 64 /* dummy */ 119 #endif 120 121 #define ERR_CSW_FAILED -1 122 123 /* Command Block Wrapper */ 124 struct bbb_cbw { 125 uDWord dCBWSignature; 126 #define CBWSIGNATURE 0x43425355 127 uDWord dCBWTag; 128 uDWord dCBWDataTransferLength; 129 uByte bCBWFlags; 130 #define CBWFLAGS_OUT 0x00 131 #define CBWFLAGS_IN 0x80 132 uByte bCBWLUN; 133 uByte bCDBLength; 134 #define CBWCDBLENGTH 16 135 uByte CBWCDB[CBWCDBLENGTH]; 136 } __packed; 137 138 /* Command Status Wrapper */ 139 struct bbb_csw { 140 uDWord dCSWSignature; 141 #define CSWSIGNATURE 0x53425355 142 uDWord dCSWTag; 143 uDWord dCSWDataResidue; 144 uByte bCSWStatus; 145 #define CSWSTATUS_GOOD 0x0 146 #define CSWSTATUS_FAILED 0x1 147 #define CSWSTATUS_PHASE 0x2 148 } __packed; 149 150 struct bbb_transfer { 151 struct mtx mtx; 152 struct cv cv; 153 struct bbb_cbw *cbw; 154 struct bbb_csw *csw; 155 156 struct usb_xfer *xfer[ST_MAX]; 157 158 uint8_t *data_ptr; 159 160 usb_size_t data_len; /* bytes */ 161 usb_size_t data_rem; /* bytes */ 162 usb_timeout_t data_timeout; /* ms */ 163 usb_frlength_t actlen; /* bytes */ 164 usb_frlength_t buffer_size; /* bytes */ 165 166 uint8_t cmd_len; /* bytes */ 167 uint8_t dir; 168 uint8_t lun; 169 uint8_t state; 170 uint8_t status_try; 171 int error; 172 173 uint8_t *buffer; 174 }; 175 176 static usb_callback_t bbb_command_callback; 177 static usb_callback_t bbb_data_read_callback; 178 static usb_callback_t bbb_data_rd_cs_callback; 179 static usb_callback_t bbb_data_write_callback; 180 static usb_callback_t bbb_data_wr_cs_callback; 181 static usb_callback_t bbb_status_callback; 182 183 static void bbb_done(struct bbb_transfer *, int); 184 static void bbb_transfer_start(struct bbb_transfer *, uint8_t); 185 static void bbb_data_clear_stall_callback(struct usb_xfer *, uint8_t, 186 uint8_t); 187 static int bbb_command_start(struct bbb_transfer *, uint8_t, uint8_t, 188 void *, size_t, void *, size_t, usb_timeout_t); 189 static struct bbb_transfer *bbb_attach(struct usb_device *, uint8_t); 190 static void bbb_detach(struct bbb_transfer *); 191 192 static const struct usb_config bbb_config[ST_MAX] = { 193 194 [ST_COMMAND] = { 195 .type = UE_BULK, 196 .endpoint = UE_ADDR_ANY, 197 .direction = UE_DIR_OUT, 198 .bufsize = sizeof(struct bbb_cbw), 199 .callback = &bbb_command_callback, 200 .timeout = 4 * USB_MS_HZ, /* 4 seconds */ 201 }, 202 203 [ST_DATA_RD] = { 204 .type = UE_BULK, 205 .endpoint = UE_ADDR_ANY, 206 .direction = UE_DIR_IN, 207 .bufsize = SCSI_MAX_LEN, 208 .flags = {.proxy_buffer = 1,.short_xfer_ok = 1,}, 209 .callback = &bbb_data_read_callback, 210 .timeout = 4 * USB_MS_HZ, /* 4 seconds */ 211 }, 212 213 [ST_DATA_RD_CS] = { 214 .type = UE_CONTROL, 215 .endpoint = 0x00, /* Control pipe */ 216 .direction = UE_DIR_ANY, 217 .bufsize = sizeof(struct usb_device_request), 218 .callback = &bbb_data_rd_cs_callback, 219 .timeout = 1 * USB_MS_HZ, /* 1 second */ 220 }, 221 222 [ST_DATA_WR] = { 223 .type = UE_BULK, 224 .endpoint = UE_ADDR_ANY, 225 .direction = UE_DIR_OUT, 226 .bufsize = SCSI_MAX_LEN, 227 .flags = {.ext_buffer = 1,.proxy_buffer = 1,}, 228 .callback = &bbb_data_write_callback, 229 .timeout = 4 * USB_MS_HZ, /* 4 seconds */ 230 }, 231 232 [ST_DATA_WR_CS] = { 233 .type = UE_CONTROL, 234 .endpoint = 0x00, /* Control pipe */ 235 .direction = UE_DIR_ANY, 236 .bufsize = sizeof(struct usb_device_request), 237 .callback = &bbb_data_wr_cs_callback, 238 .timeout = 1 * USB_MS_HZ, /* 1 second */ 239 }, 240 241 [ST_STATUS] = { 242 .type = UE_BULK, 243 .endpoint = UE_ADDR_ANY, 244 .direction = UE_DIR_IN, 245 .bufsize = sizeof(struct bbb_csw), 246 .flags = {.short_xfer_ok = 1,}, 247 .callback = &bbb_status_callback, 248 .timeout = 1 * USB_MS_HZ, /* 1 second */ 249 }, 250 }; 251 252 static void 253 bbb_done(struct bbb_transfer *sc, int error) 254 { 255 sc->error = error; 256 sc->state = ST_COMMAND; 257 sc->status_try = 1; 258 cv_signal(&sc->cv); 259 } 260 261 static void 262 bbb_transfer_start(struct bbb_transfer *sc, uint8_t xfer_index) 263 { 264 sc->state = xfer_index; 265 usbd_transfer_start(sc->xfer[xfer_index]); 266 } 267 268 static void 269 bbb_data_clear_stall_callback(struct usb_xfer *xfer, 270 uint8_t next_xfer, uint8_t stall_xfer) 271 { 272 struct bbb_transfer *sc = usbd_xfer_softc(xfer); 273 274 if (usbd_clear_stall_callback(xfer, sc->xfer[stall_xfer])) { 275 switch (USB_GET_STATE(xfer)) { 276 case USB_ST_SETUP: 277 case USB_ST_TRANSFERRED: 278 bbb_transfer_start(sc, next_xfer); 279 break; 280 default: 281 bbb_done(sc, USB_ERR_STALLED); 282 break; 283 } 284 } 285 } 286 287 static void 288 bbb_command_callback(struct usb_xfer *xfer, usb_error_t error) 289 { 290 struct bbb_transfer *sc = usbd_xfer_softc(xfer); 291 uint32_t tag; 292 293 switch (USB_GET_STATE(xfer)) { 294 case USB_ST_TRANSFERRED: 295 bbb_transfer_start 296 (sc, ((sc->dir == DIR_IN) ? ST_DATA_RD : 297 (sc->dir == DIR_OUT) ? ST_DATA_WR : 298 ST_STATUS)); 299 break; 300 301 case USB_ST_SETUP: 302 sc->status_try = 0; 303 tag = UGETDW(sc->cbw->dCBWTag) + 1; 304 USETDW(sc->cbw->dCBWSignature, CBWSIGNATURE); 305 USETDW(sc->cbw->dCBWTag, tag); 306 USETDW(sc->cbw->dCBWDataTransferLength, (uint32_t)sc->data_len); 307 sc->cbw->bCBWFlags = ((sc->dir == DIR_IN) ? CBWFLAGS_IN : CBWFLAGS_OUT); 308 sc->cbw->bCBWLUN = sc->lun; 309 sc->cbw->bCDBLength = sc->cmd_len; 310 if (sc->cbw->bCDBLength > sizeof(sc->cbw->CBWCDB)) { 311 sc->cbw->bCDBLength = sizeof(sc->cbw->CBWCDB); 312 DPRINTFN(0, "Truncating long command\n"); 313 } 314 usbd_xfer_set_frame_len(xfer, 0, 315 sizeof(struct bbb_cbw)); 316 usbd_transfer_submit(xfer); 317 break; 318 319 default: /* Error */ 320 bbb_done(sc, error); 321 break; 322 } 323 } 324 325 static void 326 bbb_data_read_callback(struct usb_xfer *xfer, usb_error_t error) 327 { 328 struct bbb_transfer *sc = usbd_xfer_softc(xfer); 329 usb_frlength_t max_bulk = usbd_xfer_max_len(xfer); 330 int actlen, sumlen; 331 332 usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL); 333 334 switch (USB_GET_STATE(xfer)) { 335 case USB_ST_TRANSFERRED: 336 sc->data_rem -= actlen; 337 sc->data_ptr += actlen; 338 sc->actlen += actlen; 339 340 if (actlen < sumlen) { 341 /* short transfer */ 342 sc->data_rem = 0; 343 } 344 case USB_ST_SETUP: 345 DPRINTF("max_bulk=%d, data_rem=%d\n", 346 max_bulk, sc->data_rem); 347 348 if (sc->data_rem == 0) { 349 bbb_transfer_start(sc, ST_STATUS); 350 break; 351 } 352 if (max_bulk > sc->data_rem) { 353 max_bulk = sc->data_rem; 354 } 355 usbd_xfer_set_timeout(xfer, sc->data_timeout); 356 usbd_xfer_set_frame_data(xfer, 0, sc->data_ptr, max_bulk); 357 usbd_transfer_submit(xfer); 358 break; 359 360 default: /* Error */ 361 if (error == USB_ERR_CANCELLED) { 362 bbb_done(sc, error); 363 } else { 364 bbb_transfer_start(sc, ST_DATA_RD_CS); 365 } 366 break; 367 } 368 } 369 370 static void 371 bbb_data_rd_cs_callback(struct usb_xfer *xfer, usb_error_t error) 372 { 373 bbb_data_clear_stall_callback(xfer, ST_STATUS, 374 ST_DATA_RD); 375 } 376 377 static void 378 bbb_data_write_callback(struct usb_xfer *xfer, usb_error_t error) 379 { 380 struct bbb_transfer *sc = usbd_xfer_softc(xfer); 381 usb_frlength_t max_bulk = usbd_xfer_max_len(xfer); 382 int actlen, sumlen; 383 384 usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL); 385 386 switch (USB_GET_STATE(xfer)) { 387 case USB_ST_TRANSFERRED: 388 sc->data_rem -= actlen; 389 sc->data_ptr += actlen; 390 sc->actlen += actlen; 391 392 if (actlen < sumlen) { 393 /* short transfer */ 394 sc->data_rem = 0; 395 } 396 case USB_ST_SETUP: 397 DPRINTF("max_bulk=%d, data_rem=%d\n", 398 max_bulk, sc->data_rem); 399 400 if (sc->data_rem == 0) { 401 bbb_transfer_start(sc, ST_STATUS); 402 break; 403 } 404 if (max_bulk > sc->data_rem) { 405 max_bulk = sc->data_rem; 406 } 407 usbd_xfer_set_timeout(xfer, sc->data_timeout); 408 usbd_xfer_set_frame_data(xfer, 0, sc->data_ptr, max_bulk); 409 usbd_transfer_submit(xfer); 410 break; 411 412 default: /* Error */ 413 if (error == USB_ERR_CANCELLED) { 414 bbb_done(sc, error); 415 } else { 416 bbb_transfer_start(sc, ST_DATA_WR_CS); 417 } 418 break; 419 } 420 } 421 422 static void 423 bbb_data_wr_cs_callback(struct usb_xfer *xfer, usb_error_t error) 424 { 425 bbb_data_clear_stall_callback(xfer, ST_STATUS, 426 ST_DATA_WR); 427 } 428 429 static void 430 bbb_status_callback(struct usb_xfer *xfer, usb_error_t error) 431 { 432 struct bbb_transfer *sc = usbd_xfer_softc(xfer); 433 int actlen; 434 int sumlen; 435 436 usbd_xfer_status(xfer, &actlen, &sumlen, NULL, NULL); 437 438 switch (USB_GET_STATE(xfer)) { 439 case USB_ST_TRANSFERRED: 440 441 /* very simple status check */ 442 443 if (actlen < (int)sizeof(struct bbb_csw)) { 444 bbb_done(sc, USB_ERR_SHORT_XFER); 445 } else if (sc->csw->bCSWStatus == CSWSTATUS_GOOD) { 446 bbb_done(sc, 0); /* success */ 447 } else { 448 bbb_done(sc, ERR_CSW_FAILED); /* error */ 449 } 450 break; 451 452 case USB_ST_SETUP: 453 usbd_xfer_set_frame_len(xfer, 0, 454 sizeof(struct bbb_csw)); 455 usbd_transfer_submit(xfer); 456 break; 457 458 default: 459 DPRINTF("Failed to read CSW: %s, try %d\n", 460 usbd_errstr(error), sc->status_try); 461 462 if (error == USB_ERR_CANCELLED || sc->status_try) { 463 bbb_done(sc, error); 464 } else { 465 sc->status_try = 1; 466 bbb_transfer_start(sc, ST_DATA_RD_CS); 467 } 468 break; 469 } 470 } 471 472 /*------------------------------------------------------------------------* 473 * bbb_command_start - execute a SCSI command synchronously 474 * 475 * Return values 476 * 0: Success 477 * Else: Failure 478 *------------------------------------------------------------------------*/ 479 static int 480 bbb_command_start(struct bbb_transfer *sc, uint8_t dir, uint8_t lun, 481 void *data_ptr, size_t data_len, void *cmd_ptr, size_t cmd_len, 482 usb_timeout_t data_timeout) 483 { 484 sc->lun = lun; 485 sc->dir = data_len ? dir : DIR_NONE; 486 sc->data_ptr = data_ptr; 487 sc->data_len = data_len; 488 sc->data_rem = data_len; 489 sc->data_timeout = (data_timeout + USB_MS_HZ); 490 sc->actlen = 0; 491 sc->error = 0; 492 sc->cmd_len = cmd_len; 493 memset(&sc->cbw->CBWCDB, 0, sizeof(sc->cbw->CBWCDB)); 494 memcpy(&sc->cbw->CBWCDB, cmd_ptr, cmd_len); 495 DPRINTFN(1, "SCSI cmd = %*D\n", (int)cmd_len, (char *)sc->cbw->CBWCDB, ":"); 496 497 mtx_lock(&sc->mtx); 498 usbd_transfer_start(sc->xfer[sc->state]); 499 500 while (usbd_transfer_pending(sc->xfer[sc->state])) { 501 cv_wait(&sc->cv, &sc->mtx); 502 } 503 mtx_unlock(&sc->mtx); 504 return (sc->error); 505 } 506 507 static struct bbb_transfer * 508 bbb_attach(struct usb_device *udev, uint8_t iface_index) 509 { 510 struct usb_interface *iface; 511 struct usb_interface_descriptor *id; 512 struct bbb_transfer *sc; 513 usb_error_t err; 514 515 #if USB_HAVE_MSCTEST_DETACH 516 uint8_t do_unlock; 517 518 /* Prevent re-enumeration */ 519 do_unlock = usbd_enum_lock(udev); 520 521 /* 522 * Make sure any driver which is hooked up to this interface, 523 * like umass is gone: 524 */ 525 usb_detach_device(udev, iface_index, 0); 526 527 if (do_unlock) 528 usbd_enum_unlock(udev); 529 #endif 530 531 iface = usbd_get_iface(udev, iface_index); 532 if (iface == NULL) 533 return (NULL); 534 535 id = iface->idesc; 536 if (id == NULL || id->bInterfaceClass != UICLASS_MASS) 537 return (NULL); 538 539 switch (id->bInterfaceSubClass) { 540 case UISUBCLASS_SCSI: 541 case UISUBCLASS_UFI: 542 case UISUBCLASS_SFF8020I: 543 case UISUBCLASS_SFF8070I: 544 break; 545 default: 546 return (NULL); 547 } 548 549 switch (id->bInterfaceProtocol) { 550 case UIPROTO_MASS_BBB_OLD: 551 case UIPROTO_MASS_BBB: 552 break; 553 default: 554 return (NULL); 555 } 556 557 sc = malloc(sizeof(*sc), M_USB, M_WAITOK | M_ZERO); 558 mtx_init(&sc->mtx, "USB autoinstall", NULL, MTX_DEF); 559 cv_init(&sc->cv, "WBBB"); 560 561 err = usbd_transfer_setup(udev, &iface_index, sc->xfer, bbb_config, 562 ST_MAX, sc, &sc->mtx); 563 if (err) { 564 bbb_detach(sc); 565 return (NULL); 566 } 567 /* store pointer to DMA buffers */ 568 sc->buffer = usbd_xfer_get_frame_buffer( 569 sc->xfer[ST_DATA_RD], 0); 570 sc->buffer_size = 571 usbd_xfer_max_len(sc->xfer[ST_DATA_RD]); 572 sc->cbw = usbd_xfer_get_frame_buffer( 573 sc->xfer[ST_COMMAND], 0); 574 sc->csw = usbd_xfer_get_frame_buffer( 575 sc->xfer[ST_STATUS], 0); 576 577 return (sc); 578 } 579 580 static void 581 bbb_detach(struct bbb_transfer *sc) 582 { 583 usbd_transfer_unsetup(sc->xfer, ST_MAX); 584 mtx_destroy(&sc->mtx); 585 cv_destroy(&sc->cv); 586 free(sc, M_USB); 587 } 588 589 /*------------------------------------------------------------------------* 590 * usb_iface_is_cdrom 591 * 592 * Return values: 593 * 1: This interface is an auto install disk (CD-ROM) 594 * 0: Not an auto install disk. 595 *------------------------------------------------------------------------*/ 596 int 597 usb_iface_is_cdrom(struct usb_device *udev, uint8_t iface_index) 598 { 599 struct bbb_transfer *sc; 600 uint8_t timeout; 601 uint8_t is_cdrom; 602 uint8_t sid_type; 603 int err; 604 605 sc = bbb_attach(udev, iface_index); 606 if (sc == NULL) 607 return (0); 608 609 is_cdrom = 0; 610 timeout = 4; /* tries */ 611 while (--timeout) { 612 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 613 SCSI_INQ_LEN, &scsi_inquiry, sizeof(scsi_inquiry), 614 USB_MS_HZ); 615 616 if (err == 0 && sc->actlen > 0) { 617 sid_type = sc->buffer[0] & 0x1F; 618 if (sid_type == 0x05) 619 is_cdrom = 1; 620 break; 621 } else if (err != ERR_CSW_FAILED) 622 break; /* non retryable error */ 623 usb_pause_mtx(NULL, hz); 624 } 625 bbb_detach(sc); 626 return (is_cdrom); 627 } 628 629 static uint8_t 630 usb_msc_get_max_lun(struct usb_device *udev, uint8_t iface_index) 631 { 632 struct usb_device_request req; 633 usb_error_t err; 634 uint8_t buf = 0; 635 636 637 /* The Get Max Lun command is a class-specific request. */ 638 req.bmRequestType = UT_READ_CLASS_INTERFACE; 639 req.bRequest = 0xFE; /* GET_MAX_LUN */ 640 USETW(req.wValue, 0); 641 req.wIndex[0] = iface_index; 642 req.wIndex[1] = 0; 643 USETW(req.wLength, 1); 644 645 err = usbd_do_request(udev, NULL, &req, &buf); 646 if (err) 647 buf = 0; 648 649 return (buf); 650 } 651 652 usb_error_t 653 usb_msc_auto_quirk(struct usb_device *udev, uint8_t iface_index) 654 { 655 struct bbb_transfer *sc; 656 uint8_t timeout; 657 uint8_t is_no_direct; 658 uint8_t sid_type; 659 int err; 660 661 sc = bbb_attach(udev, iface_index); 662 if (sc == NULL) 663 return (0); 664 665 /* 666 * Some devices need a delay after that the configuration 667 * value is set to function properly: 668 */ 669 usb_pause_mtx(NULL, hz); 670 671 if (usb_msc_get_max_lun(udev, iface_index) == 0) { 672 DPRINTF("Device has only got one LUN.\n"); 673 usbd_add_dynamic_quirk(udev, UQ_MSC_NO_GETMAXLUN); 674 } 675 676 is_no_direct = 1; 677 for (timeout = 4; timeout != 0; timeout--) { 678 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 679 SCSI_INQ_LEN, &scsi_inquiry, sizeof(scsi_inquiry), 680 USB_MS_HZ); 681 682 if (err == 0 && sc->actlen > 0) { 683 sid_type = sc->buffer[0] & 0x1F; 684 if (sid_type == 0x00) 685 is_no_direct = 0; 686 break; 687 } else if (err != ERR_CSW_FAILED) { 688 DPRINTF("Device is not responding " 689 "properly to SCSI INQUIRY command.\n"); 690 goto error; /* non retryable error */ 691 } 692 usb_pause_mtx(NULL, hz); 693 } 694 695 if (is_no_direct) { 696 DPRINTF("Device is not direct access.\n"); 697 goto done; 698 } 699 700 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 701 &scsi_test_unit_ready, sizeof(scsi_test_unit_ready), 702 USB_MS_HZ); 703 704 if (err != 0) { 705 706 if (err != ERR_CSW_FAILED) 707 goto error; 708 } 709 timeout = 1; 710 711 retry_sync_cache: 712 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 713 &scsi_sync_cache, sizeof(scsi_sync_cache), 714 USB_MS_HZ); 715 716 if (err != 0) { 717 718 if (err != ERR_CSW_FAILED) 719 goto error; 720 721 DPRINTF("Device doesn't handle synchronize cache\n"); 722 723 usbd_add_dynamic_quirk(udev, UQ_MSC_NO_SYNC_CACHE); 724 725 } else { 726 727 /* 728 * Certain Kingston memory sticks fail the first 729 * read capacity after a synchronize cache command 730 * has been issued. Disable the synchronize cache 731 * command for such devices. 732 */ 733 734 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 8, 735 &scsi_read_capacity, sizeof(scsi_read_capacity), 736 USB_MS_HZ); 737 738 if (err != 0) { 739 if (err != ERR_CSW_FAILED) 740 goto error; 741 742 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 8, 743 &scsi_read_capacity, sizeof(scsi_read_capacity), 744 USB_MS_HZ); 745 746 if (err == 0) { 747 if (timeout--) 748 goto retry_sync_cache; 749 750 DPRINTF("Device most likely doesn't " 751 "handle synchronize cache\n"); 752 753 usbd_add_dynamic_quirk(udev, 754 UQ_MSC_NO_SYNC_CACHE); 755 } else { 756 if (err != ERR_CSW_FAILED) 757 goto error; 758 } 759 } 760 } 761 762 /* clear sense status of any failed commands on the device */ 763 764 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 765 SCSI_INQ_LEN, &scsi_inquiry, sizeof(scsi_inquiry), 766 USB_MS_HZ); 767 768 DPRINTF("Inquiry = %d\n", err); 769 770 if (err != 0) { 771 772 if (err != ERR_CSW_FAILED) 773 goto error; 774 } 775 776 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 777 SCSI_SENSE_LEN, &scsi_request_sense, 778 sizeof(scsi_request_sense), USB_MS_HZ); 779 780 DPRINTF("Request sense = %d\n", err); 781 782 if (err != 0) { 783 784 if (err != ERR_CSW_FAILED) 785 goto error; 786 } 787 788 done: 789 bbb_detach(sc); 790 return (0); 791 792 error: 793 bbb_detach(sc); 794 795 DPRINTF("Device did not respond, enabling all quirks\n"); 796 797 usbd_add_dynamic_quirk(udev, UQ_MSC_NO_SYNC_CACHE); 798 usbd_add_dynamic_quirk(udev, UQ_MSC_NO_TEST_UNIT_READY); 799 800 /* Need to re-enumerate the device */ 801 usbd_req_re_enumerate(udev, NULL); 802 803 return (USB_ERR_STALLED); 804 } 805 806 usb_error_t 807 usb_msc_eject(struct usb_device *udev, uint8_t iface_index, int method) 808 { 809 struct bbb_transfer *sc; 810 usb_error_t err; 811 812 sc = bbb_attach(udev, iface_index); 813 if (sc == NULL) 814 return (USB_ERR_INVAL); 815 816 switch (method) { 817 case MSC_EJECT_STOPUNIT: 818 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 819 &scsi_test_unit_ready, sizeof(scsi_test_unit_ready), 820 USB_MS_HZ); 821 DPRINTF("Test unit ready status: %s\n", usbd_errstr(err)); 822 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 823 &scsi_start_stop_unit, sizeof(scsi_start_stop_unit), 824 USB_MS_HZ); 825 break; 826 case MSC_EJECT_REZERO: 827 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 828 &scsi_rezero_init, sizeof(scsi_rezero_init), 829 USB_MS_HZ); 830 break; 831 case MSC_EJECT_ZTESTOR: 832 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 833 &scsi_ztestor_eject, sizeof(scsi_ztestor_eject), 834 USB_MS_HZ); 835 break; 836 case MSC_EJECT_CMOTECH: 837 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 838 &scsi_cmotech_eject, sizeof(scsi_cmotech_eject), 839 USB_MS_HZ); 840 break; 841 case MSC_EJECT_HUAWEI: 842 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 843 &scsi_huawei_eject, sizeof(scsi_huawei_eject), 844 USB_MS_HZ); 845 break; 846 case MSC_EJECT_HUAWEI2: 847 err = bbb_command_start(sc, DIR_IN, 0, NULL, 0, 848 &scsi_huawei_eject2, sizeof(scsi_huawei_eject2), 849 USB_MS_HZ); 850 break; 851 case MSC_EJECT_TCT: 852 /* 853 * TCTMobile needs DIR_IN flag. To get it, we 854 * supply a dummy data with the command. 855 */ 856 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 857 sc->buffer_size, &scsi_tct_eject, 858 sizeof(scsi_tct_eject), USB_MS_HZ); 859 break; 860 default: 861 DPRINTF("Unknown eject method (%d)\n", method); 862 bbb_detach(sc); 863 return (USB_ERR_INVAL); 864 } 865 866 DPRINTF("Eject CD command status: %s\n", usbd_errstr(err)); 867 868 bbb_detach(sc); 869 return (0); 870 } 871 872 usb_error_t 873 usb_msc_read_10(struct usb_device *udev, uint8_t iface_index, 874 uint32_t lba, uint32_t blocks, void *buffer) 875 { 876 struct bbb_transfer *sc; 877 uint8_t cmd[10]; 878 usb_error_t err; 879 880 cmd[0] = 0x28; /* READ_10 */ 881 cmd[1] = 0; 882 cmd[2] = lba >> 24; 883 cmd[3] = lba >> 16; 884 cmd[4] = lba >> 8; 885 cmd[5] = lba >> 0; 886 cmd[6] = 0; 887 cmd[7] = blocks >> 8; 888 cmd[8] = blocks; 889 cmd[9] = 0; 890 891 sc = bbb_attach(udev, iface_index); 892 if (sc == NULL) 893 return (USB_ERR_INVAL); 894 895 err = bbb_command_start(sc, DIR_IN, 0, buffer, 896 blocks * SCSI_FIXED_BLOCK_SIZE, cmd, 10, USB_MS_HZ); 897 898 bbb_detach(sc); 899 900 return (err); 901 } 902 903 usb_error_t 904 usb_msc_write_10(struct usb_device *udev, uint8_t iface_index, 905 uint32_t lba, uint32_t blocks, void *buffer) 906 { 907 struct bbb_transfer *sc; 908 uint8_t cmd[10]; 909 usb_error_t err; 910 911 cmd[0] = 0x2a; /* WRITE_10 */ 912 cmd[1] = 0; 913 cmd[2] = lba >> 24; 914 cmd[3] = lba >> 16; 915 cmd[4] = lba >> 8; 916 cmd[5] = lba >> 0; 917 cmd[6] = 0; 918 cmd[7] = blocks >> 8; 919 cmd[8] = blocks; 920 cmd[9] = 0; 921 922 sc = bbb_attach(udev, iface_index); 923 if (sc == NULL) 924 return (USB_ERR_INVAL); 925 926 err = bbb_command_start(sc, DIR_OUT, 0, buffer, 927 blocks * SCSI_FIXED_BLOCK_SIZE, cmd, 10, USB_MS_HZ); 928 929 bbb_detach(sc); 930 931 return (err); 932 } 933 934 usb_error_t 935 usb_msc_read_capacity(struct usb_device *udev, uint8_t iface_index, 936 uint32_t *lba_last, uint32_t *block_size) 937 { 938 struct bbb_transfer *sc; 939 usb_error_t err; 940 941 sc = bbb_attach(udev, iface_index); 942 if (sc == NULL) 943 return (USB_ERR_INVAL); 944 945 err = bbb_command_start(sc, DIR_IN, 0, sc->buffer, 8, 946 &scsi_read_capacity, sizeof(scsi_read_capacity), 947 USB_MS_HZ); 948 949 *lba_last = 950 (sc->buffer[0] << 24) | 951 (sc->buffer[1] << 16) | 952 (sc->buffer[2] << 8) | 953 (sc->buffer[3]); 954 955 *block_size = 956 (sc->buffer[4] << 24) | 957 (sc->buffer[5] << 16) | 958 (sc->buffer[6] << 8) | 959 (sc->buffer[7]); 960 961 /* we currently only support one block size */ 962 if (*block_size != SCSI_FIXED_BLOCK_SIZE) 963 err = USB_ERR_INVAL; 964 965 bbb_detach(sc); 966 967 return (err); 968 } 969