1 /*- 2 * BSD LICENSE 3 * 4 * Copyright (c) Intel Corporation. 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * * Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * * Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in 15 * the documentation and/or other materials provided with the 16 * distribution. 17 * * Neither the name of Intel Corporation nor the names of its 18 * contributors may be used to endorse or promote products derived 19 * from this software without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 25 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 26 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 27 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 31 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32 */ 33 34 #include "spdk/stdinc.h" 35 36 #include "scsi/task.c" 37 #include "scsi/scsi_bdev.c" 38 #include "common/lib/test_env.c" 39 40 #include "spdk_cunit.h" 41 42 #include "spdk_internal/mock.h" 43 44 SPDK_LOG_REGISTER_COMPONENT("scsi", SPDK_LOG_SCSI) 45 46 struct spdk_scsi_globals g_spdk_scsi; 47 48 static uint64_t g_test_bdev_num_blocks; 49 50 TAILQ_HEAD(, spdk_bdev_io) g_bdev_io_queue; 51 int g_scsi_cb_called = 0; 52 53 TAILQ_HEAD(, spdk_bdev_io_wait_entry) g_io_wait_queue; 54 bool g_bdev_io_pool_full = false; 55 56 bool 57 spdk_bdev_io_type_supported(struct spdk_bdev *bdev, enum spdk_bdev_io_type io_type) 58 { 59 abort(); 60 return false; 61 } 62 63 void 64 spdk_bdev_free_io(struct spdk_bdev_io *bdev_io) 65 { 66 CU_ASSERT(0); 67 } 68 69 DEFINE_STUB(spdk_bdev_get_name, const char *, 70 (const struct spdk_bdev *bdev), "test"); 71 72 DEFINE_STUB(spdk_bdev_get_block_size, uint32_t, 73 (const struct spdk_bdev *bdev), 512); 74 75 DEFINE_STUB(spdk_bdev_get_data_block_size, uint32_t, 76 (const struct spdk_bdev *bdev), 512); 77 78 uint64_t 79 spdk_bdev_get_num_blocks(const struct spdk_bdev *bdev) 80 { 81 return g_test_bdev_num_blocks; 82 } 83 84 DEFINE_STUB(spdk_bdev_get_product_name, const char *, 85 (const struct spdk_bdev *bdev), "test product"); 86 87 DEFINE_STUB(spdk_bdev_has_write_cache, bool, 88 (const struct spdk_bdev *bdev), false); 89 90 void 91 spdk_scsi_lun_complete_task(struct spdk_scsi_lun *lun, struct spdk_scsi_task *task) 92 { 93 g_scsi_cb_called++; 94 } 95 96 DEFINE_STUB_V(spdk_scsi_lun_complete_reset_task, 97 (struct spdk_scsi_lun *lun, struct spdk_scsi_task *task)); 98 99 static void 100 ut_put_task(struct spdk_scsi_task *task) 101 { 102 if (task->alloc_len) { 103 free(task->iov.iov_base); 104 } 105 106 task->iov.iov_base = NULL; 107 task->iov.iov_len = 0; 108 task->alloc_len = 0; 109 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 110 } 111 112 static void 113 ut_init_task(struct spdk_scsi_task *task) 114 { 115 memset(task, 0xFF, sizeof(*task)); 116 task->iov.iov_base = NULL; 117 task->iovs = &task->iov; 118 task->iovcnt = 1; 119 task->alloc_len = 0; 120 task->dxfer_dir = SPDK_SCSI_DIR_NONE; 121 } 122 123 void 124 spdk_bdev_io_get_scsi_status(const struct spdk_bdev_io *bdev_io, 125 int *sc, int *sk, int *asc, int *ascq) 126 { 127 switch (bdev_io->internal.status) { 128 case SPDK_BDEV_IO_STATUS_SUCCESS: 129 *sc = SPDK_SCSI_STATUS_GOOD; 130 *sk = SPDK_SCSI_SENSE_NO_SENSE; 131 *asc = SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE; 132 *ascq = SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE; 133 break; 134 case SPDK_BDEV_IO_STATUS_SCSI_ERROR: 135 *sc = bdev_io->internal.error.scsi.sc; 136 *sk = bdev_io->internal.error.scsi.sk; 137 *asc = bdev_io->internal.error.scsi.asc; 138 *ascq = bdev_io->internal.error.scsi.ascq; 139 break; 140 default: 141 *sc = SPDK_SCSI_STATUS_CHECK_CONDITION; 142 *sk = SPDK_SCSI_SENSE_ABORTED_COMMAND; 143 *asc = SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE; 144 *ascq = SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE; 145 break; 146 } 147 } 148 149 void 150 spdk_bdev_io_get_iovec(struct spdk_bdev_io *bdev_io, struct iovec **iovp, int *iovcntp) 151 { 152 *iovp = NULL; 153 *iovcntp = 0; 154 } 155 156 static void 157 ut_bdev_io_flush(void) 158 { 159 struct spdk_bdev_io *bdev_io; 160 struct spdk_bdev_io_wait_entry *entry; 161 162 while (!TAILQ_EMPTY(&g_bdev_io_queue) || !TAILQ_EMPTY(&g_io_wait_queue)) { 163 while (!TAILQ_EMPTY(&g_bdev_io_queue)) { 164 bdev_io = TAILQ_FIRST(&g_bdev_io_queue); 165 TAILQ_REMOVE(&g_bdev_io_queue, bdev_io, internal.link); 166 bdev_io->internal.cb(bdev_io, true, bdev_io->internal.caller_ctx); 167 free(bdev_io); 168 } 169 170 while (!TAILQ_EMPTY(&g_io_wait_queue)) { 171 entry = TAILQ_FIRST(&g_io_wait_queue); 172 TAILQ_REMOVE(&g_io_wait_queue, entry, link); 173 entry->cb_fn(entry->cb_arg); 174 } 175 } 176 } 177 178 static int 179 _spdk_bdev_io_op(spdk_bdev_io_completion_cb cb, void *cb_arg) 180 { 181 struct spdk_bdev_io *bdev_io; 182 183 if (g_bdev_io_pool_full) { 184 g_bdev_io_pool_full = false; 185 return -ENOMEM; 186 } 187 188 bdev_io = calloc(1, sizeof(*bdev_io)); 189 SPDK_CU_ASSERT_FATAL(bdev_io != NULL); 190 bdev_io->internal.status = SPDK_BDEV_IO_STATUS_SUCCESS; 191 bdev_io->internal.cb = cb; 192 bdev_io->internal.caller_ctx = cb_arg; 193 194 TAILQ_INSERT_TAIL(&g_bdev_io_queue, bdev_io, internal.link); 195 196 return 0; 197 } 198 199 int 200 spdk_bdev_readv_blocks(struct spdk_bdev_desc *desc, struct spdk_io_channel *ch, 201 struct iovec *iov, int iovcnt, 202 uint64_t offset_blocks, uint64_t num_blocks, 203 spdk_bdev_io_completion_cb cb, void *cb_arg) 204 { 205 return _spdk_bdev_io_op(cb, cb_arg); 206 } 207 208 int 209 spdk_bdev_writev_blocks(struct spdk_bdev_desc *desc, struct spdk_io_channel *ch, 210 struct iovec *iov, int iovcnt, 211 uint64_t offset_blocks, uint64_t num_blocks, 212 spdk_bdev_io_completion_cb cb, void *cb_arg) 213 { 214 return _spdk_bdev_io_op(cb, cb_arg); 215 } 216 217 int 218 spdk_bdev_unmap_blocks(struct spdk_bdev_desc *desc, struct spdk_io_channel *ch, 219 uint64_t offset_blocks, uint64_t num_blocks, 220 spdk_bdev_io_completion_cb cb, void *cb_arg) 221 { 222 return _spdk_bdev_io_op(cb, cb_arg); 223 } 224 225 int 226 spdk_bdev_reset(struct spdk_bdev_desc *desc, struct spdk_io_channel *ch, 227 spdk_bdev_io_completion_cb cb, void *cb_arg) 228 { 229 return _spdk_bdev_io_op(cb, cb_arg); 230 } 231 232 int 233 spdk_bdev_flush_blocks(struct spdk_bdev_desc *desc, struct spdk_io_channel *ch, 234 uint64_t offset_blocks, uint64_t num_blocks, 235 spdk_bdev_io_completion_cb cb, void *cb_arg) 236 { 237 return _spdk_bdev_io_op(cb, cb_arg); 238 } 239 240 int 241 spdk_bdev_queue_io_wait(struct spdk_bdev *bdev, struct spdk_io_channel *ch, 242 struct spdk_bdev_io_wait_entry *entry) 243 { 244 TAILQ_INSERT_TAIL(&g_io_wait_queue, entry, link); 245 return 0; 246 } 247 248 /* 249 * This test specifically tests a mode select 6 command from the 250 * Windows SCSI compliance test that caused SPDK to crash. 251 */ 252 static void 253 mode_select_6_test(void) 254 { 255 struct spdk_bdev bdev; 256 struct spdk_scsi_task task; 257 struct spdk_scsi_lun lun; 258 struct spdk_scsi_dev dev; 259 char cdb[16]; 260 char data[24]; 261 int rc; 262 263 ut_init_task(&task); 264 265 cdb[0] = 0x15; 266 cdb[1] = 0x11; 267 cdb[2] = 0x00; 268 cdb[3] = 0x00; 269 cdb[4] = 0x18; 270 cdb[5] = 0x00; 271 task.cdb = cdb; 272 273 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 274 lun.bdev = &bdev; 275 lun.dev = &dev; 276 task.lun = &lun; 277 278 memset(data, 0, sizeof(data)); 279 data[4] = 0x08; 280 data[5] = 0x02; 281 spdk_scsi_task_set_data(&task, data, sizeof(data)); 282 283 rc = spdk_bdev_scsi_execute(&task); 284 285 CU_ASSERT_EQUAL(rc, 0); 286 287 ut_put_task(&task); 288 } 289 290 /* 291 * This test specifically tests a mode select 6 command which 292 * contains no mode pages. 293 */ 294 static void 295 mode_select_6_test2(void) 296 { 297 struct spdk_bdev bdev; 298 struct spdk_scsi_task task; 299 struct spdk_scsi_lun lun; 300 struct spdk_scsi_dev dev; 301 char cdb[16]; 302 int rc; 303 304 ut_init_task(&task); 305 306 cdb[0] = 0x15; 307 cdb[1] = 0x00; 308 cdb[2] = 0x00; 309 cdb[3] = 0x00; 310 cdb[4] = 0x00; 311 cdb[5] = 0x00; 312 task.cdb = cdb; 313 314 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 315 lun.bdev = &bdev; 316 lun.dev = &dev; 317 task.lun = &lun; 318 319 rc = spdk_bdev_scsi_execute(&task); 320 321 CU_ASSERT_EQUAL(rc, 0); 322 323 ut_put_task(&task); 324 } 325 326 /* 327 * This test specifically tests a mode sense 6 command which 328 * return all subpage 00h mode pages. 329 */ 330 static void 331 mode_sense_6_test(void) 332 { 333 struct spdk_bdev bdev; 334 struct spdk_scsi_task task; 335 struct spdk_scsi_lun lun; 336 struct spdk_scsi_dev dev; 337 char cdb[12]; 338 unsigned char *data; 339 int rc; 340 unsigned char mode_data_len = 0; 341 unsigned char medium_type = 0; 342 unsigned char dev_specific_param = 0; 343 unsigned char blk_descriptor_len = 0; 344 345 memset(&bdev, 0, sizeof(struct spdk_bdev)); 346 ut_init_task(&task); 347 memset(cdb, 0, sizeof(cdb)); 348 349 cdb[0] = 0x1A; 350 cdb[2] = 0x3F; 351 cdb[4] = 0xFF; 352 task.cdb = cdb; 353 354 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 355 lun.bdev = &bdev; 356 lun.dev = &dev; 357 task.lun = &lun; 358 359 rc = spdk_bdev_scsi_execute(&task); 360 SPDK_CU_ASSERT_FATAL(rc == 0); 361 362 data = task.iovs[0].iov_base; 363 mode_data_len = data[0]; 364 medium_type = data[1]; 365 dev_specific_param = data[2]; 366 blk_descriptor_len = data[3]; 367 368 CU_ASSERT(mode_data_len >= 11); 369 CU_ASSERT_EQUAL(medium_type, 0); 370 CU_ASSERT_EQUAL(dev_specific_param, 0); 371 CU_ASSERT_EQUAL(blk_descriptor_len, 8); 372 373 ut_put_task(&task); 374 } 375 376 /* 377 * This test specifically tests a mode sense 10 command which 378 * return all subpage 00h mode pages. 379 */ 380 static void 381 mode_sense_10_test(void) 382 { 383 struct spdk_bdev bdev; 384 struct spdk_scsi_task task; 385 struct spdk_scsi_lun lun; 386 struct spdk_scsi_dev dev; 387 char cdb[12]; 388 unsigned char *data; 389 int rc; 390 unsigned short mode_data_len = 0; 391 unsigned char medium_type = 0; 392 unsigned char dev_specific_param = 0; 393 unsigned short blk_descriptor_len = 0; 394 395 memset(&bdev, 0, sizeof(struct spdk_bdev)); 396 ut_init_task(&task); 397 memset(cdb, 0, sizeof(cdb)); 398 cdb[0] = 0x5A; 399 cdb[2] = 0x3F; 400 cdb[8] = 0xFF; 401 task.cdb = cdb; 402 403 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 404 lun.bdev = &bdev; 405 lun.dev = &dev; 406 task.lun = &lun; 407 408 rc = spdk_bdev_scsi_execute(&task); 409 SPDK_CU_ASSERT_FATAL(rc == 0); 410 411 data = task.iovs[0].iov_base; 412 mode_data_len = ((data[0] << 8) + data[1]); 413 medium_type = data[2]; 414 dev_specific_param = data[3]; 415 blk_descriptor_len = ((data[6] << 8) + data[7]); 416 417 CU_ASSERT(mode_data_len >= 14); 418 CU_ASSERT_EQUAL(medium_type, 0); 419 CU_ASSERT_EQUAL(dev_specific_param, 0); 420 CU_ASSERT_EQUAL(blk_descriptor_len, 8); 421 422 ut_put_task(&task); 423 } 424 425 /* 426 * This test specifically tests a scsi inquiry command from the 427 * Windows SCSI compliance test that failed to return the 428 * expected SCSI error sense code. 429 */ 430 static void 431 inquiry_evpd_test(void) 432 { 433 struct spdk_bdev bdev; 434 struct spdk_scsi_task task; 435 struct spdk_scsi_lun lun; 436 struct spdk_scsi_dev dev; 437 char cdb[6]; 438 int rc; 439 440 ut_init_task(&task); 441 442 cdb[0] = 0x12; 443 cdb[1] = 0x00; /* EVPD = 0 */ 444 cdb[2] = 0xff; /* PageCode non-zero */ 445 cdb[3] = 0x00; 446 cdb[4] = 0xff; 447 cdb[5] = 0x00; 448 task.cdb = cdb; 449 450 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 451 lun.bdev = &bdev; 452 lun.dev = &dev; 453 task.lun = &lun; 454 455 rc = spdk_bdev_scsi_execute(&task); 456 SPDK_CU_ASSERT_FATAL(rc == 0); 457 458 CU_ASSERT_EQUAL(task.status, SPDK_SCSI_STATUS_CHECK_CONDITION); 459 CU_ASSERT_EQUAL(task.sense_data[2] & 0xf, SPDK_SCSI_SENSE_ILLEGAL_REQUEST); 460 CU_ASSERT_EQUAL(task.sense_data[12], 0x24); 461 CU_ASSERT_EQUAL(task.sense_data[13], 0x0); 462 463 ut_put_task(&task); 464 } 465 466 /* 467 * This test is to verify specific return data for a standard scsi inquiry 468 * command: Version 469 */ 470 static void 471 inquiry_standard_test(void) 472 { 473 struct spdk_bdev bdev = { .blocklen = 512 }; 474 struct spdk_scsi_task task; 475 struct spdk_scsi_lun lun; 476 struct spdk_scsi_dev dev; 477 char cdb[6]; 478 char *data; 479 struct spdk_scsi_cdb_inquiry_data *inq_data; 480 int rc; 481 482 ut_init_task(&task); 483 484 cdb[0] = 0x12; 485 cdb[1] = 0x00; /* EVPD = 0 */ 486 cdb[2] = 0x00; /* PageCode zero - requesting standard inquiry */ 487 cdb[3] = 0x00; 488 cdb[4] = 0xff; /* Indicate data size used by conformance test */ 489 cdb[5] = 0x00; 490 task.cdb = cdb; 491 492 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 493 lun.bdev = &bdev; 494 lun.dev = &dev; 495 task.lun = &lun; 496 497 rc = spdk_bdev_scsi_execute(&task); 498 499 data = task.iovs[0].iov_base; 500 inq_data = (struct spdk_scsi_cdb_inquiry_data *)&data[0]; 501 502 CU_ASSERT_EQUAL(inq_data->version, SPDK_SPC_VERSION_SPC3); 503 CU_ASSERT_EQUAL(rc, 0); 504 505 ut_put_task(&task); 506 } 507 508 static void 509 _inquiry_overflow_test(uint8_t alloc_len) 510 { 511 struct spdk_bdev bdev = { .blocklen = 512 }; 512 struct spdk_scsi_task task; 513 struct spdk_scsi_lun lun; 514 struct spdk_scsi_dev dev; 515 uint8_t cdb[6]; 516 int rc; 517 /* expects a 4K internal data buffer */ 518 char data[4096], data_compare[4096]; 519 520 ut_init_task(&task); 521 522 cdb[0] = 0x12; 523 cdb[1] = 0x00; /* EVPD = 0 */ 524 cdb[2] = 0x00; /* PageCode zero - requesting standard inquiry */ 525 cdb[3] = 0x00; 526 cdb[4] = alloc_len; /* Indicate data size used by conformance test */ 527 cdb[5] = 0x00; 528 task.cdb = cdb; 529 530 snprintf(&dev.name[0], sizeof(dev.name), "spdk_iscsi_translation_test"); 531 lun.bdev = &bdev; 532 lun.dev = &dev; 533 task.lun = &lun; 534 535 memset(data, 0, sizeof(data)); 536 memset(data_compare, 0, sizeof(data_compare)); 537 538 spdk_scsi_task_set_data(&task, data, sizeof(data)); 539 540 rc = spdk_bdev_scsi_execute(&task); 541 SPDK_CU_ASSERT_FATAL(rc == 0); 542 543 CU_ASSERT_EQUAL(memcmp(data + alloc_len, data_compare + alloc_len, sizeof(data) - alloc_len), 0); 544 CU_ASSERT(task.data_transferred <= alloc_len); 545 546 ut_put_task(&task); 547 } 548 549 static void 550 inquiry_overflow_test(void) 551 { 552 int i; 553 554 for (i = 0; i < 256; i++) { 555 _inquiry_overflow_test(i); 556 } 557 } 558 559 static void 560 scsi_name_padding_test(void) 561 { 562 char name[SPDK_SCSI_DEV_MAX_NAME + 1]; 563 char buf[SPDK_SCSI_DEV_MAX_NAME + 1]; 564 int written, i; 565 566 /* case 1 */ 567 memset(name, '\0', sizeof(name)); 568 memset(name, 'x', 251); 569 written = spdk_bdev_scsi_pad_scsi_name(buf, name); 570 571 CU_ASSERT(written == 252); 572 CU_ASSERT(buf[250] == 'x'); 573 CU_ASSERT(buf[251] == '\0'); 574 575 /* case 2: */ 576 memset(name, '\0', sizeof(name)); 577 memset(name, 'x', 252); 578 written = spdk_bdev_scsi_pad_scsi_name(buf, name); 579 580 CU_ASSERT(written == 256); 581 CU_ASSERT(buf[251] == 'x'); 582 for (i = 252; i < 256; i++) { 583 CU_ASSERT(buf[i] == '\0'); 584 } 585 586 /* case 3 */ 587 memset(name, '\0', sizeof(name)); 588 memset(name, 'x', 255); 589 written = spdk_bdev_scsi_pad_scsi_name(buf, name); 590 591 CU_ASSERT(written == 256); 592 CU_ASSERT(buf[254] == 'x'); 593 CU_ASSERT(buf[255] == '\0'); 594 } 595 596 /* 597 * This test is to verify specific error translation from bdev to scsi. 598 */ 599 static void 600 task_complete_test(void) 601 { 602 struct spdk_scsi_task task; 603 struct spdk_bdev_io bdev_io = {}; 604 struct spdk_scsi_lun lun; 605 606 ut_init_task(&task); 607 608 TAILQ_INIT(&lun.tasks); 609 TAILQ_INSERT_TAIL(&lun.tasks, &task, scsi_link); 610 task.lun = &lun; 611 612 bdev_io.internal.status = SPDK_BDEV_IO_STATUS_SUCCESS; 613 spdk_bdev_scsi_task_complete_cmd(&bdev_io, bdev_io.internal.status, &task); 614 CU_ASSERT_EQUAL(task.status, SPDK_SCSI_STATUS_GOOD); 615 CU_ASSERT(g_scsi_cb_called == 1); 616 g_scsi_cb_called = 0; 617 618 bdev_io.internal.status = SPDK_BDEV_IO_STATUS_SCSI_ERROR; 619 bdev_io.internal.error.scsi.sc = SPDK_SCSI_STATUS_CHECK_CONDITION; 620 bdev_io.internal.error.scsi.sk = SPDK_SCSI_SENSE_HARDWARE_ERROR; 621 bdev_io.internal.error.scsi.asc = SPDK_SCSI_ASC_WARNING; 622 bdev_io.internal.error.scsi.ascq = SPDK_SCSI_ASCQ_POWER_LOSS_EXPECTED; 623 spdk_bdev_scsi_task_complete_cmd(&bdev_io, bdev_io.internal.status, &task); 624 CU_ASSERT_EQUAL(task.status, SPDK_SCSI_STATUS_CHECK_CONDITION); 625 CU_ASSERT_EQUAL(task.sense_data[2] & 0xf, SPDK_SCSI_SENSE_HARDWARE_ERROR); 626 CU_ASSERT_EQUAL(task.sense_data[12], SPDK_SCSI_ASC_WARNING); 627 CU_ASSERT_EQUAL(task.sense_data[13], SPDK_SCSI_ASCQ_POWER_LOSS_EXPECTED); 628 CU_ASSERT(g_scsi_cb_called == 1); 629 g_scsi_cb_called = 0; 630 631 bdev_io.internal.status = SPDK_BDEV_IO_STATUS_FAILED; 632 spdk_bdev_scsi_task_complete_cmd(&bdev_io, bdev_io.internal.status, &task); 633 CU_ASSERT_EQUAL(task.status, SPDK_SCSI_STATUS_CHECK_CONDITION); 634 CU_ASSERT_EQUAL(task.sense_data[2] & 0xf, SPDK_SCSI_SENSE_ABORTED_COMMAND); 635 CU_ASSERT_EQUAL(task.sense_data[12], SPDK_SCSI_ASC_NO_ADDITIONAL_SENSE); 636 CU_ASSERT_EQUAL(task.sense_data[13], SPDK_SCSI_ASCQ_CAUSE_NOT_REPORTABLE); 637 CU_ASSERT(g_scsi_cb_called == 1); 638 g_scsi_cb_called = 0; 639 640 ut_put_task(&task); 641 } 642 643 static void 644 lba_range_test(void) 645 { 646 struct spdk_bdev bdev = { .blocklen = 512 }; 647 struct spdk_scsi_lun lun; 648 struct spdk_scsi_task task; 649 uint8_t cdb[16]; 650 int rc; 651 652 lun.bdev = &bdev; 653 654 ut_init_task(&task); 655 task.lun = &lun; 656 task.lun->bdev_desc = NULL; 657 task.lun->io_channel = NULL; 658 task.cdb = cdb; 659 660 memset(cdb, 0, sizeof(cdb)); 661 cdb[0] = 0x88; /* READ (16) */ 662 663 /* Test block device size of 4 blocks */ 664 g_test_bdev_num_blocks = 4; 665 666 /* LBA = 0, length = 1 (in range) */ 667 to_be64(&cdb[2], 0); /* LBA */ 668 to_be32(&cdb[10], 1); /* transfer length */ 669 task.transfer_len = 1 * 512; 670 task.offset = 0; 671 task.length = 1 * 512; 672 rc = spdk_bdev_scsi_execute(&task); 673 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 674 CU_ASSERT(task.status == 0xFF); 675 SPDK_CU_ASSERT_FATAL(!TAILQ_EMPTY(&g_bdev_io_queue)); 676 ut_bdev_io_flush(); 677 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 678 CU_ASSERT(g_scsi_cb_called == 1); 679 g_scsi_cb_called = 0; 680 681 /* LBA = 4, length = 1 (LBA out of range) */ 682 to_be64(&cdb[2], 4); /* LBA */ 683 to_be32(&cdb[10], 1); /* transfer length */ 684 task.transfer_len = 1 * 512; 685 task.offset = 0; 686 task.length = 1 * 512; 687 rc = spdk_bdev_scsi_execute(&task); 688 CU_ASSERT(rc == SPDK_SCSI_TASK_COMPLETE); 689 CU_ASSERT(task.status == SPDK_SCSI_STATUS_CHECK_CONDITION); 690 CU_ASSERT(task.sense_data[12] == SPDK_SCSI_ASC_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE); 691 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 692 693 /* LBA = 0, length = 4 (in range, max valid size) */ 694 to_be64(&cdb[2], 0); /* LBA */ 695 to_be32(&cdb[10], 4); /* transfer length */ 696 task.transfer_len = 4 * 512; 697 task.status = 0xFF; 698 task.offset = 0; 699 task.length = 1 * 512; 700 rc = spdk_bdev_scsi_execute(&task); 701 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 702 CU_ASSERT(task.status == 0xFF); 703 SPDK_CU_ASSERT_FATAL(!TAILQ_EMPTY(&g_bdev_io_queue)); 704 ut_bdev_io_flush(); 705 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 706 CU_ASSERT(g_scsi_cb_called == 1); 707 g_scsi_cb_called = 0; 708 709 /* LBA = 0, length = 5 (LBA in range, length beyond end of bdev) */ 710 to_be64(&cdb[2], 0); /* LBA */ 711 to_be32(&cdb[10], 5); /* transfer length */ 712 task.transfer_len = 5 * 512; 713 task.offset = 0; 714 task.length = 1 * 512; 715 rc = spdk_bdev_scsi_execute(&task); 716 CU_ASSERT(rc == SPDK_SCSI_TASK_COMPLETE); 717 CU_ASSERT(task.status == SPDK_SCSI_STATUS_CHECK_CONDITION); 718 CU_ASSERT(task.sense_data[12] == SPDK_SCSI_ASC_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE); 719 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 720 721 ut_put_task(&task); 722 } 723 724 static void 725 xfer_len_test(void) 726 { 727 struct spdk_bdev bdev = { .blocklen = 512 }; 728 struct spdk_scsi_lun lun; 729 struct spdk_scsi_task task; 730 uint8_t cdb[16]; 731 int rc; 732 733 lun.bdev = &bdev; 734 735 ut_init_task(&task); 736 task.lun = &lun; 737 task.lun->bdev_desc = NULL; 738 task.lun->io_channel = NULL; 739 task.cdb = cdb; 740 741 memset(cdb, 0, sizeof(cdb)); 742 cdb[0] = 0x88; /* READ (16) */ 743 744 /* Test block device size of 512 MiB */ 745 g_test_bdev_num_blocks = 512 * 1024 * 1024; 746 747 /* 1 block */ 748 to_be64(&cdb[2], 0); /* LBA */ 749 to_be32(&cdb[10], 1); /* transfer length */ 750 task.transfer_len = 1 * 512; 751 task.offset = 0; 752 task.length = 1 * 512; 753 rc = spdk_bdev_scsi_execute(&task); 754 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 755 CU_ASSERT(task.status == 0xFF); 756 SPDK_CU_ASSERT_FATAL(!TAILQ_EMPTY(&g_bdev_io_queue)); 757 ut_bdev_io_flush(); 758 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 759 CU_ASSERT(g_scsi_cb_called == 1); 760 g_scsi_cb_called = 0; 761 762 /* max transfer length (as reported in block limits VPD page) */ 763 to_be64(&cdb[2], 0); /* LBA */ 764 to_be32(&cdb[10], SPDK_WORK_BLOCK_SIZE / 512); /* transfer length */ 765 task.transfer_len = SPDK_WORK_BLOCK_SIZE; 766 task.status = 0xFF; 767 task.offset = 0; 768 task.length = 1 * 512; 769 rc = spdk_bdev_scsi_execute(&task); 770 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 771 CU_ASSERT(task.status == 0xFF); 772 SPDK_CU_ASSERT_FATAL(!TAILQ_EMPTY(&g_bdev_io_queue)); 773 ut_bdev_io_flush(); 774 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 775 CU_ASSERT(g_scsi_cb_called == 1); 776 g_scsi_cb_called = 0; 777 778 /* max transfer length plus one block (invalid) */ 779 to_be64(&cdb[2], 0); /* LBA */ 780 to_be32(&cdb[10], SPDK_WORK_BLOCK_SIZE / 512 + 1); /* transfer length */ 781 task.transfer_len = SPDK_WORK_BLOCK_SIZE + 512; 782 task.offset = 0; 783 task.length = 1 * 512; 784 rc = spdk_bdev_scsi_execute(&task); 785 CU_ASSERT(rc == SPDK_SCSI_TASK_COMPLETE); 786 CU_ASSERT(task.status == SPDK_SCSI_STATUS_CHECK_CONDITION); 787 CU_ASSERT((task.sense_data[2] & 0xf) == SPDK_SCSI_SENSE_ILLEGAL_REQUEST); 788 CU_ASSERT(task.sense_data[12] == SPDK_SCSI_ASC_INVALID_FIELD_IN_CDB); 789 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 790 791 /* zero transfer length (valid) */ 792 to_be64(&cdb[2], 0); /* LBA */ 793 to_be32(&cdb[10], 0); /* transfer length */ 794 task.transfer_len = 0; 795 task.offset = 0; 796 task.length = 0; 797 rc = spdk_bdev_scsi_execute(&task); 798 CU_ASSERT(rc == SPDK_SCSI_TASK_COMPLETE); 799 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 800 CU_ASSERT(task.data_transferred == 0); 801 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 802 803 /* zero transfer length past end of disk (invalid) */ 804 to_be64(&cdb[2], g_test_bdev_num_blocks); /* LBA */ 805 to_be32(&cdb[10], 0); /* transfer length */ 806 task.transfer_len = 0; 807 task.offset = 0; 808 task.length = 0; 809 rc = spdk_bdev_scsi_execute(&task); 810 CU_ASSERT(rc == SPDK_SCSI_TASK_COMPLETE); 811 CU_ASSERT(task.status == SPDK_SCSI_STATUS_CHECK_CONDITION); 812 CU_ASSERT(task.sense_data[12] == SPDK_SCSI_ASC_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE); 813 SPDK_CU_ASSERT_FATAL(TAILQ_EMPTY(&g_bdev_io_queue)); 814 815 ut_put_task(&task); 816 } 817 818 static void 819 _xfer_test(bool bdev_io_pool_full) 820 { 821 struct spdk_bdev bdev = { .blocklen = 512 }; 822 struct spdk_scsi_lun lun; 823 struct spdk_scsi_task task; 824 uint8_t cdb[16]; 825 char data[4096]; 826 int rc; 827 828 lun.bdev = &bdev; 829 830 /* Test block device size of 512 MiB */ 831 g_test_bdev_num_blocks = 512 * 1024 * 1024; 832 833 /* Read 1 block */ 834 ut_init_task(&task); 835 task.lun = &lun; 836 task.lun->bdev_desc = NULL; 837 task.lun->io_channel = NULL; 838 task.cdb = cdb; 839 memset(cdb, 0, sizeof(cdb)); 840 cdb[0] = 0x88; /* READ (16) */ 841 to_be64(&cdb[2], 0); /* LBA */ 842 to_be32(&cdb[10], 1); /* transfer length */ 843 task.transfer_len = 1 * 512; 844 task.offset = 0; 845 task.length = 1 * 512; 846 g_bdev_io_pool_full = bdev_io_pool_full; 847 rc = spdk_bdev_scsi_execute(&task); 848 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 849 CU_ASSERT(task.status == 0xFF); 850 851 ut_bdev_io_flush(); 852 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 853 CU_ASSERT(g_scsi_cb_called == 1); 854 g_scsi_cb_called = 0; 855 ut_put_task(&task); 856 857 /* Write 1 block */ 858 ut_init_task(&task); 859 task.lun = &lun; 860 task.cdb = cdb; 861 memset(cdb, 0, sizeof(cdb)); 862 cdb[0] = 0x8a; /* WRITE (16) */ 863 to_be64(&cdb[2], 0); /* LBA */ 864 to_be32(&cdb[10], 1); /* transfer length */ 865 task.transfer_len = 1 * 512; 866 task.offset = 0; 867 task.length = 1 * 512; 868 g_bdev_io_pool_full = bdev_io_pool_full; 869 rc = spdk_bdev_scsi_execute(&task); 870 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 871 CU_ASSERT(task.status == 0xFF); 872 873 ut_bdev_io_flush(); 874 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 875 CU_ASSERT(g_scsi_cb_called == 1); 876 g_scsi_cb_called = 0; 877 ut_put_task(&task); 878 879 /* Unmap 5 blocks using 2 descriptors */ 880 ut_init_task(&task); 881 task.lun = &lun; 882 task.cdb = cdb; 883 memset(cdb, 0, sizeof(cdb)); 884 cdb[0] = 0x42; /* UNMAP */ 885 to_be16(&data[7], 2); /* 2 parameters in list */ 886 memset(data, 0, sizeof(data)); 887 to_be16(&data[2], 32); /* 2 descriptors */ 888 to_be64(&data[8], 1); /* LBA 1 */ 889 to_be32(&data[16], 2); /* 2 blocks */ 890 to_be64(&data[24], 10); /* LBA 10 */ 891 to_be32(&data[32], 3); /* 3 blocks */ 892 spdk_scsi_task_set_data(&task, data, sizeof(data)); 893 task.status = SPDK_SCSI_STATUS_GOOD; 894 g_bdev_io_pool_full = bdev_io_pool_full; 895 rc = spdk_bdev_scsi_execute(&task); 896 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 897 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 898 899 ut_bdev_io_flush(); 900 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 901 CU_ASSERT(g_scsi_cb_called == 1); 902 g_scsi_cb_called = 0; 903 ut_put_task(&task); 904 905 /* Flush 1 block */ 906 ut_init_task(&task); 907 task.lun = &lun; 908 task.cdb = cdb; 909 memset(cdb, 0, sizeof(cdb)); 910 cdb[0] = 0x91; /* SYNCHRONIZE CACHE (16) */ 911 to_be64(&cdb[2], 0); /* LBA */ 912 to_be32(&cdb[10], 1); /* 1 blocks */ 913 g_bdev_io_pool_full = bdev_io_pool_full; 914 rc = spdk_bdev_scsi_execute(&task); 915 CU_ASSERT(rc == SPDK_SCSI_TASK_PENDING); 916 CU_ASSERT(task.status == 0xFF); 917 918 ut_bdev_io_flush(); 919 CU_ASSERT(task.status == SPDK_SCSI_STATUS_GOOD); 920 CU_ASSERT(g_scsi_cb_called == 1); 921 g_scsi_cb_called = 0; 922 ut_put_task(&task); 923 } 924 925 static void 926 xfer_test(void) 927 { 928 _xfer_test(false); 929 _xfer_test(true); 930 } 931 932 int 933 main(int argc, char **argv) 934 { 935 CU_pSuite suite = NULL; 936 unsigned int num_failures; 937 938 TAILQ_INIT(&g_bdev_io_queue); 939 TAILQ_INIT(&g_io_wait_queue); 940 941 if (CU_initialize_registry() != CUE_SUCCESS) { 942 return CU_get_error(); 943 } 944 945 suite = CU_add_suite("translation_suite", NULL, NULL); 946 if (suite == NULL) { 947 CU_cleanup_registry(); 948 return CU_get_error(); 949 } 950 951 if ( 952 CU_add_test(suite, "mode select 6 test", mode_select_6_test) == NULL 953 || CU_add_test(suite, "mode select 6 test2", mode_select_6_test2) == NULL 954 || CU_add_test(suite, "mode sense 6 test", mode_sense_6_test) == NULL 955 || CU_add_test(suite, "mode sense 10 test", mode_sense_10_test) == NULL 956 || CU_add_test(suite, "inquiry evpd test", inquiry_evpd_test) == NULL 957 || CU_add_test(suite, "inquiry standard test", inquiry_standard_test) == NULL 958 || CU_add_test(suite, "inquiry overflow test", inquiry_overflow_test) == NULL 959 || CU_add_test(suite, "task complete test", task_complete_test) == NULL 960 || CU_add_test(suite, "LBA range test", lba_range_test) == NULL 961 || CU_add_test(suite, "transfer length test", xfer_len_test) == NULL 962 || CU_add_test(suite, "transfer test", xfer_test) == NULL 963 || CU_add_test(suite, "scsi name padding test", scsi_name_padding_test) == NULL 964 ) { 965 CU_cleanup_registry(); 966 return CU_get_error(); 967 } 968 969 CU_basic_set_mode(CU_BRM_VERBOSE); 970 CU_basic_run_tests(); 971 num_failures = CU_get_number_of_failures(); 972 CU_cleanup_registry(); 973 return num_failures; 974 } 975