1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright (C) 2016 Intel Corporation. 3 * All rights reserved. 4 */ 5 6 /** 7 * \file 8 * SCSI to bdev translation layer 9 */ 10 11 #ifndef SPDK_SCSI_H 12 #define SPDK_SCSI_H 13 14 #include "spdk/stdinc.h" 15 16 #include "spdk/bdev.h" 17 #include "spdk/queue.h" 18 19 #include "spdk_internal/trace_defs.h" 20 21 #ifdef __cplusplus 22 extern "C" { 23 #endif 24 25 /* Defines for SPDK tracing framework */ 26 #define SPDK_SCSI_MAX_DEVS 1024 27 #define SPDK_SCSI_DEV_MAX_PORTS 4 28 #define SPDK_SCSI_DEV_MAX_NAME 255 29 30 #define SPDK_SCSI_PORT_MAX_NAME_LENGTH 255 31 #define SPDK_SCSI_MAX_TRANSPORT_ID_LENGTH 255 32 33 enum spdk_scsi_data_dir { 34 SPDK_SCSI_DIR_NONE = 0, 35 SPDK_SCSI_DIR_TO_DEV = 1, 36 SPDK_SCSI_DIR_FROM_DEV = 2, 37 }; 38 39 enum spdk_scsi_task_func { 40 SPDK_SCSI_TASK_FUNC_ABORT_TASK = 0, 41 SPDK_SCSI_TASK_FUNC_ABORT_TASK_SET, 42 SPDK_SCSI_TASK_FUNC_CLEAR_TASK_SET, 43 SPDK_SCSI_TASK_FUNC_LUN_RESET, 44 SPDK_SCSI_TASK_FUNC_TARGET_RESET, 45 }; 46 47 /* 48 * SAM does not define the value for these service responses. Each transport 49 * (i.e. SAS, FC, iSCSI) will map these value to transport-specific codes, 50 * and may add their own. 51 */ 52 enum spdk_scsi_task_mgmt_resp { 53 SPDK_SCSI_TASK_MGMT_RESP_COMPLETE, 54 SPDK_SCSI_TASK_MGMT_RESP_SUCCESS, 55 SPDK_SCSI_TASK_MGMT_RESP_REJECT, 56 SPDK_SCSI_TASK_MGMT_RESP_INVALID_LUN, 57 SPDK_SCSI_TASK_MGMT_RESP_TARGET_FAILURE, 58 SPDK_SCSI_TASK_MGMT_RESP_REJECT_FUNC_NOT_SUPPORTED 59 }; 60 61 struct spdk_scsi_task; 62 typedef void (*spdk_scsi_task_cpl)(struct spdk_scsi_task *task); 63 typedef void (*spdk_scsi_task_free)(struct spdk_scsi_task *task); 64 65 struct spdk_scsi_task { 66 uint8_t status; 67 uint8_t function; /* task mgmt function */ 68 uint8_t response; /* task mgmt response */ 69 70 struct spdk_scsi_lun *lun; 71 struct spdk_scsi_port *target_port; 72 struct spdk_scsi_port *initiator_port; 73 74 spdk_scsi_task_cpl cpl_fn; 75 spdk_scsi_task_free free_fn; 76 77 uint32_t ref; 78 uint32_t transfer_len; 79 uint32_t dxfer_dir; 80 uint32_t length; 81 82 /** 83 * Amount of data actually transferred. Can be less than requested 84 * transfer_len - i.e. SCSI INQUIRY. 85 */ 86 uint32_t data_transferred; 87 88 uint64_t offset; 89 90 uint8_t *cdb; 91 92 /** 93 * \internal 94 * Size of internal buffer or zero when iov.iov_base is not internally managed. 95 */ 96 uint32_t alloc_len; 97 /** 98 * \internal 99 * iov is internal buffer. Use iovs to access elements of IO. 100 */ 101 struct iovec iov; 102 struct iovec caw_iov; /* used for compare and write */ 103 struct iovec *iovs; 104 uint16_t iovcnt; 105 106 uint8_t sense_data[32]; 107 size_t sense_data_len; 108 109 void *bdev_io; 110 111 TAILQ_ENTRY(spdk_scsi_task) scsi_link; 112 113 uint32_t abort_id; 114 struct spdk_bdev_io_wait_entry bdev_io_wait; 115 }; 116 117 struct spdk_scsi_port; 118 struct spdk_scsi_dev; 119 struct spdk_scsi_lun; 120 struct spdk_scsi_lun_desc; 121 122 typedef void (*spdk_scsi_lun_remove_cb_t)(struct spdk_scsi_lun *, void *); 123 typedef void (*spdk_scsi_dev_destruct_cb_t)(void *cb_arg, int rc); 124 125 /** 126 * Initialize SCSI layer. 127 * 128 * \return 0 on success, -1 on failure. 129 */ 130 int spdk_scsi_init(void); 131 132 /** 133 * Stop and clean the SCSI layer. 134 */ 135 void spdk_scsi_fini(void); 136 137 /** 138 * Get the LUN id of the given logical unit. 139 * 140 * \param lun Logical unit. 141 * 142 * \return LUN id of the logical unit. 143 */ 144 int spdk_scsi_lun_get_id(const struct spdk_scsi_lun *lun); 145 146 /** 147 * Get the name of the bdev associated with the given logical unit. 148 * 149 * \param lun Logical unit. 150 * 151 * \return the name of the bdev associated with the logical unit. 152 */ 153 const char *spdk_scsi_lun_get_bdev_name(const struct spdk_scsi_lun *lun); 154 155 /** 156 * Get the SCSI device associated with the given logical unit. 157 * 158 * \param lun Logical unit. 159 * 160 * \return the SCSI device associated with the logical unit. 161 */ 162 const struct spdk_scsi_dev *spdk_scsi_lun_get_dev(const struct spdk_scsi_lun *lun); 163 164 /** 165 * Check if the logical unit is hot removing. 166 * 167 * \param lun Logical unit 168 * 169 * \return true if removing, false otherwise. 170 */ 171 bool spdk_scsi_lun_is_removing(const struct spdk_scsi_lun *lun); 172 173 /** 174 * Get the name of the given SCSI device. 175 * 176 * \param dev SCSI device. 177 * 178 * \return the name of the SCSI device on success, or NULL on failure. 179 */ 180 const char *spdk_scsi_dev_get_name(const struct spdk_scsi_dev *dev); 181 182 /** 183 * Get the id of the given SCSI device. 184 * 185 * \param dev SCSI device. 186 * 187 * \return the id of the SCSI device. 188 */ 189 int spdk_scsi_dev_get_id(const struct spdk_scsi_dev *dev); 190 191 /** 192 * Get the logical unit of the given SCSI device whose id is lun_id. 193 * 194 * \param dev SCSI device. 195 * \param lun_id Id of the logical unit. 196 * 197 * \return the logical unit on success, or NULL on failure. 198 */ 199 struct spdk_scsi_lun *spdk_scsi_dev_get_lun(struct spdk_scsi_dev *dev, int lun_id); 200 201 /** 202 * Get the first logical unit of the given SCSI device. 203 * 204 * \param dev SCSI device. 205 * 206 * \return the first logical unit on success, or NULL if there is no logical unit. 207 */ 208 struct spdk_scsi_lun *spdk_scsi_dev_get_first_lun(struct spdk_scsi_dev *dev); 209 210 /** 211 * Get the next logical unit of a SCSI device. 212 * 213 * \param prev_lun Previous logical unit. 214 * 215 * \return the next logical unit of a SCSI device, or NULL if the prev_lun was the last. 216 */ 217 struct spdk_scsi_lun *spdk_scsi_dev_get_next_lun(struct spdk_scsi_lun *prev_lun); 218 219 /** 220 * Check whether the SCSI device has any pending task. 221 * 222 * \param dev SCSI device. 223 * \param initiator_port Check tasks only from the initiator if specified, or 224 * all all tasks otherwise. 225 * 226 * \return true if the SCSI device has any pending task, or false otherwise. 227 */ 228 bool spdk_scsi_dev_has_pending_tasks(const struct spdk_scsi_dev *dev, 229 const struct spdk_scsi_port *initiator_port); 230 231 /** 232 * Destruct the SCSI device. 233 * 234 * \param dev SCSI device. 235 * \param cb_fn Callback function. 236 * \param cb_arg Argument to callback function. 237 */ 238 void spdk_scsi_dev_destruct(struct spdk_scsi_dev *dev, 239 spdk_scsi_dev_destruct_cb_t cb_fn, void *cb_arg); 240 241 /** 242 * Execute the SCSI management task. 243 * 244 * The task can be constructed by the function spdk_scsi_task_construct(). 245 * Code of task management function to be executed is set before calling this API. 246 * 247 * \param dev SCSI device. 248 * \param task SCSI task to be executed. 249 */ 250 void spdk_scsi_dev_queue_mgmt_task(struct spdk_scsi_dev *dev, struct spdk_scsi_task *task); 251 252 /** 253 * Execute the SCSI task. 254 * 255 * The task can be constructed by the function spdk_scsi_task_construct(). 256 * 257 * \param dev SCSI device. 258 * \param task Task to be executed. 259 */ 260 void spdk_scsi_dev_queue_task(struct spdk_scsi_dev *dev, struct spdk_scsi_task *task); 261 262 /** 263 * Add a new port to the given SCSI device. 264 * 265 * \param dev SCSI device. 266 * \param id Port id. 267 * \param name Port name. 268 * 269 * \return 0 on success, -1 on failure. 270 */ 271 int spdk_scsi_dev_add_port(struct spdk_scsi_dev *dev, uint64_t id, const char *name); 272 273 /** 274 * Delete a specified port of the given SCSI device. 275 * 276 * \param dev SCSI device. 277 * \param id Port id. 278 * 279 * \return 0 on success, -1 on failure. 280 */ 281 int spdk_scsi_dev_delete_port(struct spdk_scsi_dev *dev, uint64_t id); 282 283 /** 284 * Get the port of the given SCSI device whose port ID is id. 285 * 286 * \param dev SCSI device. 287 * \param id Port id. 288 * 289 * \return the port of the SCSI device on success, or NULL on failure. 290 */ 291 struct spdk_scsi_port *spdk_scsi_dev_find_port_by_id(struct spdk_scsi_dev *dev, uint64_t id); 292 293 /** 294 * Allocate I/O channels for all LUNs of the given SCSI device. 295 * 296 * \param dev SCSI device. 297 * 298 * \return 0 on success, -1 on failure. 299 */ 300 int spdk_scsi_dev_allocate_io_channels(struct spdk_scsi_dev *dev); 301 302 /** 303 * Free I/O channels from all LUNs of the given SCSI device. 304 */ 305 void spdk_scsi_dev_free_io_channels(struct spdk_scsi_dev *dev); 306 307 /** 308 * Construct a SCSI device object using the given parameters. 309 * 310 * \param name Name for the SCSI device. 311 * \param bdev_name_list List of bdev names to attach to the LUNs for this SCSI 312 * device. 313 * \param lun_id_list List of LUN IDs for the LUN in this SCSI device. Caller is 314 * responsible for managing the memory containing this list. lun_id_list[x] is 315 * the LUN ID for lun_list[x]. 316 * \param num_luns Number of entries in lun_list and lun_id_list. 317 * \param protocol_id SCSI SPC protocol identifier to report in INQUIRY data 318 * \param hotremove_cb Callback to lun hotremoval. Will be called once hotremove 319 * is first triggered. 320 * \param hotremove_ctx Additional argument to hotremove_cb. 321 * 322 * \return the constructed spdk_scsi_dev object. 323 */ 324 struct spdk_scsi_dev *spdk_scsi_dev_construct(const char *name, 325 const char *bdev_name_list[], 326 int *lun_id_list, 327 int num_luns, 328 uint8_t protocol_id, 329 void (*hotremove_cb)(const struct spdk_scsi_lun *, void *), 330 void *hotremove_ctx); 331 332 /** 333 * Construct a SCSI device object using the more given parameters. 334 * 335 * \param name Name for the SCSI device. 336 * \param bdev_name_list List of bdev names to attach to the LUNs for this SCSI 337 * device. 338 * \param lun_id_list List of LUN IDs for the LUN in this SCSI device. Caller is 339 * responsible for managing the memory containing this list. lun_id_list[x] is 340 * the LUN ID for lun_list[x]. 341 * \param num_luns Number of entries in lun_list and lun_id_list. 342 * \param protocol_id SCSI SPC protocol identifier to report in INQUIRY data 343 * \param resize_cb Callback of lun resize. 344 * \param resize_ctx Additional argument to resize_cb. 345 * \param hotremove_cb Callback to lun hotremoval. Will be called once hotremove 346 * is first triggered. 347 * \param hotremove_ctx Additional argument to hotremove_cb. 348 * 349 * \return the constructed spdk_scsi_dev object. 350 */ 351 struct spdk_scsi_dev *spdk_scsi_dev_construct_ext(const char *name, 352 const char *bdev_name_list[], 353 int *lun_id_list, 354 int num_luns, 355 uint8_t protocol_id, 356 void (*resize_cb)(const struct spdk_scsi_lun *, void *), 357 void *resize_ctx, 358 void (*hotremove_cb)(const struct spdk_scsi_lun *, void *), 359 void *hotremove_ctx); 360 361 /** 362 * Delete a logical unit of the given SCSI device. 363 * 364 * \param dev SCSI device. 365 * \param lun Logical unit to delete. 366 */ 367 void spdk_scsi_dev_delete_lun(struct spdk_scsi_dev *dev, struct spdk_scsi_lun *lun); 368 369 /** 370 * Add a new logical unit to the given SCSI device. 371 * 372 * \param dev SCSI device. 373 * \param bdev_name Name of the bdev attached to the logical unit. 374 * \param lun_id LUN id for the new logical unit. 375 * \param hotremove_cb Callback to lun hotremoval. Will be called once hotremove 376 * is first triggered. 377 * \param hotremove_ctx Additional argument to hotremove_cb. 378 */ 379 int spdk_scsi_dev_add_lun(struct spdk_scsi_dev *dev, const char *bdev_name, int lun_id, 380 void (*hotremove_cb)(const struct spdk_scsi_lun *, void *), 381 void *hotremove_ctx); 382 383 /** 384 * Add a new logical unit to the given SCSI device with more callbacks. 385 * 386 * \param dev SCSI device. 387 * \param bdev_name Name of the bdev attached to the logical unit. 388 * \param lun_id LUN id for the new logical unit. 389 * \param resize_cb Callback of lun resize. 390 * \param resize_ctx Additional argument to resize_cb. 391 * \param hotremove_cb Callback to lun hotremoval. Will be called once hotremove 392 * is first triggered. 393 * \param hotremove_ctx Additional argument to hotremove_cb. 394 */ 395 int spdk_scsi_dev_add_lun_ext(struct spdk_scsi_dev *dev, const char *bdev_name, int lun_id, 396 void (*resize_cb)(const struct spdk_scsi_lun *, void *), 397 void *resize_ctx, 398 void (*hotremove_cb)(const struct spdk_scsi_lun *, void *), 399 void *hotremove_ctx); 400 401 /** 402 * Create a new SCSI port. 403 * 404 * \param id Port id. 405 * \param index Port index. 406 * \param name Port Name. 407 * 408 * \return a pointer to the created SCSI port on success, or NULL on failure. 409 */ 410 struct spdk_scsi_port *spdk_scsi_port_create(uint64_t id, uint16_t index, const char *name); 411 412 /** 413 * Free the SCSI port. 414 * 415 * \param pport SCSI port to free. 416 */ 417 void spdk_scsi_port_free(struct spdk_scsi_port **pport); 418 419 /** 420 * Get the name of the SCSI port. 421 * 422 * \param port SCSI port to query. 423 * 424 * \return the name of the SCSI port. 425 */ 426 const char *spdk_scsi_port_get_name(const struct spdk_scsi_port *port); 427 428 /** 429 * Construct a new SCSI task. 430 * 431 * \param task SCSI task to construct. 432 * \param cpl_fn Called when the task is completed. 433 * \param free_fn Called when the task is freed 434 */ 435 void spdk_scsi_task_construct(struct spdk_scsi_task *task, 436 spdk_scsi_task_cpl cpl_fn, 437 spdk_scsi_task_free free_fn); 438 439 /** 440 * Put the SCSI task. 441 * 442 * \param task SCSI task to put. 443 */ 444 void spdk_scsi_task_put(struct spdk_scsi_task *task); 445 446 /** 447 * Set internal buffer to given one. Caller is owner of that buffer. 448 * 449 * \param task SCSI task. 450 * \param data Pointer to buffer. 451 * \param len Buffer length. 452 */ 453 void spdk_scsi_task_set_data(struct spdk_scsi_task *task, void *data, uint32_t len); 454 455 /** 456 * Single buffer -> vector of buffers. 457 * 458 * \param task SCSI task. 459 * \param src A pointer to the data buffer read from. 460 * \param len Length of the data buffer read from. 461 * 462 * \return the total length of the vector of buffers written into on success, or 463 * -1 on failure. 464 */ 465 int spdk_scsi_task_scatter_data(struct spdk_scsi_task *task, const void *src, size_t len); 466 467 /** 468 * Vector of buffers -> single buffer. 469 * 470 * \param task SCSI task, 471 * \param len Length of the buffer allocated and written into. 472 * 473 * \return a pointer to the buffer allocated and written into. 474 */ 475 void *spdk_scsi_task_gather_data(struct spdk_scsi_task *task, int *len); 476 477 /** 478 * Build sense data for the SCSI task. 479 * 480 * \param task SCSI task. 481 * \param sk Sense key. 482 * \param asc Additional sense code. 483 * \param ascq Additional sense code qualifier. 484 */ 485 void spdk_scsi_task_build_sense_data(struct spdk_scsi_task *task, int sk, int asc, 486 int ascq); 487 488 /** 489 * Set SCSI status code to the SCSI task. When the status code is CHECK CONDITION, 490 * sense data is build too. 491 * 492 * \param task SCSI task. 493 * \param sc Sense code 494 * \param sk Sense key. 495 * \param asc Additional sense code. 496 * \param ascq Additional sense code qualifier. 497 */ 498 void spdk_scsi_task_set_status(struct spdk_scsi_task *task, int sc, int sk, int asc, 499 int ascq); 500 501 /** 502 * Copy SCSI status. 503 * 504 * \param dst SCSI task whose status is written to. 505 * \param src SCSI task whose status is read from. 506 */ 507 void spdk_scsi_task_copy_status(struct spdk_scsi_task *dst, struct spdk_scsi_task *src); 508 509 /** 510 * Process the SCSI task when no LUN is attached. 511 * 512 * \param task SCSI task. 513 */ 514 void spdk_scsi_task_process_null_lun(struct spdk_scsi_task *task); 515 516 /** 517 * Process the aborted SCSI task. 518 * 519 * \param task SCSI task. 520 */ 521 void spdk_scsi_task_process_abort(struct spdk_scsi_task *task); 522 523 /** 524 * Open a logical unit for I/O operations. 525 * 526 * The registered callback function must get all tasks from the upper layer 527 * (e.g. iSCSI) to the LUN done, free the IO channel of the LUN if allocated, 528 * and then close the LUN. 529 * 530 * \param lun Logical unit to open. 531 * \param hotremove_cb Callback function for hot removal of the logical unit. 532 * \param hotremove_ctx Param for hot removal callback function. 533 * \param desc Output parameter for the descriptor when operation is successful. 534 * \return 0 if operation is successful, suitable errno value otherwise 535 */ 536 int spdk_scsi_lun_open(struct spdk_scsi_lun *lun, spdk_scsi_lun_remove_cb_t hotremove_cb, 537 void *hotremove_ctx, struct spdk_scsi_lun_desc **desc); 538 539 /** 540 * Close an opened logical unit. 541 * 542 * \param desc Descriptor of the logical unit. 543 */ 544 void spdk_scsi_lun_close(struct spdk_scsi_lun_desc *desc); 545 546 /** 547 * Allocate I/O channel for the LUN 548 * 549 * \param desc Descriptor of the logical unit. 550 * 551 * \return 0 on success, -1 on failure. 552 */ 553 int spdk_scsi_lun_allocate_io_channel(struct spdk_scsi_lun_desc *desc); 554 555 /** 556 * Free I/O channel from the logical unit 557 * 558 * \param desc Descriptor of the logical unit. 559 */ 560 void spdk_scsi_lun_free_io_channel(struct spdk_scsi_lun_desc *desc); 561 562 /** 563 * Get DIF context for SCSI LUN and SCSI command. 564 * 565 * \param lun Logical unit. 566 * \param task SCSI task which has the payload. 567 * \param dif_ctx Output parameter which will contain initialized DIF context. 568 * 569 * \return true on success or false otherwise. 570 */ 571 bool spdk_scsi_lun_get_dif_ctx(struct spdk_scsi_lun *lun, struct spdk_scsi_task *task, 572 struct spdk_dif_ctx *dif_ctx); 573 574 /** 575 * Set iSCSI Initiator port TransportID 576 * 577 * \param port SCSI initiator port. 578 * \param iscsi_name Initiator name. 579 * \param isid Session ID. 580 */ 581 void spdk_scsi_port_set_iscsi_transport_id(struct spdk_scsi_port *port, 582 char *iscsi_name, uint64_t isid); 583 584 /** 585 * Convert LUN ID from integer to LUN format 586 * 587 * \param lun_id Integer LUN ID 588 * 589 * \return LUN format of LUN ID 590 */ 591 uint64_t spdk_scsi_lun_id_int_to_fmt(int lun_id); 592 593 /** 594 * Convert LUN ID from LUN format to integer 595 * 596 * \param fmt_lun LUN format of LUN ID 597 * 598 * \return integer LUN ID 599 */ 600 int spdk_scsi_lun_id_fmt_to_int(uint64_t fmt_lun); 601 602 /** 603 * Translate SCSI operation code and service action into string 604 * 605 * \param opcode SCSI operation code 606 * 607 * \param sa SCSI service action code 608 * 609 * \return SCSI operation string 610 */ 611 const char *spdk_scsi_sbc_opcode_string(uint8_t opcode, uint16_t sa); 612 #ifdef __cplusplus 613 } 614 #endif 615 616 #endif /* SPDK_SCSI_H */ 617