1 /*- 2 * BSD LICENSE 3 * 4 * Copyright (C) 2008-2012 Daisuke Aoyama <aoyama@peach.ne.jp>. 5 * Copyright (c) Intel Corporation. 6 * All rights reserved. 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 * 12 * * Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * * Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in 16 * the documentation and/or other materials provided with the 17 * distribution. 18 * * Neither the name of Intel Corporation nor the names of its 19 * contributors may be used to endorse or promote products derived 20 * from this software without specific prior written permission. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 23 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 24 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 25 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 26 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 27 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 28 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 32 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 */ 34 35 #include "scsi_internal.h" 36 37 #include "spdk/env.h" 38 #include "spdk/bdev.h" 39 #include "spdk/endian.h" 40 #include "spdk/string.h" 41 42 #define SPDK_WORK_BLOCK_SIZE (1ULL * 1024ULL * 1024ULL) 43 #define SPDK_WORK_ATS_BLOCK_SIZE (1ULL * 1024ULL * 1024ULL) 44 #define MAX_SERIAL_STRING 32 45 46 #define DEFAULT_DISK_VENDOR "Intel" 47 #define DEFAULT_DISK_REVISION "0001" 48 #define DEFAULT_DISK_ROTATION_RATE 7200 /* 7200 rpm */ 49 #define DEFAULT_DISK_FORM_FACTOR 0x02 /* 3.5 inch */ 50 51 #define INQUIRY_OFFSET(field) offsetof(struct spdk_scsi_cdb_inquiry_data, field) + \ 52 sizeof(((struct spdk_scsi_cdb_inquiry_data *)0x0)->field) 53 54 static int 55 spdk_hex2bin(char ch) 56 { 57 if ((ch >= '0') && (ch <= '9')) 58 return ch - '0'; 59 ch = tolower(ch); 60 if ((ch >= 'a') && (ch <= 'f')) 61 return ch - 'a' + 10; 62 return (int)ch; 63 } 64 65 static void 66 spdk_bdev_scsi_set_local_naa(char *name, uint8_t *buf) 67 { 68 int i, value, count = 0; 69 uint64_t naa, local_value; 70 71 for (i = 0; (i < 16) && (name[i] != '\0'); i++) { 72 value = spdk_hex2bin(name[i]); 73 if (i % 2) { 74 buf[count++] |= value << 4; 75 } else { 76 buf[count] = value; 77 } 78 } 79 /* NAA locally assigned filed */ 80 naa = 0x3; 81 local_value = *(uint64_t *)buf; 82 local_value = (naa << 60) | (local_value >> 4); 83 to_be64((void *)buf, local_value); 84 } 85 86 static int 87 spdk_bdev_scsi_report_luns(struct spdk_scsi_lun *lun, 88 int sel, uint8_t *data, int alloc_len) 89 { 90 struct spdk_scsi_dev *dev; 91 uint64_t fmt_lun, lun_id, method; 92 int hlen, len = 0; 93 int i; 94 95 if (alloc_len < 8) 96 return -1; 97 98 if (sel == 0x00) { 99 /* logical unit with addressing method */ 100 } else if (sel == 0x01) { 101 /* well known logical unit */ 102 } else if (sel == 0x02) { 103 /* logical unit */ 104 } else 105 return -1; 106 107 /* LUN LIST LENGTH */ 108 memset(data, 0, 4); 109 110 /* Reserved */ 111 memset(&data[4], 0, 4); 112 hlen = 8; 113 114 dev = lun->dev; 115 for (i = 0; i < dev->maxlun; i++) { 116 if (dev->lun[i] == NULL) 117 continue; 118 119 if (alloc_len - (hlen + len) < 8) 120 return -1; 121 122 lun_id = (uint64_t)i; 123 124 if (dev->maxlun <= 0x0100) { 125 /* below 256 */ 126 method = 0x00U; 127 fmt_lun = (method & 0x03U) << 62; 128 fmt_lun |= (lun_id & 0x00ffU) << 48; 129 } else if (dev->maxlun <= 0x4000) { 130 /* below 16384 */ 131 method = 0x01U; 132 fmt_lun = (method & 0x03U) << 62; 133 fmt_lun |= (lun_id & 0x3fffU) << 48; 134 } else { 135 /* XXX */ 136 fmt_lun = 0; 137 } 138 139 /* LUN */ 140 to_be64(&data[hlen + len], fmt_lun); 141 len += 8; 142 } 143 144 /* LUN LIST LENGTH */ 145 to_be32(data, len); 146 147 return hlen + len; 148 } 149 150 static int 151 spdk_bdev_scsi_inquiry(struct spdk_bdev *bdev, struct spdk_scsi_task *task, 152 uint8_t *cdb, uint8_t *data, uint16_t alloc_len) 153 { 154 struct spdk_scsi_lun *lun; 155 struct spdk_scsi_dev *dev; 156 struct spdk_scsi_port *port; 157 uint32_t blocks, optimal_blocks; 158 int hlen = 0, plen, plen2; 159 uint16_t len = 0; 160 int pc; 161 int pd; 162 int evpd; 163 int i; 164 struct spdk_scsi_cdb_inquiry *inq = (struct spdk_scsi_cdb_inquiry *)cdb; 165 166 /* standard inquiry command at lease with 36 Bytes */ 167 if (alloc_len < 0x24) 168 goto inq_error; 169 170 lun = task->lun; 171 dev = lun->dev; 172 port = task->target_port; 173 174 pd = SPDK_SPC_PERIPHERAL_DEVICE_TYPE_DISK; 175 pc = inq->page_code; 176 evpd = inq->evpd & 0x1; 177 178 if (!evpd && pc) { 179 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 180 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 181 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 182 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 183 return -1; 184 } 185 186 if (evpd) { 187 struct spdk_scsi_vpd_page *vpage = (struct spdk_scsi_vpd_page *)data; 188 189 /* PERIPHERAL QUALIFIER(7-5) PERIPHERAL DEVICE TYPE(4-0) */ 190 vpage->peripheral = pd; 191 /* PAGE CODE */ 192 vpage->page_code = pc; 193 194 /* Vital product data */ 195 switch (pc) { 196 case SPDK_SPC_VPD_SUPPORTED_VPD_PAGES: 197 hlen = 4; 198 199 vpage->params[0] = SPDK_SPC_VPD_SUPPORTED_VPD_PAGES; 200 vpage->params[1] = SPDK_SPC_VPD_UNIT_SERIAL_NUMBER; 201 vpage->params[2] = SPDK_SPC_VPD_DEVICE_IDENTIFICATION; 202 vpage->params[3] = SPDK_SPC_VPD_MANAGEMENT_NETWORK_ADDRESSES; 203 vpage->params[4] = SPDK_SPC_VPD_EXTENDED_INQUIRY_DATA; 204 vpage->params[5] = SPDK_SPC_VPD_MODE_PAGE_POLICY; 205 vpage->params[6] = SPDK_SPC_VPD_SCSI_PORTS; 206 /* SBC Block Limits */ 207 vpage->params[7] = 0xb0; 208 /* SBC Block Device Characteristics */ 209 vpage->params[8] = 0xb1; 210 len = 9; 211 if (bdev->thin_provisioning) { 212 /* SBC Thin Provisioning */ 213 vpage->params[9] = 0xb2; 214 len++; 215 } 216 217 /* PAGE LENGTH */ 218 to_be16(vpage->alloc_len, len); 219 break; 220 221 case SPDK_SPC_VPD_UNIT_SERIAL_NUMBER: 222 hlen = 4; 223 224 /* PRODUCT SERIAL NUMBER */ 225 len = strlen(bdev->name); 226 if (len > MAX_SERIAL_STRING) { 227 len = MAX_SERIAL_STRING; 228 } 229 230 spdk_strcpy_pad(vpage->params, bdev->name, len, ' '); 231 232 /* PAGE LENGTH */ 233 to_be16(vpage->alloc_len, len); 234 break; 235 236 case SPDK_SPC_VPD_DEVICE_IDENTIFICATION: { 237 uint8_t *buf = vpage->params; 238 struct spdk_scsi_desig_desc *desig; 239 240 hlen = 4; 241 242 /* Check total length by calculated how much space all entries take */ 243 len = sizeof(struct spdk_scsi_desig_desc) + 8; 244 len += sizeof(struct spdk_scsi_desig_desc) + 8 + 16 + MAX_SERIAL_STRING; 245 len += sizeof(struct spdk_scsi_desig_desc) + SPDK_SCSI_DEV_MAX_NAME; 246 len += sizeof(struct spdk_scsi_desig_desc) + SPDK_SCSI_PORT_MAX_NAME_LENGTH; 247 len += sizeof(struct spdk_scsi_desig_desc) + 4; 248 len += sizeof(struct spdk_scsi_desig_desc) + 4; 249 len += sizeof(struct spdk_scsi_desig_desc) + 4; 250 if (sizeof(struct spdk_scsi_vpd_page) + len > task->alloc_len) { 251 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 252 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 253 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 254 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 255 return -1; 256 } 257 258 /* Now fill out the designator array */ 259 260 /* NAA designator */ 261 desig = (struct spdk_scsi_desig_desc *)buf; 262 desig->code_set = SPDK_SPC_VPD_CODE_SET_BINARY; 263 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 264 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_NAA; 265 desig->association = SPDK_SPC_VPD_ASSOCIATION_LOGICAL_UNIT; 266 desig->reserved0 = 0; 267 desig->piv = 1; 268 desig->reserved1 = 0; 269 desig->len = 8; 270 spdk_bdev_scsi_set_local_naa(bdev->name, desig->desig); 271 len = sizeof(struct spdk_scsi_desig_desc) + 8; 272 273 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 274 275 /* T10 Vendor ID designator */ 276 desig = (struct spdk_scsi_desig_desc *)buf; 277 desig->code_set = SPDK_SPC_VPD_CODE_SET_ASCII; 278 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 279 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_T10_VENDOR_ID; 280 desig->association = SPDK_SPC_VPD_ASSOCIATION_LOGICAL_UNIT; 281 desig->reserved0 = 0; 282 desig->piv = 1; 283 desig->reserved1 = 0; 284 desig->len = 8 + 16 + MAX_SERIAL_STRING; 285 spdk_strcpy_pad(desig->desig, DEFAULT_DISK_VENDOR, 8, ' '); 286 spdk_strcpy_pad(&desig->desig[8], bdev->product_name, 16, ' '); 287 spdk_strcpy_pad(&desig->desig[24], bdev->name, MAX_SERIAL_STRING, ' '); 288 len += sizeof(struct spdk_scsi_desig_desc) + 8 + 16 + MAX_SERIAL_STRING; 289 290 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 291 292 /* SCSI Device Name designator */ 293 desig = (struct spdk_scsi_desig_desc *)buf; 294 desig->code_set = SPDK_SPC_VPD_CODE_SET_UTF8; 295 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 296 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_SCSI_NAME; 297 desig->association = SPDK_SPC_VPD_ASSOCIATION_TARGET_DEVICE; 298 desig->reserved0 = 0; 299 desig->piv = 1; 300 desig->reserved1 = 0; 301 desig->len = snprintf(desig->desig, SPDK_SCSI_DEV_MAX_NAME, "%s", dev->name); 302 len += sizeof(struct spdk_scsi_desig_desc) + desig->len; 303 304 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 305 306 /* SCSI Port Name designator */ 307 desig = (struct spdk_scsi_desig_desc *)buf; 308 desig->code_set = SPDK_SPC_VPD_CODE_SET_UTF8; 309 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 310 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_SCSI_NAME; 311 desig->association = SPDK_SPC_VPD_ASSOCIATION_TARGET_PORT; 312 desig->reserved0 = 0; 313 desig->piv = 1; 314 desig->reserved1 = 0; 315 desig->len = snprintf(desig->desig, SPDK_SCSI_PORT_MAX_NAME_LENGTH, "%s", port->name); 316 len += sizeof(struct spdk_scsi_desig_desc) + desig->len; 317 318 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 319 320 /* Relative Target Port designator */ 321 desig = (struct spdk_scsi_desig_desc *)buf; 322 desig->code_set = SPDK_SPC_VPD_CODE_SET_BINARY; 323 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 324 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_RELATIVE_TARGET_PORT; 325 desig->association = SPDK_SPC_VPD_ASSOCIATION_TARGET_PORT; 326 desig->reserved0 = 0; 327 desig->piv = 1; 328 desig->reserved1 = 0; 329 desig->len = 4; 330 memset(desig->desig, 0, 2); /* Reserved */ 331 to_be16(&desig->desig[2], port->index); 332 len += sizeof(struct spdk_scsi_desig_desc) + desig->len; 333 334 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 335 336 /* Target port group designator */ 337 desig = (struct spdk_scsi_desig_desc *)buf; 338 desig->code_set = SPDK_SPC_VPD_CODE_SET_BINARY; 339 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 340 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_TARGET_PORT_GROUP; 341 desig->association = SPDK_SPC_VPD_ASSOCIATION_TARGET_PORT; 342 desig->reserved0 = 0; 343 desig->piv = 1; 344 desig->reserved1 = 0; 345 desig->len = 4; 346 memset(desig->desig, 0, 4); 347 len += sizeof(struct spdk_scsi_desig_desc) + desig->len; 348 349 buf += sizeof(struct spdk_scsi_desig_desc) + desig->len; 350 351 /* Logical unit group designator */ 352 desig = (struct spdk_scsi_desig_desc *)buf; 353 desig->code_set = SPDK_SPC_VPD_CODE_SET_BINARY; 354 desig->protocol_id = SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI; 355 desig->type = SPDK_SPC_VPD_IDENTIFIER_TYPE_LOGICAL_UNIT_GROUP; 356 desig->association = SPDK_SPC_VPD_ASSOCIATION_LOGICAL_UNIT; 357 desig->reserved0 = 0; 358 desig->piv = 1; 359 desig->reserved1 = 0; 360 desig->len = 4; 361 memset(desig->desig, 0, 2); /* Reserved */ 362 to_be16(&desig->desig[2], dev->id); 363 len += sizeof(struct spdk_scsi_desig_desc) + desig->len; 364 365 /* should not exceed the data_in buffer length */ 366 if (sizeof(struct spdk_scsi_vpd_page) + len > alloc_len) { 367 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 368 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 369 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 370 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 371 return -1; 372 } 373 to_be16(vpage->alloc_len, len); 374 375 break; 376 } 377 378 case SPDK_SPC_VPD_EXTENDED_INQUIRY_DATA: { 379 struct spdk_scsi_vpd_ext_inquiry *vext = (struct spdk_scsi_vpd_ext_inquiry *)vpage; 380 381 memset(vext, 0, sizeof(*vext)); 382 hlen = 4; 383 384 /* RTO(3) GRD_CHK(2) APP_CHK(1) REF_CHK(0) */ 385 386 /* GROUP_SUP(4) PRIOR_SUP(3) HEADSUP(2) ORDSUP(1) SIMPSUP(0) */ 387 vext->sup = SPDK_SCSI_VEXT_HEADSUP | SPDK_SCSI_VEXT_SIMPSUP; 388 389 /* NV_SUP(1) V_SUP(0) */ 390 391 /* Reserved[7-63] */ 392 393 len = 64 - hlen; 394 395 /* PAGE LENGTH */ 396 to_be16(vpage->alloc_len, len); 397 break; 398 } 399 400 case SPDK_SPC_VPD_MANAGEMENT_NETWORK_ADDRESSES: 401 /* PAGE LENGTH */ 402 hlen = 4; 403 404 to_be16(vpage->alloc_len, len); 405 break; 406 407 case SPDK_SPC_VPD_MODE_PAGE_POLICY: { 408 struct spdk_scsi_mpage_policy_desc *pdesc = 409 (struct spdk_scsi_mpage_policy_desc *)vpage->params; 410 411 hlen = 4; 412 413 /* Mode page policy descriptor 1 */ 414 415 /* POLICY PAGE CODE(5-0) */ 416 /* all page code */ 417 pdesc->page_code = 0x3f; 418 419 /* POLICY SUBPAGE CODE */ 420 /* all sub page */ 421 pdesc->sub_page_code = 0xff; 422 423 /* MLUS(7) MODE PAGE POLICY(1-0) */ 424 /* MLUS own copy */ 425 /* Shared MODE PAGE policy*/ 426 pdesc->policy = 0; 427 /* Reserved */ 428 pdesc->reserved = 0; 429 430 len += 4; 431 432 to_be16(vpage->alloc_len, len); 433 break; 434 } 435 436 case SPDK_SPC_VPD_SCSI_PORTS: { 437 /* PAGE LENGTH */ 438 hlen = 4; 439 440 /* Identification descriptor list */ 441 for (i = 0; i < dev->num_ports; i++) { 442 struct spdk_scsi_port_desc *sdesc; 443 struct spdk_scsi_tgt_port_desc *pdesc; 444 445 /* Identification descriptor N */ 446 sdesc = (struct spdk_scsi_port_desc *)&vpage->params[len]; 447 448 /* Reserved */ 449 sdesc->reserved = 0; 450 451 /* RELATIVE PORT IDENTIFIER */ 452 to_be16(&sdesc->rel_port_id, dev->port[i].index); 453 454 /* Reserved */ 455 sdesc->reserved2 = 0; 456 457 /* INITIATOR PORT TRANSPORTID LENGTH */ 458 sdesc->init_port_len = 0; 459 460 /* Reserved */ 461 sdesc->init_port_id = 0; 462 463 /* TARGET PORT DESCRIPTORS LENGTH */ 464 sdesc->tgt_desc_len = 0; 465 466 len += 12; 467 468 plen2 = 0; 469 /* Target port descriptor 1 */ 470 pdesc = (struct spdk_scsi_tgt_port_desc *)sdesc->tgt_desc; 471 472 /* PROTOCOL IDENTIFIER(7-4) CODE SET(3-0) */ 473 pdesc->code_set = 474 SPDK_SPC_PROTOCOL_IDENTIFIER_ISCSI << 4 | 475 SPDK_SPC_VPD_CODE_SET_UTF8; 476 477 /* PIV(7) ASSOCIATION(5-4) IDENTIFIER TYPE(3-0) */ 478 pdesc->desig_type = SPDK_SPC_VPD_DESIG_PIV | 479 SPDK_SPC_VPD_ASSOCIATION_TARGET_PORT << 4 | 480 SPDK_SPC_VPD_IDENTIFIER_TYPE_SCSI_NAME; 481 482 /* Reserved */ 483 pdesc->reserved = 0; 484 485 /* IDENTIFIER */ 486 plen = snprintf((char *)pdesc->designator, 487 SPDK_SCSI_PORT_MAX_NAME_LENGTH, "%s", 488 dev->port[i].name); 489 pdesc->len = plen; 490 491 plen2 += 4 + plen; 492 493 /* TARGET PORT DESCRIPTORS LENGTH */ 494 to_be16(&sdesc->tgt_desc_len, plen2); 495 496 len += plen2; 497 } 498 499 to_be16(vpage->alloc_len, len); 500 break; 501 } 502 503 case SPDK_SPC_VPD_BLOCK_LIMITS: { 504 /* PAGE LENGTH */ 505 506 memset(&data[4], 0, 60); 507 508 hlen = 4; 509 510 /* WSNZ(0) */ 511 /* support zero length in WRITE SAME */ 512 513 /* MAXIMUM COMPARE AND WRITE LENGTH */ 514 blocks = SPDK_WORK_ATS_BLOCK_SIZE / bdev->blocklen; 515 516 if (blocks > 0xff) 517 blocks = 0xff; 518 519 data[5] = (uint8_t)blocks; 520 521 /* force align to 4KB */ 522 if (bdev->blocklen < 4096) { 523 optimal_blocks = 4096 / bdev->blocklen; 524 } else { 525 optimal_blocks = 1; 526 } 527 528 /* OPTIMAL TRANSFER LENGTH GRANULARITY */ 529 to_be16(&data[6], optimal_blocks); 530 531 blocks = SPDK_WORK_BLOCK_SIZE / bdev->blocklen; 532 533 /* MAXIMUM TRANSFER LENGTH */ 534 to_be32(&data[8], blocks); 535 /* OPTIMAL TRANSFER LENGTH */ 536 to_be32(&data[12], blocks); 537 538 /* MAXIMUM PREFETCH XDREAD XDWRITE TRANSFER LENGTH */ 539 540 len = 20 - hlen; 541 542 if (bdev->thin_provisioning) { 543 /* 544 * MAXIMUM UNMAP LBA COUNT: indicates the 545 * maximum number of LBAs that may be 546 * unmapped by an UNMAP command. 547 */ 548 to_be32(&data[20], g_spdk_scsi.scsi_params.max_unmap_lba_count); 549 550 /* 551 * MAXIMUM UNMAP BLOCK DESCRIPTOR COUNT: 552 * indicates the maximum number of UNMAP 553 * block descriptors that shall be contained 554 * in the parameter data transferred to the 555 * device server for an UNMAP command. 556 */ 557 if (bdev->max_unmap_bdesc_count < 558 g_spdk_scsi.scsi_params.max_unmap_block_descriptor_count) 559 to_be32(&data[24], bdev->max_unmap_bdesc_count); 560 else 561 to_be32(&data[24], g_spdk_scsi.scsi_params.max_unmap_block_descriptor_count); 562 563 /* 564 * OPTIMAL UNMAP GRANULARITY: indicates the 565 * optimal granularity in logical blocks 566 * for unmap request. 567 */ 568 to_be32(&data[28], g_spdk_scsi.scsi_params.optimal_unmap_granularity); 569 570 /* 571 * UNMAP GRANULARITY ALIGNMENT: indicates the 572 * LBA of the first logical block to which the 573 * OPTIMAL UNMAP GRANULARITY field applies. 574 */ 575 /* not specified */ 576 to_be32(&data[32], g_spdk_scsi.scsi_params.unmap_granularity_alignment); 577 578 /* 579 * UGAVALID(7): bit set to one indicates that 580 * the UNMAP GRANULARITY ALIGNMENT field is 581 * valid. 582 */ 583 /* not specified */ 584 if (g_spdk_scsi.scsi_params.ugavalid) 585 data[32] |= 1 << 7; 586 587 /* 588 * MAXIMUM WRITE SAME LENGTH: indicates the 589 * maximum number of contiguous logical blocks 590 * that the device server allows to be unmapped 591 * or written in a single WRITE SAME command. 592 */ 593 to_be64(&data[36], g_spdk_scsi.scsi_params.max_write_same_length); 594 595 /* Reserved */ 596 /* not specified */ 597 len = 64 - hlen; 598 } 599 600 to_be16(vpage->alloc_len, len); 601 break; 602 } 603 604 case SPDK_SPC_VPD_BLOCK_DEV_CHARS: { 605 /* PAGE LENGTH */ 606 hlen = 4; 607 len = 64 - hlen; 608 609 to_be16(&data[4], DEFAULT_DISK_ROTATION_RATE); 610 611 /* Reserved */ 612 data[6] = 0; 613 /* NOMINAL FORM FACTOR(3-0) */ 614 data[7] = DEFAULT_DISK_FORM_FACTOR << 4; 615 /* Reserved */ 616 memset(&data[8], 0, 64 - 8); 617 618 to_be16(vpage->alloc_len, len); 619 break; 620 } 621 622 case SPDK_SPC_VPD_BLOCK_THIN_PROVISION: { 623 if (!bdev->thin_provisioning) { 624 SPDK_ERRLOG("unsupported INQUIRY VPD page 0x%x\n", pc); 625 goto inq_error; 626 } 627 628 hlen = 4; 629 len = 7; 630 631 /* 632 * PAGE LENGTH : if the DP bit is set to one, then the 633 * page length shall be set 0004h. 634 */ 635 to_be16(&data[2], 0x0004); 636 637 /* 638 * THRESHOLD EXPONENT : it indicates the threshold set 639 * size in LBAs as a power of 2( i.e., the threshold 640 * set size = 2 ^ (threshold exponent). 641 */ 642 data[4] = 0; 643 644 /* 645 * Set the LBPU bit to indicate the support for UNMAP 646 * command. 647 */ 648 data[5] |= SPDK_SCSI_UNMAP_LBPU; 649 650 /* 651 * Set the provisioning type to thin provision. 652 */ 653 data[6] = SPDK_SCSI_UNMAP_THIN_PROVISIONING; 654 655 to_be16(vpage->alloc_len, len); 656 break; 657 } 658 659 default: 660 if (pc >= 0xc0 && pc <= 0xff) { 661 SPDK_TRACELOG(SPDK_TRACE_SCSI, "Vendor specific INQUIRY VPD page 0x%x\n", pc); 662 } else { 663 SPDK_ERRLOG("unsupported INQUIRY VPD page 0x%x\n", pc); 664 } 665 goto inq_error; 666 } 667 } else { 668 struct spdk_scsi_cdb_inquiry_data *inqdata = 669 (struct spdk_scsi_cdb_inquiry_data *)data; 670 671 /* Standard INQUIRY data */ 672 /* PERIPHERAL QUALIFIER(7-5) PERIPHERAL DEVICE TYPE(4-0) */ 673 inqdata->peripheral = pd; 674 675 /* RMB(7) */ 676 inqdata->rmb = 0; 677 678 /* VERSION */ 679 /* See SPC3/SBC2/MMC4/SAM2 for more details */ 680 inqdata->version = SPDK_SPC_VERSION_SPC3; 681 682 /* NORMACA(5) HISUP(4) RESPONSE DATA FORMAT(3-0) */ 683 /* format 2 */ /* hierarchical support */ 684 inqdata->response = 2 | 1 << 4; 685 686 hlen = 5; 687 688 /* SCCS(7) ACC(6) TPGS(5-4) 3PC(3) PROTECT(0) */ 689 /* Not support TPGS */ 690 inqdata->flags = 0; 691 692 /* MULTIP */ 693 inqdata->flags2 = 0x10; 694 695 /* WBUS16(5) SYNC(4) LINKED(3) CMDQUE(1) VS(0) */ 696 /* CMDQUE */ 697 inqdata->flags3 = 0x2; 698 699 /* T10 VENDOR IDENTIFICATION */ 700 spdk_strcpy_pad(inqdata->t10_vendor_id, DEFAULT_DISK_VENDOR, 8, ' '); 701 702 /* PRODUCT IDENTIFICATION */ 703 spdk_strcpy_pad(inqdata->product_id, bdev->product_name, 16, ' '); 704 705 /* PRODUCT REVISION LEVEL */ 706 spdk_strcpy_pad(inqdata->product_rev, DEFAULT_DISK_REVISION, 4, ' '); 707 708 /* 709 * Standard inquiry data ends here. Only populate remaining fields if alloc_len 710 * indicates enough space to hold it. 711 */ 712 len = INQUIRY_OFFSET(product_rev) - 5; 713 714 if (alloc_len >= INQUIRY_OFFSET(vendor)) { 715 /* Vendor specific */ 716 memset(inqdata->vendor, 0x20, 20); 717 len += sizeof(inqdata->vendor); 718 } 719 720 if (alloc_len >= INQUIRY_OFFSET(ius)) { 721 /* CLOCKING(3-2) QAS(1) IUS(0) */ 722 inqdata->ius = 0; 723 len += sizeof(inqdata->ius); 724 } 725 726 if (alloc_len >= INQUIRY_OFFSET(reserved)) { 727 /* Reserved */ 728 inqdata->reserved = 0; 729 len += sizeof(inqdata->reserved); 730 } 731 732 /* VERSION DESCRIPTOR 1-8 */ 733 if (alloc_len >= INQUIRY_OFFSET(reserved) + 2) { 734 to_be16(&inqdata->desc[0], 0x0960); 735 len += 2; 736 } 737 738 if (alloc_len >= INQUIRY_OFFSET(reserved) + 4) { 739 to_be16(&inqdata->desc[2], 0x0300); /* SPC-3 (no version claimed) */ 740 len += 2; 741 } 742 743 if (alloc_len >= INQUIRY_OFFSET(reserved) + 6) { 744 to_be16(&inqdata->desc[4], 0x320); /* SBC-2 (no version claimed) */ 745 len += 2; 746 } 747 748 if (alloc_len >= INQUIRY_OFFSET(reserved) + 8) { 749 to_be16(&inqdata->desc[6], 0x0040); /* SAM-2 (no version claimed) */ 750 len += 2; 751 } 752 753 /* 754 * We only fill out 4 descriptors, but if the allocation length goes past 755 * that, zero the remaining bytes. This fixes some SCSI compliance tests 756 * which expect a full 96 bytes to be returned, including the unpopulated 757 * version descriptors 5-8 (4 * 2 = 8 bytes) plus the 22 bytes of reserved 758 * space (bytes 74-95) - for a total of 30 bytes. 759 */ 760 if (alloc_len > INQUIRY_OFFSET(reserved) + 8) { 761 i = alloc_len - (INQUIRY_OFFSET(reserved) + 8); 762 if (i > 30) { 763 i = 30; 764 } 765 memset(&inqdata->desc[8], 0, i); 766 len += i; 767 } 768 769 /* ADDITIONAL LENGTH */ 770 inqdata->add_len = len; 771 } 772 773 return hlen + len; 774 775 inq_error: 776 task->data_transferred = 0; 777 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 778 SPDK_SCSI_SENSE_NO_SENSE, 779 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 780 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 781 return -1; 782 } 783 784 static void 785 mode_sense_page_init(uint8_t *buf, int len, int page, int subpage) 786 { 787 if (!buf) 788 return; 789 790 memset(buf, 0, len); 791 if (subpage != 0) { 792 buf[0] = page | 0x40; /* PAGE + SPF=1 */ 793 buf[1] = subpage; 794 to_be16(&buf[2], len - 4); 795 } else { 796 buf[0] = page; 797 buf[1] = len - 2; 798 } 799 } 800 801 static int 802 spdk_bdev_scsi_mode_sense_page(struct spdk_bdev *bdev, 803 uint8_t *cdb, int pc, int page, int subpage, 804 uint8_t *data) 805 { 806 uint8_t *cp = data; 807 int len = 0; 808 int plen; 809 int i; 810 811 if (pc == 0x00) { 812 /* Current values */ 813 } else if (pc == 0x01) { 814 /* Changeable values not supported */ 815 return -1; 816 } else if (pc == 0x02) { 817 /* Default values */ 818 } else { 819 /* Saved values not supported */ 820 return -1; 821 } 822 823 switch (page) { 824 case 0x00: 825 /* Vendor specific */ 826 break; 827 case 0x01: 828 /* Read-Write Error Recovery */ 829 SPDK_TRACELOG(SPDK_TRACE_SCSI, 830 "MODE_SENSE Read-Write Error Recovery\n"); 831 if (subpage != 0x00) 832 break; 833 plen = 0x0a + 2; 834 mode_sense_page_init(cp, plen, page, subpage); 835 len += plen; 836 break; 837 case 0x02: 838 /* Disconnect-Reconnect */ 839 SPDK_TRACELOG(SPDK_TRACE_SCSI, 840 "MODE_SENSE Disconnect-Reconnect\n"); 841 if (subpage != 0x00) 842 break; 843 plen = 0x0e + 2; 844 mode_sense_page_init(cp, plen, page, subpage); 845 len += plen; 846 break; 847 case 0x03: 848 /* Obsolete (Format Device) */ 849 break; 850 case 0x04: 851 /* Obsolete (Rigid Disk Geometry) */ 852 break; 853 case 0x05: 854 /* Obsolete (Rigid Disk Geometry) */ 855 break; 856 case 0x06: 857 /* Reserved */ 858 break; 859 case 0x07: 860 /* Verify Error Recovery */ 861 SPDK_TRACELOG(SPDK_TRACE_SCSI, 862 "MODE_SENSE Verify Error Recovery\n"); 863 864 if (subpage != 0x00) 865 break; 866 867 plen = 0x0a + 2; 868 mode_sense_page_init(cp, plen, page, subpage); 869 len += plen; 870 break; 871 case 0x08: { 872 /* Caching */ 873 SPDK_TRACELOG(SPDK_TRACE_SCSI, "MODE_SENSE Caching\n"); 874 if (subpage != 0x00) 875 break; 876 877 plen = 0x12 + 2; 878 mode_sense_page_init(cp, plen, page, subpage); 879 880 if (cp && bdev->write_cache) 881 cp[2] |= 0x4; /* WCE */ 882 883 /* Read Cache Disable (RCD) = 1 */ 884 if (cp) 885 cp[2] |= 0x1; 886 887 len += plen; 888 break; 889 } 890 case 0x09: 891 /* Obsolete */ 892 break; 893 case 0x0a: 894 switch (subpage) { 895 case 0x00: 896 /* Control */ 897 SPDK_TRACELOG(SPDK_TRACE_SCSI, 898 "MODE_SENSE Control\n"); 899 plen = 0x0a + 2; 900 mode_sense_page_init(cp, plen, page, subpage); 901 len += plen; 902 break; 903 case 0x01: 904 /* Control Extension */ 905 SPDK_TRACELOG(SPDK_TRACE_SCSI, 906 "MODE_SENSE Control Extension\n"); 907 plen = 0x1c + 4; 908 mode_sense_page_init(cp, plen, page, subpage); 909 len += plen; 910 break; 911 case 0xff: 912 /* All subpages */ 913 len += spdk_bdev_scsi_mode_sense_page(bdev, 914 cdb, pc, page, 915 0x00, 916 cp ? &cp[len] : NULL); 917 len += spdk_bdev_scsi_mode_sense_page(bdev, 918 cdb, pc, page, 919 0x01, 920 cp ? &cp[len] : NULL); 921 break; 922 default: 923 /* 0x02-0x3e: Reserved */ 924 break; 925 } 926 break; 927 case 0x0b: 928 /* Obsolete (Medium Types Supported) */ 929 break; 930 case 0x0c: 931 /* Obsolete (Notch And Partitio) */ 932 break; 933 case 0x0d: 934 /* Obsolete */ 935 break; 936 case 0x0e: 937 case 0x0f: 938 /* Reserved */ 939 break; 940 case 0x10: 941 /* XOR Control */ 942 SPDK_TRACELOG(SPDK_TRACE_SCSI, "MODE_SENSE XOR Control\n"); 943 if (subpage != 0x00) 944 break; 945 plen = 0x16 + 2; 946 mode_sense_page_init(cp, plen, page, subpage); 947 len += plen; 948 break; 949 case 0x11: 950 case 0x12: 951 case 0x13: 952 /* Reserved */ 953 break; 954 case 0x14: 955 /* Enclosure Services Management */ 956 break; 957 case 0x15: 958 case 0x16: 959 case 0x17: 960 /* Reserved */ 961 break; 962 case 0x18: 963 /* Protocol-Specific LUN */ 964 break; 965 case 0x19: 966 /* Protocol-Specific Port */ 967 break; 968 case 0x1a: 969 /* Power Condition */ 970 SPDK_TRACELOG(SPDK_TRACE_SCSI, 971 "MODE_SENSE Power Condition\n"); 972 if (subpage != 0x00) 973 break; 974 plen = 0x0a + 2; 975 mode_sense_page_init(cp, plen, page, subpage); 976 len += plen; 977 break; 978 case 0x1b: 979 /* Reserved */ 980 break; 981 case 0x1c: 982 /* Informational Exceptions Control */ 983 SPDK_TRACELOG(SPDK_TRACE_SCSI, 984 "MODE_SENSE Informational Exceptions Control\n"); 985 if (subpage != 0x00) 986 break; 987 988 plen = 0x0a + 2; 989 mode_sense_page_init(cp, plen, page, subpage); 990 len += plen; 991 break; 992 case 0x1d: 993 case 0x1e: 994 case 0x1f: 995 /* Reserved */ 996 break; 997 case 0x20: 998 case 0x21: 999 case 0x22: 1000 case 0x23: 1001 case 0x24: 1002 case 0x25: 1003 case 0x26: 1004 case 0x27: 1005 case 0x28: 1006 case 0x29: 1007 case 0x2a: 1008 case 0x2b: 1009 case 0x2c: 1010 case 0x2d: 1011 case 0x2e: 1012 case 0x2f: 1013 case 0x30: 1014 case 0x31: 1015 case 0x32: 1016 case 0x33: 1017 case 0x34: 1018 case 0x35: 1019 case 0x36: 1020 case 0x37: 1021 case 0x38: 1022 case 0x39: 1023 case 0x3a: 1024 case 0x3b: 1025 case 0x3c: 1026 case 0x3d: 1027 case 0x3e: 1028 /* Vendor-specific */ 1029 break; 1030 case 0x3f: 1031 switch (subpage) { 1032 case 0x00: 1033 /* All mode pages */ 1034 for (i = 0x00; i < 0x3e; i ++) { 1035 len += spdk_bdev_scsi_mode_sense_page( 1036 bdev, cdb, pc, i, 0x00, 1037 cp ? &cp[len] : NULL); 1038 } 1039 break; 1040 case 0xff: 1041 /* All mode pages and subpages */ 1042 for (i = 0x00; i < 0x3e; i ++) { 1043 len += spdk_bdev_scsi_mode_sense_page( 1044 bdev, cdb, pc, i, 0x00, 1045 cp ? &cp[len] : NULL); 1046 } 1047 for (i = 0x00; i < 0x3e; i ++) { 1048 len += spdk_bdev_scsi_mode_sense_page( 1049 bdev, cdb, pc, i, 0xff, 1050 cp ? &cp[len] : NULL); 1051 } 1052 break; 1053 default: 1054 /* 0x01-0x3e: Reserved */ 1055 break; 1056 } 1057 } 1058 1059 return len; 1060 } 1061 1062 static int 1063 spdk_bdev_scsi_mode_sense(struct spdk_bdev *bdev, int md, 1064 uint8_t *cdb, int dbd, int llbaa, int pc, 1065 int page, int subpage, uint8_t *data) 1066 { 1067 uint8_t *hdr, *bdesc, *pages; 1068 int hlen; 1069 int blen; 1070 int plen, total; 1071 1072 assert(md == 6 || md == 10); 1073 1074 if (md == 6) { 1075 hlen = 4; 1076 blen = 8; /* For MODE SENSE 6 only short LBA */ 1077 } else { 1078 hlen = 8; 1079 blen = llbaa ? 16 : 8; 1080 } 1081 1082 if (dbd) { 1083 blen = 0; 1084 } 1085 1086 pages = data ? &data[hlen + blen] : NULL; 1087 plen = spdk_bdev_scsi_mode_sense_page(bdev, cdb, pc, page, 1088 subpage, 1089 pages); 1090 if (plen < 0) { 1091 return -1; 1092 } 1093 1094 total = hlen + blen + plen; 1095 if (data == NULL) 1096 return total; 1097 1098 hdr = &data[0]; 1099 if (hlen == 4) { 1100 hdr[0] = total - 1; /* Mode Data Length */ 1101 hdr[1] = 0; /* Medium Type */ 1102 hdr[2] = 0; /* Device-Specific Parameter */ 1103 hdr[3] = blen; /* Block Descripter Length */ 1104 } else { 1105 to_be16(&hdr[0], total - 2); /* Mode Data Length */ 1106 hdr[2] = 0; /* Medium Type */ 1107 hdr[3] = 0; /* Device-Specific Parameter */ 1108 hdr[4] = llbaa ? 0x1 : 0; /* Long/short LBA */ 1109 hdr[5] = 0; /* Reserved */ 1110 to_be16(&hdr[6], blen); /* Block Descripter Length */ 1111 } 1112 1113 bdesc = &data[hlen]; 1114 if (blen == 16) { 1115 /* Number of Blocks */ 1116 to_be64(&bdesc[0], bdev->blockcnt); 1117 /* Reserved */ 1118 memset(&bdesc[8], 0, 4); 1119 /* Block Length */ 1120 to_be32(&bdesc[12], bdev->blocklen); 1121 } else if (blen == 8) { 1122 /* Number of Blocks */ 1123 if (bdev->blockcnt > 0xffffffffULL) 1124 memset(&bdesc[0], 0xff, 4); 1125 else 1126 to_be32(&bdesc[0], bdev->blockcnt); 1127 1128 /* Block Length */ 1129 to_be32(&bdesc[4], bdev->blocklen); 1130 } 1131 1132 return total; 1133 } 1134 1135 static int 1136 spdk_bdev_scsi_mode_select_page(struct spdk_bdev *bdev, 1137 uint8_t *cdb, int pf, int sp, 1138 uint8_t *data, size_t len) 1139 { 1140 size_t hlen, plen; 1141 int spf, page, subpage; 1142 int rc; 1143 1144 /* vendor specific */ 1145 if (pf == 0) { 1146 return 0; 1147 } 1148 1149 if (len < 1) { 1150 return 0; 1151 } 1152 1153 spf = !!(data[0] & 0x40); 1154 page = data[0] & 0x3f; 1155 if (spf) { 1156 /* Sub_page mode page format */ 1157 hlen = 4; 1158 if (len < hlen) 1159 return 0; 1160 subpage = data[1]; 1161 1162 plen = from_be16(&data[2]); 1163 } else { 1164 /* Page_0 mode page format */ 1165 hlen = 2; 1166 if (len < hlen) 1167 return 0; 1168 subpage = 0; 1169 plen = data[1]; 1170 } 1171 1172 plen += hlen; 1173 if (len < plen) { 1174 return 0; 1175 } 1176 1177 switch (page) { 1178 case 0x08: { /* Caching */ 1179 //int wce; 1180 1181 SPDK_TRACELOG(SPDK_TRACE_SCSI, "MODE_SELECT Caching\n"); 1182 if (subpage != 0x00) 1183 break; 1184 1185 if (plen != 0x12 + hlen) { 1186 /* unknown format */ 1187 break; 1188 } 1189 1190 // TODO: 1191 //wce = data[2] & 0x4; /* WCE */ 1192 1193 //fd = bdev->fd; 1194 // 1195 //rc = fcntl(fd, F_GETFL, 0); 1196 //if (rc != -1) { 1197 // if (wce) { 1198 // SPDK_TRACELOG(SPDK_TRACE_SCSI, "MODE_SELECT Writeback cache enable\n"); 1199 // rc = fcntl(fd, F_SETFL, (rc & ~O_FSYNC)); 1200 // bdev->write_cache = 1; 1201 // } else { 1202 // rc = fcntl(fd, F_SETFL, (rc | O_FSYNC)); 1203 // bdev->write_cache = 0; 1204 // } 1205 //} 1206 1207 break; 1208 } 1209 default: 1210 /* not supported */ 1211 break; 1212 } 1213 1214 len -= plen; 1215 if (len != 0) { 1216 rc = spdk_bdev_scsi_mode_select_page(bdev, cdb, pf, sp, &data[plen], len); 1217 if (rc < 0) { 1218 return rc; 1219 } 1220 } 1221 return 0; 1222 } 1223 1224 static void 1225 spdk_bdev_scsi_task_complete(spdk_event_t event) 1226 { 1227 struct spdk_bdev_io *bdev_io = spdk_event_get_arg2(event); 1228 struct spdk_scsi_task *task = spdk_event_get_arg1(event); 1229 enum spdk_bdev_io_status status = bdev_io->status; 1230 1231 if (task->type == SPDK_SCSI_TASK_TYPE_CMD) { 1232 if (status == SPDK_BDEV_IO_STATUS_SUCCESS) { 1233 task->status = SPDK_SCSI_STATUS_GOOD; 1234 } else { 1235 int sc, sk, asc, ascq; 1236 1237 switch (status) { 1238 case SPDK_BDEV_IO_STATUS_NVME_ERROR: 1239 spdk_scsi_nvme_translate(bdev_io, &sc, &sk, &asc, &ascq); 1240 break; 1241 case SPDK_BDEV_IO_STATUS_SCSI_ERROR: 1242 sc = bdev_io->error.scsi.sc; 1243 sk = bdev_io->error.scsi.sk; 1244 asc = bdev_io->error.scsi.asc; 1245 ascq = bdev_io->error.scsi.ascq; 1246 break; 1247 default: 1248 sc = SPDK_SCSI_STATUS_CHECK_CONDITION; 1249 sk = SPDK_SCSI_SENSE_ABORTED_COMMAND; 1250 asc = SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE; 1251 ascq = SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE; 1252 break; 1253 } 1254 spdk_scsi_task_set_status(task, sc, sk, asc, ascq); 1255 } 1256 1257 /* command completed. remove from outstanding task list */ 1258 TAILQ_REMOVE(&task->lun->tasks, task, scsi_link); 1259 } else if (task->type == SPDK_SCSI_TASK_TYPE_MANAGE) { 1260 if (status == SPDK_BDEV_IO_STATUS_SUCCESS) 1261 task->response = SPDK_SCSI_TASK_MGMT_RESP_SUCCESS; 1262 if (task->function == SPDK_SCSI_TASK_FUNC_LUN_RESET) { 1263 spdk_scsi_lun_clear_all(task->lun); 1264 } 1265 } 1266 if (bdev_io->type == SPDK_BDEV_IO_TYPE_READ && task->iovs != bdev_io->u.read.iovs) { 1267 assert(task->iovcnt == bdev_io->u.read.iovcnt); 1268 memcpy(task->iovs, bdev_io->u.read.iovs, sizeof(task->iovs[0]) * task->iovcnt); 1269 } 1270 1271 spdk_scsi_lun_complete_task(task->lun, task); 1272 } 1273 1274 static int 1275 spdk_bdev_scsi_read(struct spdk_bdev *bdev, 1276 struct spdk_scsi_task *task, uint64_t lba, 1277 uint32_t len) 1278 { 1279 uint64_t maxlba; 1280 uint64_t llen; 1281 uint64_t blen; 1282 uint64_t offset; 1283 uint64_t nbytes; 1284 1285 maxlba = bdev->blockcnt; 1286 blen = bdev->blocklen; 1287 lba += (task->offset / blen); 1288 offset = lba * blen; 1289 nbytes = task->length; 1290 llen = task->length / blen; 1291 1292 SPDK_TRACELOG(SPDK_TRACE_SCSI, 1293 "Read: max=%"PRIu64", lba=%"PRIu64", len=%"PRIu64"\n", 1294 maxlba, lba, llen); 1295 1296 if (lba >= maxlba || llen > maxlba || lba > (maxlba - llen)) { 1297 SPDK_ERRLOG("end of media\n"); 1298 return -1; 1299 } 1300 task->blockdev_io = spdk_bdev_readv(bdev, task->ch, task->iovs, 1301 task->iovcnt, offset, nbytes, 1302 spdk_bdev_scsi_task_complete, task); 1303 if (!task->blockdev_io) { 1304 SPDK_ERRLOG("spdk_bdev_readv() failed\n"); 1305 return -1; 1306 } 1307 1308 task->data_transferred = nbytes; 1309 1310 return 0; 1311 } 1312 1313 static int 1314 spdk_bdev_scsi_write(struct spdk_bdev *bdev, 1315 struct spdk_scsi_task *task, uint64_t lba, uint32_t len) 1316 { 1317 uint64_t maxlba; 1318 uint64_t llen; 1319 uint64_t blen; 1320 uint64_t offset; 1321 uint64_t nbytes; 1322 struct spdk_scsi_task *primary = task->parent; 1323 1324 if (len == 0) { 1325 task->data_transferred = 0; 1326 return -1; 1327 } 1328 1329 maxlba = bdev->blockcnt; 1330 llen = (uint64_t) len; 1331 blen = bdev->blocklen; 1332 offset = lba * blen; 1333 nbytes = llen * blen; 1334 1335 SPDK_TRACELOG(SPDK_TRACE_SCSI, 1336 "Write: max=%"PRIu64", lba=%"PRIu64", len=%u\n", 1337 maxlba, lba, len); 1338 1339 if (lba >= maxlba || llen > maxlba || lba > (maxlba - llen)) { 1340 SPDK_ERRLOG("end of media\n"); 1341 return -1; 1342 } 1343 1344 if (nbytes > task->transfer_len) { 1345 SPDK_ERRLOG("nbytes(%zu) > transfer_len(%u)\n", 1346 (size_t)nbytes, task->transfer_len); 1347 return -1; 1348 } 1349 1350 offset += task->offset; 1351 task->blockdev_io = spdk_bdev_writev(bdev, task->ch, task->iovs, 1352 task->iovcnt, offset, task->length, 1353 spdk_bdev_scsi_task_complete, 1354 task); 1355 1356 if (!task->blockdev_io) { 1357 SPDK_ERRLOG("spdk_bdev_writev failed\n"); 1358 return -1; 1359 } else { 1360 if (!primary) { 1361 task->data_transferred += task->length; 1362 } else { 1363 primary->data_transferred += task->length; 1364 } 1365 } 1366 1367 SPDK_TRACELOG(SPDK_TRACE_SCSI, "Wrote %"PRIu64"/%"PRIu64" bytes\n", 1368 (uint64_t)task->length, nbytes); 1369 return 0; 1370 } 1371 1372 static int 1373 spdk_bdev_scsi_sync(struct spdk_bdev *bdev, struct spdk_scsi_task *task, 1374 uint64_t lba, uint32_t len) 1375 { 1376 uint64_t maxlba; 1377 uint64_t llen; 1378 uint64_t blen; 1379 uint64_t offset; 1380 uint64_t nbytes; 1381 1382 if (len == 0) { 1383 return SPDK_SCSI_TASK_COMPLETE; 1384 } 1385 1386 maxlba = bdev->blockcnt; 1387 llen = len; 1388 blen = bdev->blocklen; 1389 offset = lba * blen; 1390 nbytes = llen * blen; 1391 1392 if (lba >= maxlba || llen > maxlba || lba > (maxlba - llen)) { 1393 SPDK_ERRLOG("end of media\n"); 1394 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1395 SPDK_SCSI_SENSE_NO_SENSE, 1396 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1397 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1398 return SPDK_SCSI_TASK_COMPLETE; 1399 } 1400 1401 task->blockdev_io = spdk_bdev_flush(bdev, task->ch, offset, nbytes, 1402 spdk_bdev_scsi_task_complete, task); 1403 1404 if (!task->blockdev_io) { 1405 SPDK_ERRLOG("spdk_bdev_flush() failed\n"); 1406 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1407 SPDK_SCSI_SENSE_NO_SENSE, 1408 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1409 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1410 return SPDK_SCSI_TASK_COMPLETE; 1411 } 1412 task->data_transferred = 0; 1413 task->status = SPDK_SCSI_STATUS_GOOD; 1414 return SPDK_SCSI_TASK_PENDING; 1415 } 1416 1417 static int 1418 spdk_bdev_scsi_readwrite(struct spdk_bdev *bdev, 1419 struct spdk_scsi_task *task, 1420 uint64_t lba, uint32_t xfer_len) 1421 { 1422 int rc; 1423 1424 if (task->dxfer_dir == SPDK_SCSI_DIR_FROM_DEV) { 1425 rc = spdk_bdev_scsi_read(bdev, task, lba, xfer_len); 1426 } else if (task->dxfer_dir == SPDK_SCSI_DIR_TO_DEV) { 1427 rc = spdk_bdev_scsi_write(bdev, task, lba, xfer_len); 1428 } else { 1429 SPDK_ERRLOG("Incorrect data direction\n"); 1430 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1431 SPDK_SCSI_SENSE_NO_SENSE, 1432 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1433 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1434 return SPDK_SCSI_TASK_COMPLETE; 1435 } 1436 1437 if (rc < 0) { 1438 SPDK_ERRLOG("disk op (rw) failed\n"); 1439 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1440 SPDK_SCSI_SENSE_NO_SENSE, 1441 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1442 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1443 1444 return SPDK_SCSI_TASK_COMPLETE; 1445 } else { 1446 task->status = SPDK_SCSI_STATUS_GOOD; 1447 } 1448 1449 return SPDK_SCSI_TASK_PENDING; 1450 } 1451 1452 static int 1453 spdk_bdev_scsi_unmap(struct spdk_bdev *bdev, 1454 struct spdk_scsi_task *task) 1455 { 1456 1457 uint8_t *data; 1458 uint16_t bdesc_data_len, bdesc_count; 1459 1460 data = (uint8_t *)task->iovs[0].iov_base; 1461 1462 /* 1463 * The UNMAP BLOCK DESCRIPTOR DATA LENGTH field specifies the length in 1464 * bytes of the UNMAP block descriptors that are available to be 1465 * transferred from the Data-Out Buffer. The unmap block descriptor data 1466 * length should be a multiple of 16. If the unmap block descriptor data 1467 * length is not a multiple of 16, then the last unmap block descriptor 1468 * is incomplete and shall be ignored. 1469 */ 1470 bdesc_data_len = from_be16(&data[2]); 1471 bdesc_count = bdesc_data_len / 16; 1472 1473 if (bdesc_count > bdev->max_unmap_bdesc_count) { 1474 SPDK_ERRLOG("Error - supported unmap block descriptor count limit" 1475 " is %u\n", bdev->max_unmap_bdesc_count); 1476 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1477 SPDK_SCSI_SENSE_NO_SENSE, 1478 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1479 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1480 return SPDK_SCSI_TASK_COMPLETE; 1481 } 1482 1483 task->blockdev_io = spdk_bdev_unmap(bdev, task->ch, (struct spdk_scsi_unmap_bdesc *)&data[8], 1484 bdesc_count, spdk_bdev_scsi_task_complete, 1485 task); 1486 1487 if (!task->blockdev_io) { 1488 SPDK_ERRLOG("SCSI Unmapping failed\n"); 1489 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1490 SPDK_SCSI_SENSE_NO_SENSE, 1491 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1492 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1493 return SPDK_SCSI_TASK_COMPLETE; 1494 } 1495 1496 return SPDK_SCSI_TASK_PENDING; 1497 } 1498 1499 static int 1500 spdk_bdev_scsi_process_block(struct spdk_bdev *bdev, 1501 struct spdk_scsi_task *task) 1502 { 1503 uint64_t lba; 1504 uint32_t xfer_len; 1505 uint32_t len = 0; 1506 uint8_t *cdb = task->cdb; 1507 uint8_t *data; 1508 1509 /* XXX: We need to support FUA bit for writes! */ 1510 switch (cdb[0]) { 1511 case SPDK_SBC_READ_6: 1512 case SPDK_SBC_WRITE_6: 1513 lba = (uint64_t)cdb[1] << 16; 1514 lba |= (uint64_t)cdb[2] << 8; 1515 lba |= (uint64_t)cdb[3]; 1516 xfer_len = cdb[4]; 1517 if (xfer_len == 0) { 1518 xfer_len = 256; 1519 } 1520 return spdk_bdev_scsi_readwrite(bdev, task, lba, xfer_len); 1521 1522 case SPDK_SBC_READ_10: 1523 case SPDK_SBC_WRITE_10: 1524 lba = from_be32(&cdb[2]); 1525 xfer_len = from_be16(&cdb[7]); 1526 return spdk_bdev_scsi_readwrite(bdev, task, lba, xfer_len); 1527 1528 case SPDK_SBC_READ_12: 1529 case SPDK_SBC_WRITE_12: 1530 lba = from_be32(&cdb[2]); 1531 xfer_len = from_be32(&cdb[6]); 1532 return spdk_bdev_scsi_readwrite(bdev, task, lba, xfer_len); 1533 1534 case SPDK_SBC_READ_16: 1535 case SPDK_SBC_WRITE_16: 1536 lba = from_be64(&cdb[2]); 1537 xfer_len = from_be32(&cdb[10]); 1538 return spdk_bdev_scsi_readwrite(bdev, task, lba, xfer_len); 1539 1540 case SPDK_SBC_READ_CAPACITY_10: { 1541 uint8_t buffer[8]; 1542 1543 if (bdev->blockcnt - 1 > 0xffffffffULL) { 1544 memset(buffer, 0xff, 4); 1545 } else { 1546 to_be32(buffer, bdev->blockcnt - 1); 1547 } 1548 to_be32(&buffer[4], bdev->blocklen); 1549 1550 len = task->length < 8 ? task->length : sizeof(buffer); 1551 if (len) { 1552 data = spdk_scsi_task_alloc_data(task, len); 1553 memcpy(data, buffer, len); 1554 } 1555 1556 task->data_transferred = 8; 1557 task->status = SPDK_SCSI_STATUS_GOOD; 1558 break; 1559 } 1560 1561 case SPDK_SPC_SERVICE_ACTION_IN_16: 1562 switch (cdb[1] & 0x1f) { /* SERVICE ACTION */ 1563 case SPDK_SBC_SAI_READ_CAPACITY_16: { 1564 uint8_t buffer[32] = {0}; 1565 1566 to_be64(&buffer[0], bdev->blockcnt - 1); 1567 to_be32(&buffer[8], bdev->blocklen); 1568 /* 1569 * Set the TPE bit to 1 to indicate thin provisioning. 1570 * The position of TPE bit is the 7th bit in 14th byte 1571 * in READ CAPACITY (16) parameter data. 1572 */ 1573 if (bdev->thin_provisioning) { 1574 buffer[14] |= 1 << 7; 1575 } 1576 1577 len = from_be32(&cdb[10]); 1578 if (len) { 1579 len = len < sizeof(buffer) ? len : sizeof(buffer); 1580 data = spdk_scsi_task_alloc_data(task, len); 1581 memcpy(data, buffer, len); 1582 } 1583 1584 task->data_transferred = len; 1585 task->status = SPDK_SCSI_STATUS_GOOD; 1586 break; 1587 } 1588 1589 default: 1590 return SPDK_SCSI_TASK_UNKNOWN; 1591 } 1592 break; 1593 1594 case SPDK_SBC_SYNCHRONIZE_CACHE_10: 1595 case SPDK_SBC_SYNCHRONIZE_CACHE_16: 1596 if (cdb[0] == SPDK_SBC_SYNCHRONIZE_CACHE_10) { 1597 lba = from_be32(&cdb[2]); 1598 len = from_be16(&cdb[7]); 1599 } else { 1600 lba = from_be64(&cdb[2]); 1601 len = from_be32(&cdb[10]); 1602 } 1603 1604 if (len == 0) { 1605 len = bdev->blockcnt - lba; 1606 } 1607 1608 return spdk_bdev_scsi_sync(bdev, task, lba, len); 1609 break; 1610 1611 case SPDK_SBC_UNMAP: 1612 return spdk_bdev_scsi_unmap(bdev, task); 1613 1614 default: 1615 return SPDK_SCSI_TASK_UNKNOWN; 1616 } 1617 1618 return SPDK_SCSI_TASK_COMPLETE; 1619 } 1620 1621 static int 1622 spdk_bdev_scsi_process_primary(struct spdk_bdev *bdev, 1623 struct spdk_scsi_task *task) 1624 { 1625 int alloc_len; 1626 int data_len; 1627 uint8_t *cdb = task->cdb; 1628 uint8_t *data; 1629 int pllen, md = 0; 1630 int pf, sp; 1631 int bdlen, llba; 1632 int dbd, pc, page, subpage; 1633 int cmd_parsed = 0; 1634 1635 switch (cdb[0]) { 1636 case SPDK_SPC_INQUIRY: 1637 alloc_len = from_be16(&cdb[3]); 1638 if (alloc_len) { 1639 data = spdk_scsi_task_alloc_data(task, alloc_len); 1640 } else { 1641 data = NULL; 1642 } 1643 1644 data_len = spdk_bdev_scsi_inquiry(bdev, task, cdb, 1645 data, alloc_len); 1646 if (data_len < 0) { 1647 break; 1648 } 1649 1650 SPDK_TRACEDUMP(SPDK_TRACE_DEBUG, "INQUIRY", data, data_len); 1651 task->data_transferred = (uint64_t)data_len; 1652 task->status = SPDK_SCSI_STATUS_GOOD; 1653 break; 1654 1655 case SPDK_SPC_REPORT_LUNS: { 1656 int sel; 1657 1658 sel = cdb[2]; 1659 SPDK_TRACELOG(SPDK_TRACE_DEBUG, "sel=%x\n", sel); 1660 1661 alloc_len = from_be32(&cdb[6]); 1662 if (alloc_len < 16) { 1663 /* INVALID FIELD IN CDB */ 1664 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1665 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1666 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 1667 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1668 break; 1669 } 1670 1671 data = spdk_scsi_task_alloc_data(task, alloc_len); 1672 data_len = spdk_bdev_scsi_report_luns(task->lun, sel, data, task->alloc_len); 1673 if (data_len < 0) { 1674 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1675 SPDK_SCSI_SENSE_NO_SENSE, 1676 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1677 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1678 break; 1679 } 1680 1681 SPDK_TRACEDUMP(SPDK_TRACE_DEBUG, "REPORT LUNS", data, data_len); 1682 task->data_transferred = (uint64_t)data_len; 1683 task->status = SPDK_SCSI_STATUS_GOOD; 1684 break; 1685 } 1686 1687 case SPDK_SPC_MODE_SELECT_6: 1688 case SPDK_SPC_MODE_SELECT_10: 1689 data = task->iovs[0].iov_base; 1690 1691 if (cdb[0] == SPDK_SPC_MODE_SELECT_6) { 1692 md = 4; 1693 pllen = cdb[4]; 1694 } else { 1695 md = 8; 1696 pllen = from_be16(&cdb[7]); 1697 } 1698 1699 if (pllen == 0) { 1700 task->data_transferred = 0; 1701 task->status = SPDK_SCSI_STATUS_GOOD; 1702 break; 1703 } else if (cdb[0] == SPDK_SPC_MODE_SELECT_6 && pllen < 4) { 1704 /* MODE_SELECT(6) must have at least a 4 byte header. */ 1705 /* INVALID FIELD IN CDB */ 1706 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1707 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1708 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 1709 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1710 break; 1711 } else if (cdb[0] == SPDK_SPC_MODE_SELECT_10 && pllen < 8) { 1712 /* MODE_SELECT(10) must have at least an 8 byte header. */ 1713 /* INVALID FIELD IN CDB */ 1714 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1715 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1716 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 1717 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1718 break; 1719 } 1720 1721 if (cdb[0] == SPDK_SPC_MODE_SELECT_6) { 1722 bdlen = data[3]; 1723 } else { 1724 bdlen = from_be16(&data[6]); 1725 } 1726 1727 pf = !!(cdb[1] & 0x10); 1728 sp = !!(cdb[1] & 0x1); 1729 1730 /* page data */ 1731 data_len = spdk_bdev_scsi_mode_select_page( 1732 bdev, cdb, 1733 pf, sp, 1734 &data[md + bdlen], 1735 pllen - (md + bdlen)); 1736 if (data_len != 0) { 1737 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1738 SPDK_SCSI_SENSE_NO_SENSE, 1739 SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE, 1740 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1741 break; 1742 } 1743 1744 task->data_transferred = pllen; 1745 task->status = SPDK_SCSI_STATUS_GOOD; 1746 break; 1747 1748 case SPDK_SPC_MODE_SENSE_6: 1749 alloc_len = cdb[4]; 1750 md = 6; 1751 1752 case SPDK_SPC_MODE_SENSE_10: 1753 llba = 0; 1754 1755 if (md == 0) { 1756 alloc_len = from_be16(&cdb[7]); 1757 llba = !!(cdb[1] & 0x10); 1758 md = 10; 1759 } 1760 1761 dbd = !!(cdb[1] & 0x8); 1762 pc = (cdb[2] & 0xc) >> 6; 1763 page = cdb[2] & 0x3f; 1764 subpage = cdb[3]; 1765 1766 /* First call with no buffer to discover needed buffer size */ 1767 data_len = spdk_bdev_scsi_mode_sense(bdev, md, 1768 cdb, dbd, llba, pc, 1769 page, subpage, 1770 NULL); 1771 if (data_len < 0) { 1772 /* INVALID FIELD IN CDB */ 1773 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1774 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1775 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 1776 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1777 break; 1778 } 1779 1780 if (alloc_len > data_len) 1781 alloc_len = data_len; 1782 1783 if (alloc_len) { 1784 uint8_t *buffer; 1785 1786 data = spdk_scsi_task_alloc_data(task, alloc_len); 1787 buffer = alloc_len < data_len ? spdk_zmalloc(data_len, 0, NULL) : data; 1788 1789 data_len = spdk_bdev_scsi_mode_sense(bdev, md, 1790 cdb, dbd, llba, pc, 1791 page, subpage, 1792 buffer); 1793 assert(data_len >= 0); 1794 if (buffer != data) { 1795 memcpy(data, buffer, alloc_len); 1796 spdk_free(buffer); 1797 } 1798 } 1799 1800 task->data_transferred = (uint64_t)data_len; 1801 task->status = SPDK_SCSI_STATUS_GOOD; 1802 break; 1803 1804 case SPDK_SPC_REQUEST_SENSE: { 1805 int desc; 1806 int sk, asc, ascq; 1807 1808 desc = cdb[1] & 0x1; 1809 if (desc != 0) { 1810 /* INVALID FIELD IN CDB */ 1811 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1812 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1813 SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB, 1814 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1815 break; 1816 } 1817 1818 alloc_len = cdb[4]; 1819 data = spdk_scsi_task_alloc_data(task, alloc_len); 1820 1821 /* NO ADDITIONAL SENSE INFORMATION */ 1822 sk = SPDK_SCSI_SENSE_NO_SENSE; 1823 asc = 0x00; 1824 ascq = 0x00; 1825 1826 spdk_scsi_task_build_sense_data(task, sk, asc, ascq); 1827 1828 data_len = task->sense_data_len; 1829 memcpy(data, task->sense_data, data_len); 1830 task->data_transferred = (uint64_t)data_len; 1831 task->status = SPDK_SCSI_STATUS_GOOD; 1832 break; 1833 } 1834 1835 case SPDK_SPC_LOG_SELECT: 1836 SPDK_TRACELOG(SPDK_TRACE_SCSI, "LOG_SELECT\n"); 1837 cmd_parsed = 1; 1838 case SPDK_SPC_LOG_SENSE: 1839 if (!cmd_parsed) { 1840 SPDK_TRACELOG(SPDK_TRACE_SCSI, "LOG_SENSE\n"); 1841 } 1842 1843 /* INVALID COMMAND OPERATION CODE */ 1844 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1845 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1846 SPDK_SCSI_ASC_INVALID_COMMAND_OPERATION_CODE, 1847 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1848 break; 1849 1850 case SPDK_SPC_TEST_UNIT_READY: 1851 SPDK_TRACELOG(SPDK_TRACE_SCSI, "TEST_UNIT_READY\n"); 1852 cmd_parsed = 1; 1853 case SPDK_SBC_START_STOP_UNIT: 1854 if (!cmd_parsed) { 1855 SPDK_TRACELOG(SPDK_TRACE_SCSI, "START_STOP_UNIT\n"); 1856 } 1857 1858 task->data_transferred = 0; 1859 task->status = SPDK_SCSI_STATUS_GOOD; 1860 break; 1861 1862 default: 1863 return SPDK_SCSI_TASK_UNKNOWN; 1864 } 1865 1866 return SPDK_SCSI_TASK_COMPLETE; 1867 } 1868 1869 int 1870 spdk_bdev_scsi_execute(struct spdk_bdev *bdev, struct spdk_scsi_task *task) 1871 { 1872 int rc; 1873 1874 if ((rc = spdk_bdev_scsi_process_block(bdev, task)) == SPDK_SCSI_TASK_UNKNOWN) { 1875 if ((rc = spdk_bdev_scsi_process_primary(bdev, task)) == SPDK_SCSI_TASK_UNKNOWN) { 1876 SPDK_TRACELOG(SPDK_TRACE_SCSI, "unsupported SCSI OP=0x%x\n", task->cdb[0]); 1877 /* INVALID COMMAND OPERATION CODE */ 1878 spdk_scsi_task_set_status(task, SPDK_SCSI_STATUS_CHECK_CONDITION, 1879 SPDK_SCSI_SENSE_ILLEGAL_REQUEST, 1880 SPDK_SCSI_ASC_INVALID_COMMAND_OPERATION_CODE, 1881 SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 1882 return SPDK_SCSI_TASK_COMPLETE; 1883 } 1884 } 1885 1886 return rc; 1887 } 1888 1889 int 1890 spdk_bdev_scsi_reset(struct spdk_bdev *bdev, struct spdk_scsi_task *task) 1891 { 1892 return spdk_bdev_reset(bdev, SPDK_BDEV_RESET_HARD, 1893 spdk_bdev_scsi_task_complete, task); 1894 } 1895