1 /*- 2 * Copyright (c) 2017 Broadcom. All rights reserved. 3 * The term "Broadcom" refers to Broadcom Limited and/or its subsidiaries. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright notice, 9 * this list of conditions and the following disclaimer. 10 * 11 * 2. Redistributions in binary form must reproduce the above copyright notice, 12 * this list of conditions and the following disclaimer in the documentation 13 * and/or other materials provided with the distribution. 14 * 15 * 3. Neither the name of the copyright holder nor the names of its contributors 16 * may be used to endorse or promote products derived from this software 17 * without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 20 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 23 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 /** 33 * @defgroup scsi_api_target SCSI Target API 34 * @defgroup scsi_api_initiator SCSI Initiator API 35 * @defgroup cam_api Common Access Method (CAM) API 36 * @defgroup cam_io CAM IO 37 */ 38 39 /** 40 * @file 41 * Provides CAM functionality. 42 */ 43 44 #include "ocs.h" 45 #include "ocs_scsi.h" 46 #include "ocs_device.h" 47 48 /* Default IO timeout value for initiators is 30 seconds */ 49 #define OCS_CAM_IO_TIMEOUT 30 50 51 typedef struct { 52 ocs_scsi_sgl_t *sgl; 53 uint32_t sgl_max; 54 uint32_t sgl_count; 55 int32_t rc; 56 } ocs_dmamap_load_arg_t; 57 58 static void ocs_action(struct cam_sim *, union ccb *); 59 static void ocs_poll(struct cam_sim *); 60 61 static ocs_tgt_resource_t *ocs_tgt_resource_get(ocs_fcport *, 62 struct ccb_hdr *, uint32_t *); 63 static int32_t ocs_tgt_resource_abort(struct ocs_softc *, ocs_tgt_resource_t *); 64 static uint32_t ocs_abort_initiator_io(struct ocs_softc *ocs, union ccb *accb); 65 static void ocs_abort_inot(struct ocs_softc *ocs, union ccb *ccb); 66 static void ocs_abort_atio(struct ocs_softc *ocs, union ccb *ccb); 67 static int32_t ocs_target_tmf_cb(ocs_io_t *, ocs_scsi_io_status_e, uint32_t, void *); 68 static int32_t ocs_io_abort_cb(ocs_io_t *, ocs_scsi_io_status_e, uint32_t, void *); 69 static int32_t ocs_task_set_full_or_busy(ocs_io_t *io); 70 static int32_t ocs_initiator_tmf_cb(ocs_io_t *, ocs_scsi_io_status_e, 71 ocs_scsi_cmd_resp_t *, uint32_t, void *); 72 static uint32_t 73 ocs_fcp_change_role(struct ocs_softc *ocs, ocs_fcport *fcp, uint32_t new_role); 74 75 static void ocs_ldt(void *arg); 76 static void ocs_ldt_task(void *arg, int pending); 77 static void ocs_delete_target(ocs_t *ocs, ocs_fcport *fcp, int tgt); 78 uint32_t ocs_add_new_tgt(ocs_node_t *node, ocs_fcport *fcp); 79 uint32_t ocs_update_tgt(ocs_node_t *node, ocs_fcport *fcp, uint32_t tgt_id); 80 81 int32_t ocs_tgt_find(ocs_fcport *fcp, ocs_node_t *node); 82 83 static inline ocs_io_t *ocs_scsi_find_io(struct ocs_softc *ocs, uint32_t tag) 84 { 85 86 return ocs_io_get_instance(ocs, tag); 87 } 88 89 static inline void ocs_target_io_free(ocs_io_t *io) 90 { 91 io->tgt_io.state = OCS_CAM_IO_FREE; 92 io->tgt_io.flags = 0; 93 io->tgt_io.app = NULL; 94 ocs_scsi_io_complete(io); 95 if(io->ocs->io_in_use != 0) 96 atomic_subtract_acq_32(&io->ocs->io_in_use, 1); 97 } 98 99 static int32_t 100 ocs_attach_port(ocs_t *ocs, int chan) 101 { 102 103 struct cam_sim *sim = NULL; 104 struct cam_path *path = NULL; 105 uint32_t max_io = ocs_scsi_get_property(ocs, OCS_SCSI_MAX_IOS); 106 ocs_fcport *fcp = FCPORT(ocs, chan); 107 108 if (NULL == (sim = cam_sim_alloc(ocs_action, ocs_poll, 109 device_get_name(ocs->dev), ocs, 110 device_get_unit(ocs->dev), &ocs->sim_lock, 111 max_io, max_io, ocs->devq))) { 112 device_printf(ocs->dev, "Can't allocate SIM\n"); 113 return 1; 114 } 115 116 mtx_lock(&ocs->sim_lock); 117 if (CAM_SUCCESS != xpt_bus_register(sim, ocs->dev, chan)) { 118 device_printf(ocs->dev, "Can't register bus %d\n", 0); 119 mtx_unlock(&ocs->sim_lock); 120 cam_sim_free(sim, FALSE); 121 return 1; 122 } 123 mtx_unlock(&ocs->sim_lock); 124 125 if (CAM_REQ_CMP != xpt_create_path(&path, NULL, cam_sim_path(sim), 126 CAM_TARGET_WILDCARD, CAM_LUN_WILDCARD)) { 127 device_printf(ocs->dev, "Can't create path\n"); 128 xpt_bus_deregister(cam_sim_path(sim)); 129 mtx_unlock(&ocs->sim_lock); 130 cam_sim_free(sim, FALSE); 131 return 1; 132 } 133 134 fcp->ocs = ocs; 135 fcp->sim = sim; 136 fcp->path = path; 137 138 callout_init_mtx(&fcp->ldt, &ocs->sim_lock, 0); 139 TASK_INIT(&fcp->ltask, 1, ocs_ldt_task, fcp); 140 141 return 0; 142 } 143 144 static int32_t 145 ocs_detach_port(ocs_t *ocs, int32_t chan) 146 { 147 ocs_fcport *fcp = NULL; 148 struct cam_sim *sim = NULL; 149 struct cam_path *path = NULL; 150 fcp = FCPORT(ocs, chan); 151 152 sim = fcp->sim; 153 path = fcp->path; 154 155 callout_drain(&fcp->ldt); 156 ocs_ldt_task(fcp, 0); 157 158 if (fcp->sim) { 159 mtx_lock(&ocs->sim_lock); 160 ocs_tgt_resource_abort(ocs, &fcp->targ_rsrc_wildcard); 161 if (path) { 162 xpt_async(AC_LOST_DEVICE, path, NULL); 163 xpt_free_path(path); 164 fcp->path = NULL; 165 } 166 xpt_bus_deregister(cam_sim_path(sim)); 167 168 cam_sim_free(sim, FALSE); 169 fcp->sim = NULL; 170 mtx_unlock(&ocs->sim_lock); 171 } 172 173 return 0; 174 } 175 176 int32_t 177 ocs_cam_attach(ocs_t *ocs) 178 { 179 struct cam_devq *devq = NULL; 180 int i = 0; 181 uint32_t max_io = ocs_scsi_get_property(ocs, OCS_SCSI_MAX_IOS); 182 183 if (NULL == (devq = cam_simq_alloc(max_io))) { 184 device_printf(ocs->dev, "Can't allocate SIMQ\n"); 185 return -1; 186 } 187 188 ocs->devq = devq; 189 190 if (mtx_initialized(&ocs->sim_lock) == 0) { 191 mtx_init(&ocs->sim_lock, "ocs_sim_lock", NULL, MTX_DEF); 192 } 193 194 for (i = 0; i < (ocs->num_vports + 1); i++) { 195 if (ocs_attach_port(ocs, i)) { 196 ocs_log_err(ocs, "Attach port failed for chan: %d\n", i); 197 goto detach_port; 198 } 199 } 200 201 ocs->io_high_watermark = max_io; 202 ocs->io_in_use = 0; 203 return 0; 204 205 detach_port: 206 while (--i >= 0) { 207 ocs_detach_port(ocs, i); 208 } 209 210 cam_simq_free(ocs->devq); 211 212 if (mtx_initialized(&ocs->sim_lock)) 213 mtx_destroy(&ocs->sim_lock); 214 215 return 1; 216 } 217 218 int32_t 219 ocs_cam_detach(ocs_t *ocs) 220 { 221 int i = 0; 222 223 for (i = (ocs->num_vports); i >= 0; i--) { 224 ocs_detach_port(ocs, i); 225 } 226 227 cam_simq_free(ocs->devq); 228 229 if (mtx_initialized(&ocs->sim_lock)) 230 mtx_destroy(&ocs->sim_lock); 231 232 return 0; 233 } 234 235 /*************************************************************************** 236 * Functions required by SCSI base driver API 237 */ 238 239 /** 240 * @ingroup scsi_api_target 241 * @brief Attach driver to the BSD SCSI layer (a.k.a CAM) 242 * 243 * Allocates + initializes CAM related resources and attaches to the CAM 244 * 245 * @param ocs the driver instance's software context 246 * 247 * @return 0 on success, non-zero otherwise 248 */ 249 int32_t 250 ocs_scsi_tgt_new_device(ocs_t *ocs) 251 { 252 ocs->enable_task_set_full = ocs_scsi_get_property(ocs, 253 OCS_SCSI_ENABLE_TASK_SET_FULL); 254 ocs_log_debug(ocs, "task set full processing is %s\n", 255 ocs->enable_task_set_full ? "enabled" : "disabled"); 256 257 return 0; 258 } 259 260 /** 261 * @ingroup scsi_api_target 262 * @brief Tears down target members of ocs structure. 263 * 264 * Called by OS code when device is removed. 265 * 266 * @param ocs pointer to ocs 267 * 268 * @return returns 0 for success, a negative error code value for failure. 269 */ 270 int32_t 271 ocs_scsi_tgt_del_device(ocs_t *ocs) 272 { 273 274 return 0; 275 } 276 277 /** 278 * @ingroup scsi_api_target 279 * @brief accept new domain notification 280 * 281 * Called by base drive when new domain is discovered. A target-server 282 * will use this call to prepare for new remote node notifications 283 * arising from ocs_scsi_new_initiator(). 284 * 285 * The domain context has an element <b>ocs_scsi_tgt_domain_t tgt_domain</b> 286 * which is declared by the target-server code and is used for target-server 287 * private data. 288 * 289 * This function will only be called if the base-driver has been enabled for 290 * target capability. 291 * 292 * Note that this call is made to target-server backends, 293 * the ocs_scsi_ini_new_domain() function is called to initiator-client backends. 294 * 295 * @param domain pointer to domain 296 * 297 * @return returns 0 for success, a negative error code value for failure. 298 */ 299 int32_t 300 ocs_scsi_tgt_new_domain(ocs_domain_t *domain) 301 { 302 return 0; 303 } 304 305 /** 306 * @ingroup scsi_api_target 307 * @brief accept domain lost notification 308 * 309 * Called by base-driver when a domain goes away. A target-server will 310 * use this call to clean up all domain scoped resources. 311 * 312 * Note that this call is made to target-server backends, 313 * the ocs_scsi_ini_del_domain() function is called to initiator-client backends. 314 * 315 * @param domain pointer to domain 316 * 317 * @return returns 0 for success, a negative error code value for failure. 318 */ 319 void 320 ocs_scsi_tgt_del_domain(ocs_domain_t *domain) 321 { 322 } 323 324 /** 325 * @ingroup scsi_api_target 326 * @brief accept new sli port (sport) notification 327 * 328 * Called by base drive when new sport is discovered. A target-server 329 * will use this call to prepare for new remote node notifications 330 * arising from ocs_scsi_new_initiator(). 331 * 332 * The domain context has an element <b>ocs_scsi_tgt_sport_t tgt_sport</b> 333 * which is declared by the target-server code and is used for 334 * target-server private data. 335 * 336 * This function will only be called if the base-driver has been enabled for 337 * target capability. 338 * 339 * Note that this call is made to target-server backends, 340 * the ocs_scsi_tgt_new_domain() is called to initiator-client backends. 341 * 342 * @param sport pointer to SLI port 343 * 344 * @return returns 0 for success, a negative error code value for failure. 345 */ 346 int32_t 347 ocs_scsi_tgt_new_sport(ocs_sport_t *sport) 348 { 349 ocs_t *ocs = sport->ocs; 350 351 if(!sport->is_vport) { 352 sport->tgt_data = FCPORT(ocs, 0); 353 } 354 355 return 0; 356 } 357 358 /** 359 * @ingroup scsi_api_target 360 * @brief accept SLI port gone notification 361 * 362 * Called by base-driver when a sport goes away. A target-server will 363 * use this call to clean up all sport scoped resources. 364 * 365 * Note that this call is made to target-server backends, 366 * the ocs_scsi_ini_del_sport() is called to initiator-client backends. 367 * 368 * @param sport pointer to SLI port 369 * 370 * @return returns 0 for success, a negative error code value for failure. 371 */ 372 void 373 ocs_scsi_tgt_del_sport(ocs_sport_t *sport) 374 { 375 return; 376 } 377 378 /** 379 * @ingroup scsi_api_target 380 * @brief receive notification of a new SCSI initiator node 381 * 382 * Sent by base driver to notify a target-server of the presense of a new 383 * remote initiator. The target-server may use this call to prepare for 384 * inbound IO from this node. 385 * 386 * The ocs_node_t structure has and elment of type ocs_scsi_tgt_node_t named 387 * tgt_node that is declared and used by a target-server for private 388 * information. 389 * 390 * This function is only called if the target capability is enabled in driver. 391 * 392 * @param node pointer to new remote initiator node 393 * 394 * @return returns 0 for success, a negative error code value for failure. 395 * 396 * @note 397 */ 398 int32_t 399 ocs_scsi_new_initiator(ocs_node_t *node) 400 { 401 ocs_t *ocs = node->ocs; 402 struct ac_contract ac; 403 struct ac_device_changed *adc; 404 405 ocs_fcport *fcp = NULL; 406 407 fcp = node->sport->tgt_data; 408 if (fcp == NULL) { 409 ocs_log_err(ocs, "FCP is NULL \n"); 410 return 1; 411 } 412 413 /* 414 * Update the IO watermark by decrementing it by the 415 * number of IOs reserved for each initiator. 416 */ 417 atomic_subtract_acq_32(&ocs->io_high_watermark, OCS_RSVD_INI_IO); 418 419 ac.contract_number = AC_CONTRACT_DEV_CHG; 420 adc = (struct ac_device_changed *) ac.contract_data; 421 adc->wwpn = ocs_node_get_wwpn(node); 422 adc->port = node->rnode.fc_id; 423 adc->target = node->instance_index; 424 adc->arrived = 1; 425 xpt_async(AC_CONTRACT, fcp->path, &ac); 426 427 return 0; 428 } 429 430 /** 431 * @ingroup scsi_api_target 432 * @brief validate new initiator 433 * 434 * Sent by base driver to validate a remote initiatiator. The target-server 435 * returns TRUE if this initiator should be accepted. 436 * 437 * This function is only called if the target capability is enabled in driver. 438 * 439 * @param node pointer to remote initiator node to validate 440 * 441 * @return TRUE if initiator should be accepted, FALSE if it should be rejected 442 * 443 * @note 444 */ 445 446 int32_t 447 ocs_scsi_validate_initiator(ocs_node_t *node) 448 { 449 return 1; 450 } 451 452 /** 453 * @ingroup scsi_api_target 454 * @brief Delete a SCSI initiator node 455 * 456 * Sent by base driver to notify a target-server that a remote initiator 457 * is now gone. The base driver will have terminated all outstanding IOs 458 * and the target-server will receive appropriate completions. 459 * 460 * This function is only called if the base driver is enabled for 461 * target capability. 462 * 463 * @param node pointer node being deleted 464 * @param reason Reason why initiator is gone. 465 * 466 * @return OCS_SCSI_CALL_COMPLETE to indicate that all work was completed 467 * 468 * @note 469 */ 470 int32_t 471 ocs_scsi_del_initiator(ocs_node_t *node, ocs_scsi_del_initiator_reason_e reason) 472 { 473 ocs_t *ocs = node->ocs; 474 475 struct ac_contract ac; 476 struct ac_device_changed *adc; 477 ocs_fcport *fcp = NULL; 478 479 fcp = node->sport->tgt_data; 480 if (fcp == NULL) { 481 ocs_log_err(ocs, "FCP is NULL \n"); 482 return 1; 483 } 484 485 ac.contract_number = AC_CONTRACT_DEV_CHG; 486 adc = (struct ac_device_changed *) ac.contract_data; 487 adc->wwpn = ocs_node_get_wwpn(node); 488 adc->port = node->rnode.fc_id; 489 adc->target = node->instance_index; 490 adc->arrived = 0; 491 xpt_async(AC_CONTRACT, fcp->path, &ac); 492 493 if (reason == OCS_SCSI_INITIATOR_MISSING) { 494 return OCS_SCSI_CALL_COMPLETE; 495 } 496 497 /* 498 * Update the IO watermark by incrementing it by the 499 * number of IOs reserved for each initiator. 500 */ 501 atomic_add_acq_32(&ocs->io_high_watermark, OCS_RSVD_INI_IO); 502 503 return OCS_SCSI_CALL_COMPLETE; 504 } 505 506 /** 507 * @ingroup scsi_api_target 508 * @brief receive FCP SCSI Command 509 * 510 * Called by the base driver when a new SCSI command has been received. The 511 * target-server will process the command, and issue data and/or response phase 512 * requests to the base driver. 513 * 514 * The IO context (ocs_io_t) structure has and element of type 515 * ocs_scsi_tgt_io_t named tgt_io that is declared and used by 516 * a target-server for private information. 517 * 518 * @param io pointer to IO context 519 * @param lun LUN for this IO 520 * @param cdb pointer to SCSI CDB 521 * @param cdb_len length of CDB in bytes 522 * @param flags command flags 523 * 524 * @return returns 0 for success, a negative error code value for failure. 525 */ 526 int32_t ocs_scsi_recv_cmd(ocs_io_t *io, uint64_t lun, uint8_t *cdb, 527 uint32_t cdb_len, uint32_t flags) 528 { 529 ocs_t *ocs = io->ocs; 530 struct ccb_accept_tio *atio = NULL; 531 ocs_node_t *node = io->node; 532 ocs_tgt_resource_t *trsrc = NULL; 533 int32_t rc = -1; 534 ocs_fcport *fcp = NULL; 535 536 fcp = node->sport->tgt_data; 537 if (fcp == NULL) { 538 ocs_log_err(ocs, "FCP is NULL \n"); 539 return 1; 540 } 541 542 atomic_add_acq_32(&ocs->io_in_use, 1); 543 544 /* set target io timeout */ 545 io->timeout = ocs->target_io_timer_sec; 546 547 if (ocs->enable_task_set_full && 548 (ocs->io_in_use >= ocs->io_high_watermark)) { 549 return ocs_task_set_full_or_busy(io); 550 } else { 551 atomic_store_rel_32(&io->node->tgt_node.busy_sent, FALSE); 552 } 553 554 if ((lun < OCS_MAX_LUN) && fcp->targ_rsrc[lun].enabled) { 555 trsrc = &fcp->targ_rsrc[lun]; 556 } else if (fcp->targ_rsrc_wildcard.enabled) { 557 trsrc = &fcp->targ_rsrc_wildcard; 558 } 559 560 if (trsrc) { 561 atio = (struct ccb_accept_tio *)STAILQ_FIRST(&trsrc->atio); 562 } 563 564 if (atio) { 565 STAILQ_REMOVE_HEAD(&trsrc->atio, sim_links.stqe); 566 567 atio->ccb_h.status = CAM_CDB_RECVD; 568 atio->ccb_h.target_lun = lun; 569 atio->sense_len = 0; 570 571 atio->init_id = node->instance_index; 572 atio->tag_id = io->tag; 573 atio->ccb_h.ccb_io_ptr = io; 574 575 if (flags & OCS_SCSI_CMD_SIMPLE) 576 atio->tag_action = MSG_SIMPLE_Q_TAG; 577 else if (flags & OCS_SCSI_CMD_HEAD_OF_QUEUE) 578 atio->tag_action = MSG_HEAD_OF_Q_TAG; 579 else if (flags & OCS_SCSI_CMD_ORDERED) 580 atio->tag_action = MSG_ORDERED_Q_TAG; 581 else if (flags & OCS_SCSI_CMD_ACA) 582 atio->tag_action = MSG_ACA_TASK; 583 else 584 atio->tag_action = CAM_TAG_ACTION_NONE; 585 atio->priority = (flags & OCS_SCSI_PRIORITY_MASK) >> 586 OCS_SCSI_PRIORITY_SHIFT; 587 588 atio->cdb_len = cdb_len; 589 ocs_memcpy(atio->cdb_io.cdb_bytes, cdb, cdb_len); 590 591 io->tgt_io.flags = 0; 592 io->tgt_io.state = OCS_CAM_IO_COMMAND; 593 io->tgt_io.lun = lun; 594 595 xpt_done((union ccb *)atio); 596 597 rc = 0; 598 } else { 599 device_printf( 600 ocs->dev, "%s: no ATIO for LUN %lx (en=%s) OX_ID %#x\n", 601 __func__, (unsigned long)lun, 602 trsrc ? (trsrc->enabled ? "T" : "F") : "X", 603 be16toh(io->init_task_tag)); 604 605 io->tgt_io.state = OCS_CAM_IO_MAX; 606 ocs_target_io_free(io); 607 } 608 609 return rc; 610 } 611 612 /** 613 * @ingroup scsi_api_target 614 * @brief receive FCP SCSI Command with first burst data. 615 * 616 * Receive a new FCP SCSI command from the base driver with first burst data. 617 * 618 * @param io pointer to IO context 619 * @param lun LUN for this IO 620 * @param cdb pointer to SCSI CDB 621 * @param cdb_len length of CDB in bytes 622 * @param flags command flags 623 * @param first_burst_buffers first burst buffers 624 * @param first_burst_buffer_count The number of bytes received in the first burst 625 * 626 * @return returns 0 for success, a negative error code value for failure. 627 */ 628 int32_t ocs_scsi_recv_cmd_first_burst(ocs_io_t *io, uint64_t lun, uint8_t *cdb, 629 uint32_t cdb_len, uint32_t flags, 630 ocs_dma_t first_burst_buffers[], 631 uint32_t first_burst_buffer_count) 632 { 633 return -1; 634 } 635 636 /** 637 * @ingroup scsi_api_target 638 * @brief receive a TMF command IO 639 * 640 * Called by the base driver when a SCSI TMF command has been received. The 641 * target-server will process the command, aborting commands as needed, and post 642 * a response using ocs_scsi_send_resp() 643 * 644 * The IO context (ocs_io_t) structure has and element of type ocs_scsi_tgt_io_t named 645 * tgt_io that is declared and used by a target-server for private information. 646 * 647 * If the target-server walks the nodes active_ios linked list, and starts IO 648 * abort processing, the code <b>must</b> be sure not to abort the IO passed into the 649 * ocs_scsi_recv_tmf() command. 650 * 651 * @param tmfio pointer to IO context 652 * @param lun logical unit value 653 * @param cmd command request 654 * @param abortio pointer to IO object to abort for TASK_ABORT (NULL for all other TMF) 655 * @param flags flags 656 * 657 * @return returns 0 for success, a negative error code value for failure. 658 */ 659 int32_t ocs_scsi_recv_tmf(ocs_io_t *tmfio, uint64_t lun, ocs_scsi_tmf_cmd_e cmd, 660 ocs_io_t *abortio, uint32_t flags) 661 { 662 ocs_t *ocs = tmfio->ocs; 663 ocs_node_t *node = tmfio->node; 664 ocs_tgt_resource_t *trsrc = NULL; 665 struct ccb_immediate_notify *inot = NULL; 666 int32_t rc = -1; 667 ocs_fcport *fcp = NULL; 668 669 fcp = node->sport->tgt_data; 670 if (fcp == NULL) { 671 ocs_log_err(ocs, "FCP is NULL \n"); 672 return 1; 673 } 674 675 if ((lun < OCS_MAX_LUN) && fcp->targ_rsrc[lun].enabled) { 676 trsrc = &fcp->targ_rsrc[lun]; 677 } else if (fcp->targ_rsrc_wildcard.enabled) { 678 trsrc = &fcp->targ_rsrc_wildcard; 679 } 680 681 device_printf(tmfio->ocs->dev, "%s: io=%p cmd=%#x LU=%lx en=%s\n", 682 __func__, tmfio, cmd, (unsigned long)lun, 683 trsrc ? (trsrc->enabled ? "T" : "F") : "X"); 684 if (trsrc) { 685 inot = (struct ccb_immediate_notify *)STAILQ_FIRST(&trsrc->inot); 686 } 687 688 if (!inot) { 689 device_printf( 690 ocs->dev, "%s: no INOT for LUN %llx (en=%s) OX_ID %#x\n", 691 __func__, (unsigned long long)lun, trsrc ? (trsrc->enabled ? "T" : "F") : "X", 692 be16toh(tmfio->init_task_tag)); 693 694 if (abortio) { 695 ocs_scsi_io_complete(abortio); 696 } 697 ocs_scsi_io_complete(tmfio); 698 goto ocs_scsi_recv_tmf_out; 699 } 700 701 tmfio->tgt_io.app = abortio; 702 703 STAILQ_REMOVE_HEAD(&trsrc->inot, sim_links.stqe); 704 705 inot->tag_id = tmfio->tag; 706 inot->seq_id = tmfio->tag; 707 708 if ((lun < OCS_MAX_LUN) && fcp->targ_rsrc[lun].enabled) { 709 inot->initiator_id = node->instance_index; 710 } else { 711 inot->initiator_id = CAM_TARGET_WILDCARD; 712 } 713 714 inot->ccb_h.status = CAM_MESSAGE_RECV; 715 inot->ccb_h.target_lun = lun; 716 717 switch (cmd) { 718 case OCS_SCSI_TMF_ABORT_TASK: 719 inot->arg = MSG_ABORT_TASK; 720 inot->seq_id = abortio->tag; 721 device_printf(ocs->dev, "%s: ABTS IO.%#x st=%#x\n", 722 __func__, abortio->tag, abortio->tgt_io.state); 723 abortio->tgt_io.flags |= OCS_CAM_IO_F_ABORT_RECV; 724 abortio->tgt_io.flags |= OCS_CAM_IO_F_ABORT_NOTIFY; 725 break; 726 case OCS_SCSI_TMF_QUERY_TASK_SET: 727 device_printf(ocs->dev, 728 "%s: OCS_SCSI_TMF_QUERY_TASK_SET not supported\n", 729 __func__); 730 STAILQ_INSERT_TAIL(&trsrc->inot, &inot->ccb_h, sim_links.stqe); 731 ocs_scsi_io_complete(tmfio); 732 goto ocs_scsi_recv_tmf_out; 733 break; 734 case OCS_SCSI_TMF_ABORT_TASK_SET: 735 inot->arg = MSG_ABORT_TASK_SET; 736 break; 737 case OCS_SCSI_TMF_CLEAR_TASK_SET: 738 inot->arg = MSG_CLEAR_TASK_SET; 739 break; 740 case OCS_SCSI_TMF_QUERY_ASYNCHRONOUS_EVENT: 741 inot->arg = MSG_QUERY_ASYNC_EVENT; 742 break; 743 case OCS_SCSI_TMF_LOGICAL_UNIT_RESET: 744 inot->arg = MSG_LOGICAL_UNIT_RESET; 745 break; 746 case OCS_SCSI_TMF_CLEAR_ACA: 747 inot->arg = MSG_CLEAR_ACA; 748 break; 749 case OCS_SCSI_TMF_TARGET_RESET: 750 inot->arg = MSG_TARGET_RESET; 751 break; 752 default: 753 device_printf(ocs->dev, "%s: unsupported TMF %#x\n", 754 __func__, cmd); 755 STAILQ_INSERT_TAIL(&trsrc->inot, &inot->ccb_h, sim_links.stqe); 756 goto ocs_scsi_recv_tmf_out; 757 } 758 759 rc = 0; 760 761 xpt_print(inot->ccb_h.path, "%s: func=%#x stat=%#x id=%#x lun=%#x" 762 " flags=%#x tag=%#x seq=%#x ini=%#x arg=%#x\n", 763 __func__, inot->ccb_h.func_code, inot->ccb_h.status, 764 inot->ccb_h.target_id, 765 (unsigned int)inot->ccb_h.target_lun, inot->ccb_h.flags, 766 inot->tag_id, inot->seq_id, inot->initiator_id, 767 inot->arg); 768 xpt_done((union ccb *)inot); 769 770 if (abortio) { 771 abortio->tgt_io.flags |= OCS_CAM_IO_F_ABORT_DEV; 772 rc = ocs_scsi_tgt_abort_io(abortio, ocs_io_abort_cb, tmfio); 773 } 774 775 ocs_scsi_recv_tmf_out: 776 return rc; 777 } 778 779 /** 780 * @ingroup scsi_api_initiator 781 * @brief Initializes any initiator fields on the ocs structure. 782 * 783 * Called by OS initialization code when a new device is discovered. 784 * 785 * @param ocs pointer to ocs 786 * 787 * @return returns 0 for success, a negative error code value for failure. 788 */ 789 int32_t 790 ocs_scsi_ini_new_device(ocs_t *ocs) 791 { 792 793 return 0; 794 } 795 796 /** 797 * @ingroup scsi_api_initiator 798 * @brief Tears down initiator members of ocs structure. 799 * 800 * Called by OS code when device is removed. 801 * 802 * @param ocs pointer to ocs 803 * 804 * @return returns 0 for success, a negative error code value for failure. 805 */ 806 807 int32_t 808 ocs_scsi_ini_del_device(ocs_t *ocs) 809 { 810 811 return 0; 812 } 813 814 /** 815 * @ingroup scsi_api_initiator 816 * @brief accept new domain notification 817 * 818 * Called by base drive when new domain is discovered. An initiator-client 819 * will accept this call to prepare for new remote node notifications 820 * arising from ocs_scsi_new_target(). 821 * 822 * The domain context has the element <b>ocs_scsi_ini_domain_t ini_domain</b> 823 * which is declared by the initiator-client code and is used for 824 * initiator-client private data. 825 * 826 * This function will only be called if the base-driver has been enabled for 827 * initiator capability. 828 * 829 * Note that this call is made to initiator-client backends, 830 * the ocs_scsi_tgt_new_domain() function is called to target-server backends. 831 * 832 * @param domain pointer to domain 833 * 834 * @return returns 0 for success, a negative error code value for failure. 835 */ 836 int32_t 837 ocs_scsi_ini_new_domain(ocs_domain_t *domain) 838 { 839 return 0; 840 } 841 842 /** 843 * @ingroup scsi_api_initiator 844 * @brief accept domain lost notification 845 * 846 * Called by base-driver when a domain goes away. An initiator-client will 847 * use this call to clean up all domain scoped resources. 848 * 849 * This function will only be called if the base-driver has been enabled for 850 * initiator capability. 851 * 852 * Note that this call is made to initiator-client backends, 853 * the ocs_scsi_tgt_del_domain() function is called to target-server backends. 854 * 855 * @param domain pointer to domain 856 * 857 * @return returns 0 for success, a negative error code value for failure. 858 */ 859 void 860 ocs_scsi_ini_del_domain(ocs_domain_t *domain) 861 { 862 } 863 864 /** 865 * @ingroup scsi_api_initiator 866 * @brief accept new sli port notification 867 * 868 * Called by base drive when new sli port (sport) is discovered. 869 * A target-server will use this call to prepare for new remote node 870 * notifications arising from ocs_scsi_new_initiator(). 871 * 872 * This function will only be called if the base-driver has been enabled for 873 * target capability. 874 * 875 * Note that this call is made to target-server backends, 876 * the ocs_scsi_ini_new_sport() function is called to initiator-client backends. 877 * 878 * @param sport pointer to sport 879 * 880 * @return returns 0 for success, a negative error code value for failure. 881 */ 882 int32_t 883 ocs_scsi_ini_new_sport(ocs_sport_t *sport) 884 { 885 ocs_t *ocs = sport->ocs; 886 ocs_fcport *fcp = FCPORT(ocs, 0); 887 888 if (!sport->is_vport) { 889 sport->tgt_data = fcp; 890 fcp->fc_id = sport->fc_id; 891 } 892 893 return 0; 894 } 895 896 /** 897 * @ingroup scsi_api_initiator 898 * @brief accept sli port gone notification 899 * 900 * Called by base-driver when a sport goes away. A target-server will 901 * use this call to clean up all sport scoped resources. 902 * 903 * Note that this call is made to target-server backends, 904 * the ocs_scsi_ini_del_sport() function is called to initiator-client backends. 905 * 906 * @param sport pointer to SLI port 907 * 908 * @return returns 0 for success, a negative error code value for failure. 909 */ 910 void 911 ocs_scsi_ini_del_sport(ocs_sport_t *sport) 912 { 913 ocs_t *ocs = sport->ocs; 914 ocs_fcport *fcp = FCPORT(ocs, 0); 915 916 if (!sport->is_vport) { 917 fcp->fc_id = 0; 918 } 919 } 920 921 void 922 ocs_scsi_sport_deleted(ocs_sport_t *sport) 923 { 924 ocs_t *ocs = sport->ocs; 925 ocs_fcport *fcp = NULL; 926 927 ocs_xport_stats_t value; 928 929 if (!sport->is_vport) { 930 return; 931 } 932 933 fcp = sport->tgt_data; 934 935 ocs_xport_status(ocs->xport, OCS_XPORT_PORT_STATUS, &value); 936 937 if (value.value == 0) { 938 ocs_log_debug(ocs, "PORT offline,.. skipping\n"); 939 return; 940 } 941 942 if ((fcp->role != KNOB_ROLE_NONE)) { 943 if(fcp->vport->sport != NULL) { 944 ocs_log_debug(ocs,"sport is not NULL, skipping\n"); 945 return; 946 } 947 948 ocs_sport_vport_alloc(ocs->domain, fcp->vport); 949 return; 950 } 951 952 } 953 954 int32_t 955 ocs_tgt_find(ocs_fcport *fcp, ocs_node_t *node) 956 { 957 ocs_fc_target_t *tgt = NULL; 958 uint32_t i; 959 960 for (i = 0; i < OCS_MAX_TARGETS; i++) { 961 tgt = &fcp->tgt[i]; 962 963 if (tgt->state == OCS_TGT_STATE_NONE) 964 continue; 965 966 if (ocs_node_get_wwpn(node) == tgt->wwpn) { 967 return i; 968 } 969 } 970 971 return -1; 972 } 973 974 /** 975 * @ingroup scsi_api_initiator 976 * @brief receive notification of a new SCSI target node 977 * 978 * Sent by base driver to notify an initiator-client of the presense of a new 979 * remote target. The initiator-server may use this call to prepare for 980 * inbound IO from this node. 981 * 982 * This function is only called if the base driver is enabled for 983 * initiator capability. 984 * 985 * @param node pointer to new remote initiator node 986 * 987 * @return none 988 * 989 * @note 990 */ 991 992 uint32_t 993 ocs_update_tgt(ocs_node_t *node, ocs_fcport *fcp, uint32_t tgt_id) 994 { 995 ocs_fc_target_t *tgt = NULL; 996 997 tgt = &fcp->tgt[tgt_id]; 998 999 tgt->node_id = node->instance_index; 1000 tgt->state = OCS_TGT_STATE_VALID; 1001 1002 tgt->port_id = node->rnode.fc_id; 1003 tgt->wwpn = ocs_node_get_wwpn(node); 1004 tgt->wwnn = ocs_node_get_wwnn(node); 1005 return 0; 1006 } 1007 1008 uint32_t 1009 ocs_add_new_tgt(ocs_node_t *node, ocs_fcport *fcp) 1010 { 1011 uint32_t i; 1012 1013 struct ocs_softc *ocs = node->ocs; 1014 union ccb *ccb = NULL; 1015 for (i = 0; i < OCS_MAX_TARGETS; i++) { 1016 if (fcp->tgt[i].state == OCS_TGT_STATE_NONE) 1017 break; 1018 } 1019 1020 if (NULL == (ccb = xpt_alloc_ccb_nowait())) { 1021 device_printf(ocs->dev, "%s: ccb allocation failed\n", __func__); 1022 return -1; 1023 } 1024 1025 if (CAM_REQ_CMP != xpt_create_path(&ccb->ccb_h.path, xpt_periph, 1026 cam_sim_path(fcp->sim), 1027 i, CAM_LUN_WILDCARD)) { 1028 device_printf( 1029 ocs->dev, "%s: target path creation failed\n", __func__); 1030 xpt_free_ccb(ccb); 1031 return -1; 1032 } 1033 1034 ocs_update_tgt(node, fcp, i); 1035 xpt_rescan(ccb); 1036 return 0; 1037 } 1038 1039 int32_t 1040 ocs_scsi_new_target(ocs_node_t *node) 1041 { 1042 ocs_fcport *fcp = NULL; 1043 int32_t i; 1044 1045 fcp = node->sport->tgt_data; 1046 if (fcp == NULL) { 1047 printf("%s:FCP is NULL \n", __func__); 1048 return 0; 1049 } 1050 1051 i = ocs_tgt_find(fcp, node); 1052 1053 if (i < 0) { 1054 ocs_add_new_tgt(node, fcp); 1055 return 0; 1056 } 1057 1058 ocs_update_tgt(node, fcp, i); 1059 return 0; 1060 } 1061 1062 static void 1063 ocs_delete_target(ocs_t *ocs, ocs_fcport *fcp, int tgt) 1064 { 1065 struct cam_path *cpath = NULL; 1066 1067 if (!fcp->sim) { 1068 device_printf(ocs->dev, "%s: calling with NULL sim\n", __func__); 1069 return; 1070 } 1071 1072 if (CAM_REQ_CMP == xpt_create_path(&cpath, NULL, cam_sim_path(fcp->sim), 1073 tgt, CAM_LUN_WILDCARD)) { 1074 xpt_async(AC_LOST_DEVICE, cpath, NULL); 1075 1076 xpt_free_path(cpath); 1077 } 1078 } 1079 1080 /* 1081 * Device Lost Timer Function- when we have decided that a device was lost, 1082 * we wait a specific period of time prior to telling the OS about lost device. 1083 * 1084 * This timer function gets activated when the device was lost. 1085 * This function fires once a second and then scans the port database 1086 * for devices that are marked dead but still have a virtual target assigned. 1087 * We decrement a counter for that port database entry, and when it hits zero, 1088 * we tell the OS the device was lost. Timer will be stopped when the device 1089 * comes back active or removed from the OS. 1090 */ 1091 static void 1092 ocs_ldt(void *arg) 1093 { 1094 ocs_fcport *fcp = arg; 1095 taskqueue_enqueue(taskqueue_thread, &fcp->ltask); 1096 } 1097 1098 static void 1099 ocs_ldt_task(void *arg, int pending) 1100 { 1101 ocs_fcport *fcp = arg; 1102 ocs_t *ocs = fcp->ocs; 1103 int i, more_to_do = 0; 1104 ocs_fc_target_t *tgt = NULL; 1105 1106 for (i = 0; i < OCS_MAX_TARGETS; i++) { 1107 tgt = &fcp->tgt[i]; 1108 1109 if (tgt->state != OCS_TGT_STATE_LOST) { 1110 continue; 1111 } 1112 1113 if ((tgt->gone_timer != 0) && (ocs->attached)){ 1114 tgt->gone_timer -= 1; 1115 more_to_do++; 1116 continue; 1117 } 1118 1119 ocs_delete_target(ocs, fcp, i); 1120 1121 tgt->state = OCS_TGT_STATE_NONE; 1122 } 1123 1124 if (more_to_do) { 1125 callout_reset(&fcp->ldt, hz, ocs_ldt, fcp); 1126 } else { 1127 callout_deactivate(&fcp->ldt); 1128 } 1129 1130 } 1131 1132 /** 1133 * @ingroup scsi_api_initiator 1134 * @brief Delete a SCSI target node 1135 * 1136 * Sent by base driver to notify a initiator-client that a remote target 1137 * is now gone. The base driver will have terminated all outstanding IOs 1138 * and the initiator-client will receive appropriate completions. 1139 * 1140 * The ocs_node_t structure has and elment of type ocs_scsi_ini_node_t named 1141 * ini_node that is declared and used by a target-server for private 1142 * information. 1143 * 1144 * This function is only called if the base driver is enabled for 1145 * initiator capability. 1146 * 1147 * @param node pointer node being deleted 1148 * @param reason reason for deleting the target 1149 * 1150 * @return Returns OCS_SCSI_CALL_ASYNC if target delete is queued for async 1151 * completion and OCS_SCSI_CALL_COMPLETE if call completed or error. 1152 * 1153 * @note 1154 */ 1155 int32_t 1156 ocs_scsi_del_target(ocs_node_t *node, ocs_scsi_del_target_reason_e reason) 1157 { 1158 struct ocs_softc *ocs = node->ocs; 1159 ocs_fcport *fcp = NULL; 1160 ocs_fc_target_t *tgt = NULL; 1161 int32_t tgt_id; 1162 1163 if (ocs == NULL) { 1164 ocs_log_err(ocs,"OCS is NULL \n"); 1165 return -1; 1166 } 1167 1168 fcp = node->sport->tgt_data; 1169 if (fcp == NULL) { 1170 ocs_log_err(ocs,"FCP is NULL \n"); 1171 return -1; 1172 } 1173 1174 tgt_id = ocs_tgt_find(fcp, node); 1175 if (tgt_id == -1) { 1176 ocs_log_err(ocs,"target is invalid\n"); 1177 return -1; 1178 } 1179 1180 tgt = &fcp->tgt[tgt_id]; 1181 1182 // IF in shutdown delete target. 1183 if(!ocs->attached) { 1184 ocs_delete_target(ocs, fcp, tgt_id); 1185 } else { 1186 tgt->state = OCS_TGT_STATE_LOST; 1187 tgt->gone_timer = 30; 1188 if (!callout_active(&fcp->ldt)) { 1189 callout_reset(&fcp->ldt, hz, ocs_ldt, fcp); 1190 } 1191 } 1192 1193 return 0; 1194 } 1195 1196 /** 1197 * @brief Initialize SCSI IO 1198 * 1199 * Initialize SCSI IO, this function is called once per IO during IO pool 1200 * allocation so that the target server may initialize any of its own private 1201 * data. 1202 * 1203 * @param io pointer to SCSI IO object 1204 * 1205 * @return returns 0 for success, a negative error code value for failure. 1206 */ 1207 int32_t 1208 ocs_scsi_tgt_io_init(ocs_io_t *io) 1209 { 1210 return 0; 1211 } 1212 1213 /** 1214 * @brief Uninitialize SCSI IO 1215 * 1216 * Uninitialize target server private data in a SCSI io object 1217 * 1218 * @param io pointer to SCSI IO object 1219 * 1220 * @return returns 0 for success, a negative error code value for failure. 1221 */ 1222 int32_t 1223 ocs_scsi_tgt_io_exit(ocs_io_t *io) 1224 { 1225 return 0; 1226 } 1227 1228 /** 1229 * @brief Initialize SCSI IO 1230 * 1231 * Initialize SCSI IO, this function is called once per IO during IO pool 1232 * allocation so that the initiator client may initialize any of its own private 1233 * data. 1234 * 1235 * @param io pointer to SCSI IO object 1236 * 1237 * @return returns 0 for success, a negative error code value for failure. 1238 */ 1239 int32_t 1240 ocs_scsi_ini_io_init(ocs_io_t *io) 1241 { 1242 return 0; 1243 } 1244 1245 /** 1246 * @brief Uninitialize SCSI IO 1247 * 1248 * Uninitialize initiator client private data in a SCSI io object 1249 * 1250 * @param io pointer to SCSI IO object 1251 * 1252 * @return returns 0 for success, a negative error code value for failure. 1253 */ 1254 int32_t 1255 ocs_scsi_ini_io_exit(ocs_io_t *io) 1256 { 1257 return 0; 1258 } 1259 /* 1260 * End of functions required by SCSI base driver API 1261 ***************************************************************************/ 1262 1263 static __inline void 1264 ocs_set_ccb_status(union ccb *ccb, cam_status status) 1265 { 1266 ccb->ccb_h.status &= ~CAM_STATUS_MASK; 1267 ccb->ccb_h.status |= status; 1268 } 1269 1270 static int32_t 1271 ocs_task_set_full_or_busy_cb(ocs_io_t *io, ocs_scsi_io_status_e scsi_status, 1272 uint32_t flags, void *arg) 1273 { 1274 1275 ocs_target_io_free(io); 1276 1277 return 0; 1278 } 1279 1280 /** 1281 * @brief send SCSI task set full or busy status 1282 * 1283 * A SCSI task set full or busy response is sent depending on whether 1284 * another IO is already active on the LUN. 1285 * 1286 * @param io pointer to IO context 1287 * 1288 * @return returns 0 for success, a negative error code value for failure. 1289 */ 1290 1291 static int32_t 1292 ocs_task_set_full_or_busy(ocs_io_t *io) 1293 { 1294 ocs_scsi_cmd_resp_t rsp = { 0 }; 1295 ocs_t *ocs = io->ocs; 1296 1297 /* 1298 * If there is another command for the LUN, then send task set full, 1299 * if this is the first one, then send the busy status. 1300 * 1301 * if 'busy sent' is FALSE, set it to TRUE and send BUSY 1302 * otherwise send FULL 1303 */ 1304 if (atomic_cmpset_acq_32(&io->node->tgt_node.busy_sent, FALSE, TRUE)) { 1305 rsp.scsi_status = SCSI_STATUS_BUSY; /* Busy */ 1306 printf("%s: busy [%s] tag=%x iiu=%d ihw=%d\n", __func__, 1307 io->node->display_name, io->tag, 1308 io->ocs->io_in_use, io->ocs->io_high_watermark); 1309 } else { 1310 rsp.scsi_status = SCSI_STATUS_TASK_SET_FULL; /* Task set full */ 1311 printf("%s: full tag=%x iiu=%d\n", __func__, io->tag, 1312 io->ocs->io_in_use); 1313 } 1314 1315 /* Log a message here indicating a busy or task set full state */ 1316 if (OCS_LOG_ENABLE_Q_FULL_BUSY_MSG(ocs)) { 1317 /* Log Task Set Full */ 1318 if (rsp.scsi_status == SCSI_STATUS_TASK_SET_FULL) { 1319 /* Task Set Full Message */ 1320 ocs_log_info(ocs, "OCS CAM TASK SET FULL. Tasks >= %d\n", 1321 ocs->io_high_watermark); 1322 } 1323 else if (rsp.scsi_status == SCSI_STATUS_BUSY) { 1324 /* Log Busy Message */ 1325 ocs_log_info(ocs, "OCS CAM SCSI BUSY\n"); 1326 } 1327 } 1328 1329 /* Send the response */ 1330 return 1331 ocs_scsi_send_resp(io, 0, &rsp, ocs_task_set_full_or_busy_cb, NULL); 1332 } 1333 1334 /** 1335 * @ingroup cam_io 1336 * @brief Process target IO completions 1337 * 1338 * @param io 1339 * @param scsi_status did the IO complete successfully 1340 * @param flags 1341 * @param arg application specific pointer provided in the call to ocs_target_io() 1342 * 1343 * @todo 1344 */ 1345 static int32_t ocs_scsi_target_io_cb(ocs_io_t *io, 1346 ocs_scsi_io_status_e scsi_status, 1347 uint32_t flags, void *arg) 1348 { 1349 union ccb *ccb = arg; 1350 struct ccb_scsiio *csio = &ccb->csio; 1351 struct ocs_softc *ocs = csio->ccb_h.ccb_ocs_ptr; 1352 uint32_t cam_dir = ccb->ccb_h.flags & CAM_DIR_MASK; 1353 uint32_t io_is_done = 1354 (ccb->ccb_h.flags & CAM_SEND_STATUS) == CAM_SEND_STATUS; 1355 1356 ccb->ccb_h.status &= ~CAM_SIM_QUEUED; 1357 1358 if (CAM_DIR_NONE != cam_dir) { 1359 bus_dmasync_op_t op; 1360 1361 if (CAM_DIR_IN == cam_dir) { 1362 op = BUS_DMASYNC_POSTREAD; 1363 } else { 1364 op = BUS_DMASYNC_POSTWRITE; 1365 } 1366 /* Synchronize the DMA memory with the CPU and free the mapping */ 1367 bus_dmamap_sync(ocs->buf_dmat, io->tgt_io.dmap, op); 1368 if (io->tgt_io.flags & OCS_CAM_IO_F_DMAPPED) { 1369 bus_dmamap_unload(ocs->buf_dmat, io->tgt_io.dmap); 1370 } 1371 } 1372 1373 if (io->tgt_io.sendresp) { 1374 io->tgt_io.sendresp = 0; 1375 ocs_scsi_cmd_resp_t resp = { 0 }; 1376 io->tgt_io.state = OCS_CAM_IO_RESP; 1377 resp.scsi_status = scsi_status; 1378 if (ccb->ccb_h.flags & CAM_SEND_SENSE) { 1379 resp.sense_data = (uint8_t *)&csio->sense_data; 1380 resp.sense_data_length = csio->sense_len; 1381 } 1382 resp.residual = io->exp_xfer_len - io->transferred; 1383 1384 return ocs_scsi_send_resp(io, 0, &resp, ocs_scsi_target_io_cb, ccb); 1385 } 1386 1387 switch (scsi_status) { 1388 case OCS_SCSI_STATUS_GOOD: 1389 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 1390 break; 1391 case OCS_SCSI_STATUS_ABORTED: 1392 ocs_set_ccb_status(ccb, CAM_REQ_ABORTED); 1393 break; 1394 default: 1395 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 1396 } 1397 1398 if (io_is_done) { 1399 if ((io->tgt_io.flags & OCS_CAM_IO_F_ABORT_NOTIFY) == 0) { 1400 ocs_target_io_free(io); 1401 } 1402 } else { 1403 io->tgt_io.state = OCS_CAM_IO_DATA_DONE; 1404 /*device_printf(ocs->dev, "%s: CTIO state=%d tag=%#x\n", 1405 __func__, io->tgt_io.state, io->tag);*/ 1406 } 1407 1408 xpt_done(ccb); 1409 1410 return 0; 1411 } 1412 1413 /** 1414 * @note 1. Since the CCB is assigned to the ocs_io_t on an XPT_CONT_TARGET_IO 1415 * action, if an initiator aborts a command prior to the SIM receiving 1416 * a CTIO, the IO's CCB will be NULL. 1417 */ 1418 static int32_t 1419 ocs_io_abort_cb(ocs_io_t *io, ocs_scsi_io_status_e scsi_status, uint32_t flags, void *arg) 1420 { 1421 struct ocs_softc *ocs = NULL; 1422 ocs_io_t *tmfio = arg; 1423 ocs_scsi_tmf_resp_e tmf_resp = OCS_SCSI_TMF_FUNCTION_COMPLETE; 1424 int32_t rc = 0; 1425 1426 ocs = io->ocs; 1427 1428 io->tgt_io.flags &= ~OCS_CAM_IO_F_ABORT_DEV; 1429 1430 /* A good status indicates the IO was aborted and will be completed in 1431 * the IO's completion handler. Handle the other cases here. */ 1432 switch (scsi_status) { 1433 case OCS_SCSI_STATUS_GOOD: 1434 break; 1435 case OCS_SCSI_STATUS_NO_IO: 1436 break; 1437 default: 1438 device_printf(ocs->dev, "%s: unhandled status %d\n", 1439 __func__, scsi_status); 1440 tmf_resp = OCS_SCSI_TMF_FUNCTION_REJECTED; 1441 rc = -1; 1442 } 1443 1444 ocs_scsi_send_tmf_resp(tmfio, tmf_resp, NULL, ocs_target_tmf_cb, NULL); 1445 1446 return rc; 1447 } 1448 1449 /** 1450 * @ingroup cam_io 1451 * @brief Process initiator IO completions 1452 * 1453 * @param io 1454 * @param scsi_status did the IO complete successfully 1455 * @param rsp pointer to response buffer 1456 * @param flags 1457 * @param arg application specific pointer provided in the call to ocs_target_io() 1458 * 1459 * @todo 1460 */ 1461 static int32_t ocs_scsi_initiator_io_cb(ocs_io_t *io, 1462 ocs_scsi_io_status_e scsi_status, 1463 ocs_scsi_cmd_resp_t *rsp, 1464 uint32_t flags, void *arg) 1465 { 1466 union ccb *ccb = arg; 1467 struct ccb_scsiio *csio = &ccb->csio; 1468 struct ocs_softc *ocs = csio->ccb_h.ccb_ocs_ptr; 1469 uint32_t cam_dir = ccb->ccb_h.flags & CAM_DIR_MASK; 1470 cam_status ccb_status= CAM_REQ_CMP_ERR; 1471 1472 if (CAM_DIR_NONE != cam_dir) { 1473 bus_dmasync_op_t op; 1474 1475 if (CAM_DIR_IN == cam_dir) { 1476 op = BUS_DMASYNC_POSTREAD; 1477 } else { 1478 op = BUS_DMASYNC_POSTWRITE; 1479 } 1480 /* Synchronize the DMA memory with the CPU and free the mapping */ 1481 bus_dmamap_sync(ocs->buf_dmat, io->tgt_io.dmap, op); 1482 if (io->tgt_io.flags & OCS_CAM_IO_F_DMAPPED) { 1483 bus_dmamap_unload(ocs->buf_dmat, io->tgt_io.dmap); 1484 } 1485 } 1486 1487 if (scsi_status == OCS_SCSI_STATUS_CHECK_RESPONSE) { 1488 csio->scsi_status = rsp->scsi_status; 1489 if (SCSI_STATUS_OK != rsp->scsi_status) 1490 ccb_status = CAM_SCSI_STATUS_ERROR; 1491 else 1492 ccb_status = CAM_REQ_CMP; 1493 1494 csio->resid = rsp->residual; 1495 1496 /* 1497 * If we've already got a SCSI error, prefer that because it 1498 * will have more detail. 1499 */ 1500 if ((rsp->residual < 0) && (ccb_status == CAM_REQ_CMP)) { 1501 ccb_status = CAM_DATA_RUN_ERR; 1502 } 1503 1504 if ((rsp->sense_data_length) && 1505 !(ccb->ccb_h.flags & (CAM_SENSE_PHYS | CAM_SENSE_PTR))) { 1506 uint32_t sense_len = 0; 1507 1508 ccb->ccb_h.status |= CAM_AUTOSNS_VALID; 1509 if (rsp->sense_data_length < csio->sense_len) { 1510 csio->sense_resid = 1511 csio->sense_len - rsp->sense_data_length; 1512 sense_len = rsp->sense_data_length; 1513 } else { 1514 csio->sense_resid = 0; 1515 sense_len = csio->sense_len; 1516 } 1517 ocs_memcpy(&csio->sense_data, rsp->sense_data, sense_len); 1518 } 1519 } else if (scsi_status != OCS_SCSI_STATUS_GOOD) { 1520 ccb_status = CAM_REQ_CMP_ERR; 1521 } else { 1522 ccb_status = CAM_REQ_CMP; 1523 } 1524 1525 ocs_set_ccb_status(ccb, ccb_status); 1526 1527 ocs_scsi_io_free(io); 1528 1529 csio->ccb_h.ccb_io_ptr = NULL; 1530 csio->ccb_h.ccb_ocs_ptr = NULL; 1531 1532 ccb->ccb_h.status &= ~CAM_SIM_QUEUED; 1533 1534 if ((ccb_status != CAM_REQ_CMP) && 1535 ((ccb->ccb_h.status & CAM_DEV_QFRZN) == 0)) { 1536 ccb->ccb_h.status |= CAM_DEV_QFRZN; 1537 xpt_freeze_devq(ccb->ccb_h.path, 1); 1538 } 1539 1540 xpt_done(ccb); 1541 1542 return 0; 1543 } 1544 1545 /** 1546 * @brief Load scatter-gather list entries into an IO 1547 * 1548 * This routine relies on the driver instance's software context pointer and 1549 * the IO object pointer having been already assigned to hooks in the CCB. 1550 * Although the routine does not return success/fail, callers can look at the 1551 * n_sge member to determine if the mapping failed (0 on failure). 1552 * 1553 * @param arg pointer to the CAM ccb for this IO 1554 * @param seg DMA address/length pairs 1555 * @param nseg number of DMA address/length pairs 1556 * @param error any errors while mapping the IO 1557 */ 1558 static void 1559 ocs_scsi_dmamap_load(void *arg, bus_dma_segment_t *seg, int nseg, int error) 1560 { 1561 ocs_dmamap_load_arg_t *sglarg = (ocs_dmamap_load_arg_t*) arg; 1562 1563 if (error) { 1564 printf("%s: seg=%p nseg=%d error=%d\n", 1565 __func__, seg, nseg, error); 1566 sglarg->rc = -1; 1567 } else { 1568 uint32_t i = 0; 1569 uint32_t c = 0; 1570 1571 if ((sglarg->sgl_count + nseg) > sglarg->sgl_max) { 1572 printf("%s: sgl_count=%d nseg=%d max=%d\n", __func__, 1573 sglarg->sgl_count, nseg, sglarg->sgl_max); 1574 sglarg->rc = -2; 1575 return; 1576 } 1577 1578 for (i = 0, c = sglarg->sgl_count; i < nseg; i++, c++) { 1579 sglarg->sgl[c].addr = seg[i].ds_addr; 1580 sglarg->sgl[c].len = seg[i].ds_len; 1581 } 1582 1583 sglarg->sgl_count = c; 1584 1585 sglarg->rc = 0; 1586 } 1587 } 1588 1589 /** 1590 * @brief Build a scatter-gather list from a CAM CCB 1591 * 1592 * @param ocs the driver instance's software context 1593 * @param ccb pointer to the CCB 1594 * @param io pointer to the previously allocated IO object 1595 * @param sgl pointer to SGL 1596 * @param sgl_max number of entries in sgl 1597 * 1598 * @return 0 on success, non-zero otherwise 1599 */ 1600 static int32_t 1601 ocs_build_scsi_sgl(struct ocs_softc *ocs, union ccb *ccb, ocs_io_t *io, 1602 ocs_scsi_sgl_t *sgl, uint32_t sgl_max) 1603 { 1604 ocs_dmamap_load_arg_t dmaarg; 1605 int32_t err = 0; 1606 1607 if (!ocs || !ccb || !io || !sgl) { 1608 printf("%s: bad param o=%p c=%p i=%p s=%p\n", __func__, 1609 ocs, ccb, io, sgl); 1610 return -1; 1611 } 1612 1613 io->tgt_io.flags &= ~OCS_CAM_IO_F_DMAPPED; 1614 1615 dmaarg.sgl = sgl; 1616 dmaarg.sgl_count = 0; 1617 dmaarg.sgl_max = sgl_max; 1618 dmaarg.rc = 0; 1619 1620 err = bus_dmamap_load_ccb(ocs->buf_dmat, io->tgt_io.dmap, ccb, 1621 ocs_scsi_dmamap_load, &dmaarg, 0); 1622 1623 if (err || dmaarg.rc) { 1624 device_printf( 1625 ocs->dev, "%s: bus_dmamap_load_ccb error (%d %d)\n", 1626 __func__, err, dmaarg.rc); 1627 return -1; 1628 } 1629 1630 io->tgt_io.flags |= OCS_CAM_IO_F_DMAPPED; 1631 return dmaarg.sgl_count; 1632 } 1633 1634 /** 1635 * @ingroup cam_io 1636 * @brief Send a target IO 1637 * 1638 * @param ocs the driver instance's software context 1639 * @param ccb pointer to the CCB 1640 * 1641 * @return 0 on success, non-zero otherwise 1642 */ 1643 static int32_t 1644 ocs_target_io(struct ocs_softc *ocs, union ccb *ccb) 1645 { 1646 struct ccb_scsiio *csio = &ccb->csio; 1647 ocs_io_t *io = NULL; 1648 uint32_t cam_dir = ccb->ccb_h.flags & CAM_DIR_MASK; 1649 bool sendstatus = ccb->ccb_h.flags & CAM_SEND_STATUS; 1650 uint32_t xferlen = csio->dxfer_len; 1651 int32_t rc = 0; 1652 1653 io = ocs_scsi_find_io(ocs, csio->tag_id); 1654 if (io == NULL) { 1655 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 1656 panic("bad tag value"); 1657 return 1; 1658 } 1659 1660 /* Received an ABORT TASK for this IO */ 1661 if (io->tgt_io.flags & OCS_CAM_IO_F_ABORT_RECV) { 1662 /*device_printf(ocs->dev, 1663 "%s: XPT_CONT_TARGET_IO state=%d tag=%#x xid=%#x flags=%#x\n", 1664 __func__, io->tgt_io.state, io->tag, io->init_task_tag, 1665 io->tgt_io.flags);*/ 1666 io->tgt_io.flags |= OCS_CAM_IO_F_ABORT_CAM; 1667 1668 if (ccb->ccb_h.flags & CAM_SEND_STATUS) { 1669 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 1670 ocs_target_io_free(io); 1671 return 1; 1672 } 1673 1674 ocs_set_ccb_status(ccb, CAM_REQ_ABORTED); 1675 1676 return 1; 1677 } 1678 1679 io->tgt_io.app = ccb; 1680 1681 ocs_set_ccb_status(ccb, CAM_REQ_INPROG); 1682 ccb->ccb_h.status |= CAM_SIM_QUEUED; 1683 1684 csio->ccb_h.ccb_ocs_ptr = ocs; 1685 csio->ccb_h.ccb_io_ptr = io; 1686 1687 if ((sendstatus && (xferlen == 0))) { 1688 ocs_scsi_cmd_resp_t resp = { 0 }; 1689 1690 ocs_assert(ccb->ccb_h.flags & CAM_SEND_STATUS, -1); 1691 1692 io->tgt_io.state = OCS_CAM_IO_RESP; 1693 1694 resp.scsi_status = csio->scsi_status; 1695 1696 if (ccb->ccb_h.flags & CAM_SEND_SENSE) { 1697 resp.sense_data = (uint8_t *)&csio->sense_data; 1698 resp.sense_data_length = csio->sense_len; 1699 } 1700 1701 resp.residual = io->exp_xfer_len - io->transferred; 1702 rc = ocs_scsi_send_resp(io, 0, &resp, ocs_scsi_target_io_cb, ccb); 1703 1704 } else if (xferlen != 0) { 1705 ocs_scsi_sgl_t *sgl; 1706 int32_t sgl_count = 0; 1707 1708 io->tgt_io.state = OCS_CAM_IO_DATA; 1709 1710 if (sendstatus) 1711 io->tgt_io.sendresp = 1; 1712 1713 sgl = io->sgl; 1714 1715 sgl_count = ocs_build_scsi_sgl(ocs, ccb, io, sgl, io->sgl_allocated); 1716 if (sgl_count > 0) { 1717 if (cam_dir == CAM_DIR_IN) { 1718 rc = ocs_scsi_send_rd_data(io, 0, NULL, sgl, 1719 sgl_count, csio->dxfer_len, 1720 ocs_scsi_target_io_cb, ccb); 1721 } else if (cam_dir == CAM_DIR_OUT) { 1722 rc = ocs_scsi_recv_wr_data(io, 0, NULL, sgl, 1723 sgl_count, csio->dxfer_len, 1724 ocs_scsi_target_io_cb, ccb); 1725 } else { 1726 device_printf(ocs->dev, "%s:" 1727 " unknown CAM direction %#x\n", 1728 __func__, cam_dir); 1729 ocs_set_ccb_status(ccb, CAM_REQ_INVALID); 1730 rc = 1; 1731 } 1732 } else { 1733 device_printf(ocs->dev, "%s: building SGL failed\n", 1734 __func__); 1735 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 1736 rc = 1; 1737 } 1738 } else { 1739 device_printf(ocs->dev, "%s: Wrong value xfer and sendstatus" 1740 " are 0 \n", __func__); 1741 ocs_set_ccb_status(ccb, CAM_REQ_INVALID); 1742 rc = 1; 1743 } 1744 1745 if (rc) { 1746 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 1747 ccb->ccb_h.status &= ~CAM_SIM_QUEUED; 1748 io->tgt_io.state = OCS_CAM_IO_DATA_DONE; 1749 device_printf(ocs->dev, "%s: CTIO state=%d tag=%#x\n", 1750 __func__, io->tgt_io.state, io->tag); 1751 if ((sendstatus && (xferlen == 0))) { 1752 ocs_target_io_free(io); 1753 } 1754 } 1755 1756 return rc; 1757 } 1758 1759 static int32_t 1760 ocs_target_tmf_cb(ocs_io_t *io, ocs_scsi_io_status_e scsi_status, uint32_t flags, 1761 void *arg) 1762 { 1763 1764 /*device_printf(io->ocs->dev, "%s: tag=%x io=%p s=%#x\n", 1765 __func__, io->tag, io, scsi_status);*/ 1766 ocs_scsi_io_complete(io); 1767 1768 return 0; 1769 } 1770 1771 /** 1772 * @ingroup cam_io 1773 * @brief Send an initiator IO 1774 * 1775 * @param ocs the driver instance's software context 1776 * @param ccb pointer to the CCB 1777 * 1778 * @return 0 on success, non-zero otherwise 1779 */ 1780 static int32_t 1781 ocs_initiator_io(struct ocs_softc *ocs, union ccb *ccb) 1782 { 1783 int32_t rc; 1784 struct ccb_scsiio *csio = &ccb->csio; 1785 struct ccb_hdr *ccb_h = &csio->ccb_h; 1786 ocs_node_t *node = NULL; 1787 ocs_io_t *io = NULL; 1788 ocs_scsi_sgl_t *sgl; 1789 int32_t flags, sgl_count; 1790 ocs_fcport *fcp; 1791 1792 fcp = FCPORT(ocs, cam_sim_bus(xpt_path_sim((ccb)->ccb_h.path))); 1793 1794 if (fcp->tgt[ccb_h->target_id].state == OCS_TGT_STATE_LOST) { 1795 device_printf(ocs->dev, "%s: device LOST %d\n", __func__, 1796 ccb_h->target_id); 1797 return CAM_REQUEUE_REQ; 1798 } 1799 1800 if (fcp->tgt[ccb_h->target_id].state == OCS_TGT_STATE_NONE) { 1801 device_printf(ocs->dev, "%s: device not ready %d\n", __func__, 1802 ccb_h->target_id); 1803 return CAM_SEL_TIMEOUT; 1804 } 1805 1806 node = ocs_node_get_instance(ocs, fcp->tgt[ccb_h->target_id].node_id); 1807 if (node == NULL) { 1808 device_printf(ocs->dev, "%s: no device %d\n", __func__, 1809 ccb_h->target_id); 1810 return CAM_SEL_TIMEOUT; 1811 } 1812 1813 if (!node->targ) { 1814 device_printf(ocs->dev, "%s: not target device %d\n", __func__, 1815 ccb_h->target_id); 1816 return CAM_SEL_TIMEOUT; 1817 } 1818 1819 io = ocs_scsi_io_alloc(node, OCS_SCSI_IO_ROLE_ORIGINATOR); 1820 if (io == NULL) { 1821 device_printf(ocs->dev, "%s: unable to alloc IO\n", __func__); 1822 return -1; 1823 } 1824 1825 /* eventhough this is INI, use target structure as ocs_build_scsi_sgl 1826 * only references the tgt_io part of an ocs_io_t */ 1827 io->tgt_io.app = ccb; 1828 1829 csio->ccb_h.ccb_ocs_ptr = ocs; 1830 csio->ccb_h.ccb_io_ptr = io; 1831 sgl = io->sgl; 1832 1833 sgl_count = ocs_build_scsi_sgl(ocs, ccb, io, sgl, io->sgl_allocated); 1834 if (sgl_count < 0) { 1835 ocs_scsi_io_free(io); 1836 device_printf(ocs->dev, "%s: building SGL failed\n", __func__); 1837 return -1; 1838 } 1839 1840 if (ccb->ccb_h.timeout == CAM_TIME_INFINITY) { 1841 io->timeout = 0; 1842 } else if (ccb->ccb_h.timeout == CAM_TIME_DEFAULT) { 1843 io->timeout = OCS_CAM_IO_TIMEOUT; 1844 } else { 1845 io->timeout = ccb->ccb_h.timeout; 1846 } 1847 1848 switch (csio->tag_action) { 1849 case MSG_HEAD_OF_Q_TAG: 1850 flags = OCS_SCSI_CMD_HEAD_OF_QUEUE; 1851 break; 1852 case MSG_ORDERED_Q_TAG: 1853 flags = OCS_SCSI_CMD_ORDERED; 1854 break; 1855 case MSG_ACA_TASK: 1856 flags = OCS_SCSI_CMD_ACA; 1857 break; 1858 case CAM_TAG_ACTION_NONE: 1859 case MSG_SIMPLE_Q_TAG: 1860 default: 1861 flags = OCS_SCSI_CMD_SIMPLE; 1862 break; 1863 } 1864 flags |= (csio->priority << OCS_SCSI_PRIORITY_SHIFT) & 1865 OCS_SCSI_PRIORITY_MASK; 1866 1867 switch (ccb->ccb_h.flags & CAM_DIR_MASK) { 1868 case CAM_DIR_NONE: 1869 rc = ocs_scsi_send_nodata_io(node, io, ccb_h->target_lun, 1870 ccb->ccb_h.flags & CAM_CDB_POINTER ? 1871 csio->cdb_io.cdb_ptr: csio->cdb_io.cdb_bytes, 1872 csio->cdb_len, 1873 ocs_scsi_initiator_io_cb, ccb, flags); 1874 break; 1875 case CAM_DIR_IN: 1876 rc = ocs_scsi_send_rd_io(node, io, ccb_h->target_lun, 1877 ccb->ccb_h.flags & CAM_CDB_POINTER ? 1878 csio->cdb_io.cdb_ptr: csio->cdb_io.cdb_bytes, 1879 csio->cdb_len, 1880 NULL, 1881 sgl, sgl_count, csio->dxfer_len, 1882 ocs_scsi_initiator_io_cb, ccb, flags); 1883 break; 1884 case CAM_DIR_OUT: 1885 rc = ocs_scsi_send_wr_io(node, io, ccb_h->target_lun, 1886 ccb->ccb_h.flags & CAM_CDB_POINTER ? 1887 csio->cdb_io.cdb_ptr: csio->cdb_io.cdb_bytes, 1888 csio->cdb_len, 1889 NULL, 1890 sgl, sgl_count, csio->dxfer_len, 1891 ocs_scsi_initiator_io_cb, ccb, flags); 1892 break; 1893 default: 1894 panic("%s invalid data direction %08x\n", __func__, 1895 ccb->ccb_h.flags); 1896 break; 1897 } 1898 1899 return rc; 1900 } 1901 1902 static uint32_t 1903 ocs_fcp_change_role(struct ocs_softc *ocs, ocs_fcport *fcp, uint32_t new_role) 1904 { 1905 1906 uint32_t rc = 0, was = 0, i = 0; 1907 ocs_vport_spec_t *vport = fcp->vport; 1908 1909 for (was = 0, i = 0; i < (ocs->num_vports + 1); i++) { 1910 if (FCPORT(ocs, i)->role != KNOB_ROLE_NONE) 1911 was++; 1912 } 1913 1914 // Physical port 1915 if ((was == 0) || (vport == NULL)) { 1916 fcp->role = new_role; 1917 if (vport == NULL) { 1918 ocs->enable_ini = (new_role & KNOB_ROLE_INITIATOR)? 1:0; 1919 ocs->enable_tgt = (new_role & KNOB_ROLE_TARGET)? 1:0; 1920 } else { 1921 vport->enable_ini = (new_role & KNOB_ROLE_INITIATOR)? 1:0; 1922 vport->enable_tgt = (new_role & KNOB_ROLE_TARGET)? 1:0; 1923 } 1924 1925 rc = ocs_xport_control(ocs->xport, OCS_XPORT_PORT_OFFLINE); 1926 if (rc) { 1927 ocs_log_debug(ocs, "port offline failed : %d\n", rc); 1928 } 1929 1930 rc = ocs_xport_control(ocs->xport, OCS_XPORT_PORT_ONLINE); 1931 if (rc) { 1932 ocs_log_debug(ocs, "port online failed : %d\n", rc); 1933 } 1934 1935 return 0; 1936 } 1937 1938 if ((fcp->role != KNOB_ROLE_NONE)){ 1939 fcp->role = new_role; 1940 vport->enable_ini = (new_role & KNOB_ROLE_INITIATOR)? 1:0; 1941 vport->enable_tgt = (new_role & KNOB_ROLE_TARGET)? 1:0; 1942 /* New Sport will be created in sport deleted cb */ 1943 return ocs_sport_vport_del(ocs, ocs->domain, vport->wwpn, vport->wwnn); 1944 } 1945 1946 fcp->role = new_role; 1947 1948 vport->enable_ini = (new_role & KNOB_ROLE_INITIATOR)? 1:0; 1949 vport->enable_tgt = (new_role & KNOB_ROLE_TARGET)? 1:0; 1950 1951 if (fcp->role != KNOB_ROLE_NONE) { 1952 return ocs_sport_vport_alloc(ocs->domain, vport); 1953 } 1954 1955 return (0); 1956 } 1957 1958 /** 1959 * @ingroup cam_api 1960 * @brief Process CAM actions 1961 * 1962 * The driver supplies this routine to the CAM during intialization and 1963 * is the main entry point for processing CAM Control Blocks (CCB) 1964 * 1965 * @param sim pointer to the SCSI Interface Module 1966 * @param ccb CAM control block 1967 * 1968 * @todo 1969 * - populate path inquiry data via info retrieved from SLI port 1970 */ 1971 static void 1972 ocs_action(struct cam_sim *sim, union ccb *ccb) 1973 { 1974 struct ocs_softc *ocs = (struct ocs_softc *)cam_sim_softc(sim); 1975 struct ccb_hdr *ccb_h = &ccb->ccb_h; 1976 1977 int32_t rc, bus; 1978 bus = cam_sim_bus(sim); 1979 1980 switch (ccb_h->func_code) { 1981 case XPT_SCSI_IO: 1982 1983 if ((ccb->ccb_h.flags & CAM_CDB_POINTER) != 0) { 1984 if ((ccb->ccb_h.flags & CAM_CDB_PHYS) != 0) { 1985 ccb->ccb_h.status = CAM_REQ_INVALID; 1986 xpt_done(ccb); 1987 break; 1988 } 1989 } 1990 1991 rc = ocs_initiator_io(ocs, ccb); 1992 if (0 == rc) { 1993 ocs_set_ccb_status(ccb, CAM_REQ_INPROG | CAM_SIM_QUEUED); 1994 break; 1995 } else { 1996 if (rc == CAM_REQUEUE_REQ) { 1997 cam_freeze_devq(ccb->ccb_h.path); 1998 cam_release_devq(ccb->ccb_h.path, RELSIM_RELEASE_AFTER_TIMEOUT, 0, 100, 0); 1999 ccb->ccb_h.status = CAM_REQUEUE_REQ; 2000 xpt_done(ccb); 2001 break; 2002 } 2003 2004 ccb->ccb_h.status &= ~CAM_SIM_QUEUED; 2005 if (rc > 0) { 2006 ocs_set_ccb_status(ccb, rc); 2007 } else { 2008 ocs_set_ccb_status(ccb, CAM_SEL_TIMEOUT); 2009 } 2010 } 2011 xpt_done(ccb); 2012 break; 2013 case XPT_PATH_INQ: 2014 { 2015 struct ccb_pathinq *cpi = &ccb->cpi; 2016 struct ccb_pathinq_settings_fc *fc = &cpi->xport_specific.fc; 2017 ocs_fcport *fcp = FCPORT(ocs, bus); 2018 2019 uint64_t wwn = 0; 2020 ocs_xport_stats_t value; 2021 2022 cpi->version_num = 1; 2023 2024 cpi->protocol = PROTO_SCSI; 2025 cpi->protocol_version = SCSI_REV_SPC; 2026 2027 if (ocs->ocs_xport == OCS_XPORT_FC) { 2028 cpi->transport = XPORT_FC; 2029 } else { 2030 cpi->transport = XPORT_UNKNOWN; 2031 } 2032 2033 cpi->transport_version = 0; 2034 2035 /* Set the transport parameters of the SIM */ 2036 ocs_xport_status(ocs->xport, OCS_XPORT_LINK_SPEED, &value); 2037 fc->bitrate = value.value * 1000; /* speed in Mbps */ 2038 2039 wwn = *((uint64_t *)ocs_scsi_get_property_ptr(ocs, OCS_SCSI_WWPN)); 2040 fc->wwpn = be64toh(wwn); 2041 2042 wwn = *((uint64_t *)ocs_scsi_get_property_ptr(ocs, OCS_SCSI_WWNN)); 2043 fc->wwnn = be64toh(wwn); 2044 2045 fc->port = fcp->fc_id; 2046 2047 if (ocs->config_tgt) { 2048 cpi->target_sprt = 2049 PIT_PROCESSOR | PIT_DISCONNECT | PIT_TERM_IO; 2050 } 2051 2052 cpi->hba_misc = PIM_NOBUSRESET | PIM_UNMAPPED; 2053 cpi->hba_misc |= PIM_EXTLUNS | PIM_NOSCAN; 2054 2055 cpi->hba_inquiry = PI_TAG_ABLE; 2056 cpi->max_target = OCS_MAX_TARGETS; 2057 cpi->initiator_id = ocs->max_remote_nodes + 1; 2058 2059 if (!ocs->enable_ini) { 2060 cpi->hba_misc |= PIM_NOINITIATOR; 2061 } 2062 2063 cpi->max_lun = OCS_MAX_LUN; 2064 cpi->bus_id = cam_sim_bus(sim); 2065 2066 /* Need to supply a base transfer speed prior to linking up 2067 * Worst case, this would be FC 1Gbps */ 2068 cpi->base_transfer_speed = 1 * 1000 * 1000; 2069 2070 /* Calculate the max IO supported 2071 * Worst case would be an OS page per SGL entry */ 2072 2073 cpi->maxio = PAGE_SIZE * 2074 (ocs_scsi_get_property(ocs, OCS_SCSI_MAX_SGL) - 1); 2075 2076 strncpy(cpi->sim_vid, "FreeBSD", SIM_IDLEN); 2077 strncpy(cpi->hba_vid, "Emulex", HBA_IDLEN); 2078 strncpy(cpi->dev_name, cam_sim_name(sim), DEV_IDLEN); 2079 cpi->unit_number = cam_sim_unit(sim); 2080 2081 cpi->ccb_h.status = CAM_REQ_CMP; 2082 xpt_done(ccb); 2083 break; 2084 } 2085 case XPT_GET_TRAN_SETTINGS: 2086 { 2087 struct ccb_trans_settings *cts = &ccb->cts; 2088 struct ccb_trans_settings_scsi *scsi = &cts->proto_specific.scsi; 2089 struct ccb_trans_settings_fc *fc = &cts->xport_specific.fc; 2090 ocs_xport_stats_t value; 2091 ocs_fcport *fcp = FCPORT(ocs, bus); 2092 ocs_fc_target_t *tgt = NULL; 2093 2094 if (ocs->ocs_xport != OCS_XPORT_FC) { 2095 ocs_set_ccb_status(ccb, CAM_REQ_INVALID); 2096 xpt_done(ccb); 2097 break; 2098 } 2099 2100 if (cts->ccb_h.target_id > OCS_MAX_TARGETS) { 2101 ocs_set_ccb_status(ccb, CAM_DEV_NOT_THERE); 2102 xpt_done(ccb); 2103 break; 2104 } 2105 2106 tgt = &fcp->tgt[cts->ccb_h.target_id]; 2107 if (tgt->state == OCS_TGT_STATE_NONE) { 2108 ocs_set_ccb_status(ccb, CAM_DEV_NOT_THERE); 2109 xpt_done(ccb); 2110 break; 2111 } 2112 2113 cts->protocol = PROTO_SCSI; 2114 cts->protocol_version = SCSI_REV_SPC2; 2115 cts->transport = XPORT_FC; 2116 cts->transport_version = 2; 2117 2118 scsi->valid = CTS_SCSI_VALID_TQ; 2119 scsi->flags = CTS_SCSI_FLAGS_TAG_ENB; 2120 2121 /* speed in Mbps */ 2122 ocs_xport_status(ocs->xport, OCS_XPORT_LINK_SPEED, &value); 2123 fc->bitrate = value.value * 100; 2124 2125 fc->wwpn = tgt->wwpn; 2126 2127 fc->wwnn = tgt->wwnn; 2128 2129 fc->port = tgt->port_id; 2130 2131 fc->valid = CTS_FC_VALID_SPEED | 2132 CTS_FC_VALID_WWPN | 2133 CTS_FC_VALID_WWNN | 2134 CTS_FC_VALID_PORT; 2135 2136 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2137 xpt_done(ccb); 2138 break; 2139 } 2140 case XPT_SET_TRAN_SETTINGS: 2141 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2142 xpt_done(ccb); 2143 break; 2144 2145 case XPT_CALC_GEOMETRY: 2146 cam_calc_geometry(&ccb->ccg, TRUE); 2147 xpt_done(ccb); 2148 break; 2149 2150 case XPT_GET_SIM_KNOB: 2151 { 2152 struct ccb_sim_knob *knob = &ccb->knob; 2153 uint64_t wwn = 0; 2154 ocs_fcport *fcp = FCPORT(ocs, bus); 2155 2156 if (ocs->ocs_xport != OCS_XPORT_FC) { 2157 ocs_set_ccb_status(ccb, CAM_REQ_INVALID); 2158 xpt_done(ccb); 2159 break; 2160 } 2161 2162 if (bus == 0) { 2163 wwn = *((uint64_t *)ocs_scsi_get_property_ptr(ocs, 2164 OCS_SCSI_WWNN)); 2165 knob->xport_specific.fc.wwnn = be64toh(wwn); 2166 2167 wwn = *((uint64_t *)ocs_scsi_get_property_ptr(ocs, 2168 OCS_SCSI_WWPN)); 2169 knob->xport_specific.fc.wwpn = be64toh(wwn); 2170 } else { 2171 knob->xport_specific.fc.wwnn = fcp->vport->wwnn; 2172 knob->xport_specific.fc.wwpn = fcp->vport->wwpn; 2173 } 2174 2175 knob->xport_specific.fc.role = fcp->role; 2176 knob->xport_specific.fc.valid = KNOB_VALID_ADDRESS | 2177 KNOB_VALID_ROLE; 2178 2179 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2180 xpt_done(ccb); 2181 break; 2182 } 2183 case XPT_SET_SIM_KNOB: 2184 { 2185 struct ccb_sim_knob *knob = &ccb->knob; 2186 bool role_changed = FALSE; 2187 ocs_fcport *fcp = FCPORT(ocs, bus); 2188 2189 if (ocs->ocs_xport != OCS_XPORT_FC) { 2190 ocs_set_ccb_status(ccb, CAM_REQ_INVALID); 2191 xpt_done(ccb); 2192 break; 2193 } 2194 2195 if (knob->xport_specific.fc.valid & KNOB_VALID_ADDRESS) { 2196 device_printf(ocs->dev, 2197 "%s: XPT_SET_SIM_KNOB wwnn=%llx wwpn=%llx\n", 2198 __func__, 2199 (unsigned long long)knob->xport_specific.fc.wwnn, 2200 (unsigned long long)knob->xport_specific.fc.wwpn); 2201 } 2202 2203 if (knob->xport_specific.fc.valid & KNOB_VALID_ROLE) { 2204 switch (knob->xport_specific.fc.role) { 2205 case KNOB_ROLE_NONE: 2206 if (fcp->role != KNOB_ROLE_NONE) { 2207 role_changed = TRUE; 2208 } 2209 break; 2210 case KNOB_ROLE_TARGET: 2211 if (fcp->role != KNOB_ROLE_TARGET) { 2212 role_changed = TRUE; 2213 } 2214 break; 2215 case KNOB_ROLE_INITIATOR: 2216 if (fcp->role != KNOB_ROLE_INITIATOR) { 2217 role_changed = TRUE; 2218 } 2219 break; 2220 case KNOB_ROLE_BOTH: 2221 if (fcp->role != KNOB_ROLE_BOTH) { 2222 role_changed = TRUE; 2223 } 2224 break; 2225 default: 2226 device_printf(ocs->dev, 2227 "%s: XPT_SET_SIM_KNOB unsupported role: %d\n", 2228 __func__, knob->xport_specific.fc.role); 2229 } 2230 2231 if (role_changed) { 2232 device_printf(ocs->dev, 2233 "BUS:%d XPT_SET_SIM_KNOB old_role: %d new_role: %d\n", 2234 bus, fcp->role, knob->xport_specific.fc.role); 2235 2236 ocs_fcp_change_role(ocs, fcp, knob->xport_specific.fc.role); 2237 } 2238 } 2239 2240 2241 2242 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2243 xpt_done(ccb); 2244 break; 2245 } 2246 case XPT_ABORT: 2247 { 2248 union ccb *accb = ccb->cab.abort_ccb; 2249 2250 switch (accb->ccb_h.func_code) { 2251 case XPT_ACCEPT_TARGET_IO: 2252 ocs_abort_atio(ocs, ccb); 2253 break; 2254 case XPT_IMMEDIATE_NOTIFY: 2255 ocs_abort_inot(ocs, ccb); 2256 break; 2257 case XPT_SCSI_IO: 2258 rc = ocs_abort_initiator_io(ocs, accb); 2259 if (rc) { 2260 ccb->ccb_h.status = CAM_UA_ABORT; 2261 } else { 2262 ccb->ccb_h.status = CAM_REQ_CMP; 2263 } 2264 2265 break; 2266 default: 2267 printf("abort of unknown func %#x\n", 2268 accb->ccb_h.func_code); 2269 ccb->ccb_h.status = CAM_REQ_INVALID; 2270 break; 2271 } 2272 break; 2273 } 2274 case XPT_RESET_BUS: 2275 if (ocs_xport_control(ocs->xport, OCS_XPORT_PORT_OFFLINE) == 0) { 2276 rc = ocs_xport_control(ocs->xport, OCS_XPORT_PORT_ONLINE); 2277 if (rc) { 2278 ocs_log_debug(ocs, "Failed to bring port online" 2279 " : %d\n", rc); 2280 } 2281 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2282 } else { 2283 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 2284 } 2285 xpt_done(ccb); 2286 break; 2287 case XPT_RESET_DEV: 2288 { 2289 ocs_node_t *node = NULL; 2290 ocs_io_t *io = NULL; 2291 int32_t rc = 0; 2292 ocs_fcport *fcp = FCPORT(ocs, bus); 2293 2294 node = ocs_node_get_instance(ocs, fcp->tgt[ccb_h->target_id].node_id); 2295 if (node == NULL) { 2296 device_printf(ocs->dev, "%s: no device %d\n", 2297 __func__, ccb_h->target_id); 2298 ocs_set_ccb_status(ccb, CAM_DEV_NOT_THERE); 2299 xpt_done(ccb); 2300 break; 2301 } 2302 2303 io = ocs_scsi_io_alloc(node, OCS_SCSI_IO_ROLE_ORIGINATOR); 2304 if (io == NULL) { 2305 device_printf(ocs->dev, "%s: unable to alloc IO\n", 2306 __func__); 2307 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 2308 xpt_done(ccb); 2309 break; 2310 } 2311 2312 rc = ocs_scsi_send_tmf(node, io, NULL, ccb_h->target_lun, 2313 OCS_SCSI_TMF_LOGICAL_UNIT_RESET, 2314 NULL, 0, 0, /* sgl, sgl_count, length */ 2315 ocs_initiator_tmf_cb, NULL/*arg*/); 2316 2317 if (rc) { 2318 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 2319 } else { 2320 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2321 } 2322 2323 if (node->fcp2device) { 2324 ocs_reset_crn(node, ccb_h->target_lun); 2325 } 2326 2327 xpt_done(ccb); 2328 break; 2329 } 2330 case XPT_EN_LUN: /* target support */ 2331 { 2332 ocs_tgt_resource_t *trsrc = NULL; 2333 uint32_t status = 0; 2334 ocs_fcport *fcp = FCPORT(ocs, bus); 2335 2336 device_printf(ocs->dev, "XPT_EN_LUN %sable %d:%d\n", 2337 ccb->cel.enable ? "en" : "dis", 2338 ccb->ccb_h.target_id, 2339 (unsigned int)ccb->ccb_h.target_lun); 2340 2341 trsrc = ocs_tgt_resource_get(fcp, &ccb->ccb_h, &status); 2342 if (trsrc) { 2343 trsrc->enabled = ccb->cel.enable; 2344 2345 /* Abort all ATIO/INOT on LUN disable */ 2346 if (trsrc->enabled == FALSE) { 2347 ocs_tgt_resource_abort(ocs, trsrc); 2348 } else { 2349 STAILQ_INIT(&trsrc->atio); 2350 STAILQ_INIT(&trsrc->inot); 2351 } 2352 status = CAM_REQ_CMP; 2353 } 2354 2355 ocs_set_ccb_status(ccb, status); 2356 xpt_done(ccb); 2357 break; 2358 } 2359 /* 2360 * The flow of target IOs in CAM is: 2361 * - CAM supplies a number of CCBs to the driver used for received 2362 * commands. 2363 * - when the driver receives a command, it copies the relevant 2364 * information to the CCB and returns it to the CAM using xpt_done() 2365 * - after the target server processes the request, it creates 2366 * a new CCB containing information on how to continue the IO and 2367 * passes that to the driver 2368 * - the driver processes the "continue IO" (a.k.a CTIO) CCB 2369 * - once the IO completes, the driver returns the CTIO to the CAM 2370 * using xpt_done() 2371 */ 2372 case XPT_ACCEPT_TARGET_IO: /* used to inform upper layer of 2373 received CDB (a.k.a. ATIO) */ 2374 case XPT_IMMEDIATE_NOTIFY: /* used to inform upper layer of other 2375 event (a.k.a. INOT) */ 2376 { 2377 ocs_tgt_resource_t *trsrc = NULL; 2378 uint32_t status = 0; 2379 ocs_fcport *fcp = FCPORT(ocs, bus); 2380 2381 /*printf("XPT_%s %p\n", ccb_h->func_code == XPT_ACCEPT_TARGET_IO ? 2382 "ACCEPT_TARGET_IO" : "IMMEDIATE_NOTIFY", ccb);*/ 2383 trsrc = ocs_tgt_resource_get(fcp, &ccb->ccb_h, &status); 2384 if (trsrc == NULL) { 2385 ocs_set_ccb_status(ccb, CAM_DEV_NOT_THERE); 2386 xpt_done(ccb); 2387 break; 2388 } 2389 2390 if (XPT_ACCEPT_TARGET_IO == ccb->ccb_h.func_code) { 2391 struct ccb_accept_tio *atio = NULL; 2392 2393 atio = (struct ccb_accept_tio *)ccb; 2394 atio->init_id = 0x0badbeef; 2395 atio->tag_id = 0xdeadc0de; 2396 2397 STAILQ_INSERT_TAIL(&trsrc->atio, &ccb->ccb_h, 2398 sim_links.stqe); 2399 } else { 2400 STAILQ_INSERT_TAIL(&trsrc->inot, &ccb->ccb_h, 2401 sim_links.stqe); 2402 } 2403 ccb->ccb_h.ccb_io_ptr = NULL; 2404 ccb->ccb_h.ccb_ocs_ptr = ocs; 2405 ocs_set_ccb_status(ccb, CAM_REQ_INPROG); 2406 /* 2407 * These actions give resources to the target driver. 2408 * If we didn't return here, this function would call 2409 * xpt_done(), signaling to the upper layers that an 2410 * IO or other event had arrived. 2411 */ 2412 break; 2413 } 2414 case XPT_NOTIFY_ACKNOWLEDGE: 2415 { 2416 ocs_io_t *io = NULL; 2417 ocs_io_t *abortio = NULL; 2418 2419 /* Get the IO reference for this tag */ 2420 io = ocs_scsi_find_io(ocs, ccb->cna2.tag_id); 2421 if (io == NULL) { 2422 device_printf(ocs->dev, 2423 "%s: XPT_NOTIFY_ACKNOWLEDGE no IO with tag %#x\n", 2424 __func__, ccb->cna2.tag_id); 2425 ocs_set_ccb_status(ccb, CAM_REQ_CMP_ERR); 2426 xpt_done(ccb); 2427 break; 2428 } 2429 2430 abortio = io->tgt_io.app; 2431 if (abortio) { 2432 abortio->tgt_io.flags &= ~OCS_CAM_IO_F_ABORT_NOTIFY; 2433 device_printf(ocs->dev, 2434 "%s: XPT_NOTIFY_ACK state=%d tag=%#x xid=%#x" 2435 " flags=%#x\n", __func__, abortio->tgt_io.state, 2436 abortio->tag, abortio->init_task_tag, 2437 abortio->tgt_io.flags); 2438 /* TMF response was sent in abort callback */ 2439 } else { 2440 ocs_scsi_send_tmf_resp(io, 2441 OCS_SCSI_TMF_FUNCTION_COMPLETE, 2442 NULL, ocs_target_tmf_cb, NULL); 2443 } 2444 2445 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2446 xpt_done(ccb); 2447 break; 2448 } 2449 case XPT_CONT_TARGET_IO: /* continue target IO, sending data/response (a.k.a. CTIO) */ 2450 if (ocs_target_io(ocs, ccb)) { 2451 device_printf(ocs->dev, 2452 "XPT_CONT_TARGET_IO failed flags=%x tag=%#x\n", 2453 ccb->ccb_h.flags, ccb->csio.tag_id); 2454 xpt_done(ccb); 2455 } 2456 break; 2457 default: 2458 device_printf(ocs->dev, "unhandled func_code = %#x\n", 2459 ccb_h->func_code); 2460 ccb_h->status = CAM_REQ_INVALID; 2461 xpt_done(ccb); 2462 break; 2463 } 2464 } 2465 2466 /** 2467 * @ingroup cam_api 2468 * @brief Process events 2469 * 2470 * @param sim pointer to the SCSI Interface Module 2471 * 2472 */ 2473 static void 2474 ocs_poll(struct cam_sim *sim) 2475 { 2476 printf("%s\n", __func__); 2477 } 2478 2479 static int32_t 2480 ocs_initiator_tmf_cb(ocs_io_t *io, ocs_scsi_io_status_e scsi_status, 2481 ocs_scsi_cmd_resp_t *rsp, uint32_t flags, void *arg) 2482 { 2483 int32_t rc = 0; 2484 2485 switch (scsi_status) { 2486 case OCS_SCSI_STATUS_GOOD: 2487 case OCS_SCSI_STATUS_NO_IO: 2488 break; 2489 case OCS_SCSI_STATUS_CHECK_RESPONSE: 2490 if (rsp->response_data_length == 0) { 2491 ocs_log_test(io->ocs, "check response without data?!?\n"); 2492 rc = -1; 2493 break; 2494 } 2495 2496 if (rsp->response_data[3] != 0) { 2497 ocs_log_test(io->ocs, "TMF status %08x\n", 2498 be32toh(*((uint32_t *)rsp->response_data))); 2499 rc = -1; 2500 break; 2501 } 2502 break; 2503 default: 2504 ocs_log_test(io->ocs, "status=%#x\n", scsi_status); 2505 rc = -1; 2506 } 2507 2508 ocs_scsi_io_free(io); 2509 2510 return rc; 2511 } 2512 2513 /** 2514 * @brief lookup target resource structure 2515 * 2516 * Arbitrarily support 2517 * - wildcard target ID + LU 2518 * - 0 target ID + non-wildcard LU 2519 * 2520 * @param ocs the driver instance's software context 2521 * @param ccb_h pointer to the CCB header 2522 * @param status returned status value 2523 * 2524 * @return pointer to the target resource, NULL if none available (e.g. if LU 2525 * is not enabled) 2526 */ 2527 static ocs_tgt_resource_t *ocs_tgt_resource_get(ocs_fcport *fcp, 2528 struct ccb_hdr *ccb_h, uint32_t *status) 2529 { 2530 target_id_t tid = ccb_h->target_id; 2531 lun_id_t lun = ccb_h->target_lun; 2532 2533 if (CAM_TARGET_WILDCARD == tid) { 2534 if (CAM_LUN_WILDCARD != lun) { 2535 *status = CAM_LUN_INVALID; 2536 return NULL; 2537 } 2538 return &fcp->targ_rsrc_wildcard; 2539 } else { 2540 if (lun < OCS_MAX_LUN) { 2541 return &fcp->targ_rsrc[lun]; 2542 } else { 2543 *status = CAM_LUN_INVALID; 2544 return NULL; 2545 } 2546 } 2547 2548 } 2549 2550 static int32_t 2551 ocs_tgt_resource_abort(struct ocs_softc *ocs, ocs_tgt_resource_t *trsrc) 2552 { 2553 union ccb *ccb = NULL; 2554 2555 do { 2556 ccb = (union ccb *)STAILQ_FIRST(&trsrc->atio); 2557 if (ccb) { 2558 STAILQ_REMOVE_HEAD(&trsrc->atio, sim_links.stqe); 2559 ccb->ccb_h.status = CAM_REQ_ABORTED; 2560 xpt_done(ccb); 2561 } 2562 } while (ccb); 2563 2564 do { 2565 ccb = (union ccb *)STAILQ_FIRST(&trsrc->inot); 2566 if (ccb) { 2567 STAILQ_REMOVE_HEAD(&trsrc->inot, sim_links.stqe); 2568 ccb->ccb_h.status = CAM_REQ_ABORTED; 2569 xpt_done(ccb); 2570 } 2571 } while (ccb); 2572 2573 return 0; 2574 } 2575 2576 static void 2577 ocs_abort_atio(struct ocs_softc *ocs, union ccb *ccb) 2578 { 2579 2580 ocs_io_t *aio = NULL; 2581 ocs_tgt_resource_t *trsrc = NULL; 2582 uint32_t status = CAM_REQ_INVALID; 2583 struct ccb_hdr *cur = NULL; 2584 union ccb *accb = ccb->cab.abort_ccb; 2585 2586 int bus = cam_sim_bus(xpt_path_sim((ccb)->ccb_h.path)); 2587 ocs_fcport *fcp = FCPORT(ocs, bus); 2588 2589 trsrc = ocs_tgt_resource_get(fcp, &accb->ccb_h, &status); 2590 if (trsrc != NULL) { 2591 STAILQ_FOREACH(cur, &trsrc->atio, sim_links.stqe) { 2592 if (cur != &accb->ccb_h) 2593 continue; 2594 2595 STAILQ_REMOVE(&trsrc->atio, cur, ccb_hdr, 2596 sim_links.stqe); 2597 accb->ccb_h.status = CAM_REQ_ABORTED; 2598 xpt_done(accb); 2599 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2600 return; 2601 } 2602 } 2603 2604 /* if the ATIO has a valid IO pointer, CAM is telling 2605 * the driver that the ATIO (which represents the entire 2606 * exchange) has been aborted. */ 2607 2608 aio = accb->ccb_h.ccb_io_ptr; 2609 if (aio == NULL) { 2610 ccb->ccb_h.status = CAM_UA_ABORT; 2611 return; 2612 } 2613 2614 device_printf(ocs->dev, 2615 "%s: XPT_ABORT ATIO state=%d tag=%#x" 2616 " xid=%#x flags=%#x\n", __func__, 2617 aio->tgt_io.state, aio->tag, 2618 aio->init_task_tag, aio->tgt_io.flags); 2619 /* Expectations are: 2620 * - abort task was received 2621 * - already aborted IO in the DEVICE 2622 * - already received NOTIFY ACKNOWLEDGE */ 2623 2624 if ((aio->tgt_io.flags & OCS_CAM_IO_F_ABORT_RECV) == 0) { 2625 device_printf(ocs->dev, "%s: abort not received or io completed \n", __func__); 2626 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2627 return; 2628 } 2629 2630 aio->tgt_io.flags |= OCS_CAM_IO_F_ABORT_CAM; 2631 ocs_target_io_free(aio); 2632 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2633 2634 return; 2635 } 2636 2637 static void 2638 ocs_abort_inot(struct ocs_softc *ocs, union ccb *ccb) 2639 { 2640 ocs_tgt_resource_t *trsrc = NULL; 2641 uint32_t status = CAM_REQ_INVALID; 2642 struct ccb_hdr *cur = NULL; 2643 union ccb *accb = ccb->cab.abort_ccb; 2644 2645 int bus = cam_sim_bus(xpt_path_sim((ccb)->ccb_h.path)); 2646 ocs_fcport *fcp = FCPORT(ocs, bus); 2647 2648 trsrc = ocs_tgt_resource_get(fcp, &accb->ccb_h, &status); 2649 if (trsrc) { 2650 STAILQ_FOREACH(cur, &trsrc->inot, sim_links.stqe) { 2651 if (cur != &accb->ccb_h) 2652 continue; 2653 2654 STAILQ_REMOVE(&trsrc->inot, cur, ccb_hdr, 2655 sim_links.stqe); 2656 accb->ccb_h.status = CAM_REQ_ABORTED; 2657 xpt_done(accb); 2658 ocs_set_ccb_status(ccb, CAM_REQ_CMP); 2659 return; 2660 } 2661 } 2662 2663 ocs_set_ccb_status(ccb, CAM_UA_ABORT); 2664 return; 2665 } 2666 2667 static uint32_t 2668 ocs_abort_initiator_io(struct ocs_softc *ocs, union ccb *accb) 2669 { 2670 2671 ocs_node_t *node = NULL; 2672 ocs_io_t *io = NULL; 2673 int32_t rc = 0; 2674 struct ccb_scsiio *csio = &accb->csio; 2675 2676 ocs_fcport *fcp = FCPORT(ocs, cam_sim_bus(xpt_path_sim((accb)->ccb_h.path))); 2677 node = ocs_node_get_instance(ocs, fcp->tgt[accb->ccb_h.target_id].node_id); 2678 if (node == NULL) { 2679 device_printf(ocs->dev, "%s: no device %d\n", 2680 __func__, accb->ccb_h.target_id); 2681 ocs_set_ccb_status(accb, CAM_DEV_NOT_THERE); 2682 xpt_done(accb); 2683 return (-1); 2684 } 2685 2686 io = ocs_scsi_io_alloc(node, OCS_SCSI_IO_ROLE_ORIGINATOR); 2687 if (io == NULL) { 2688 device_printf(ocs->dev, 2689 "%s: unable to alloc IO\n", __func__); 2690 ocs_set_ccb_status(accb, CAM_REQ_CMP_ERR); 2691 xpt_done(accb); 2692 return (-1); 2693 } 2694 2695 rc = ocs_scsi_send_tmf(node, io, 2696 (ocs_io_t *)csio->ccb_h.ccb_io_ptr, 2697 accb->ccb_h.target_lun, 2698 OCS_SCSI_TMF_ABORT_TASK, 2699 NULL, 0, 0, 2700 ocs_initiator_tmf_cb, NULL/*arg*/); 2701 2702 return rc; 2703 } 2704 2705 void 2706 ocs_scsi_ini_ddump(ocs_textbuf_t *textbuf, ocs_scsi_ddump_type_e type, void *obj) 2707 { 2708 switch(type) { 2709 case OCS_SCSI_DDUMP_DEVICE: { 2710 //ocs_t *ocs = obj; 2711 break; 2712 } 2713 case OCS_SCSI_DDUMP_DOMAIN: { 2714 //ocs_domain_t *domain = obj; 2715 break; 2716 } 2717 case OCS_SCSI_DDUMP_SPORT: { 2718 //ocs_sport_t *sport = obj; 2719 break; 2720 } 2721 case OCS_SCSI_DDUMP_NODE: { 2722 //ocs_node_t *node = obj; 2723 break; 2724 } 2725 case OCS_SCSI_DDUMP_IO: { 2726 //ocs_io_t *io = obj; 2727 break; 2728 } 2729 default: { 2730 break; 2731 } 2732 } 2733 } 2734 2735 void 2736 ocs_scsi_tgt_ddump(ocs_textbuf_t *textbuf, ocs_scsi_ddump_type_e type, void *obj) 2737 { 2738 switch(type) { 2739 case OCS_SCSI_DDUMP_DEVICE: { 2740 //ocs_t *ocs = obj; 2741 break; 2742 } 2743 case OCS_SCSI_DDUMP_DOMAIN: { 2744 //ocs_domain_t *domain = obj; 2745 break; 2746 } 2747 case OCS_SCSI_DDUMP_SPORT: { 2748 //ocs_sport_t *sport = obj; 2749 break; 2750 } 2751 case OCS_SCSI_DDUMP_NODE: { 2752 //ocs_node_t *node = obj; 2753 break; 2754 } 2755 case OCS_SCSI_DDUMP_IO: { 2756 ocs_io_t *io = obj; 2757 char *state_str = NULL; 2758 2759 switch (io->tgt_io.state) { 2760 case OCS_CAM_IO_FREE: 2761 state_str = "FREE"; 2762 break; 2763 case OCS_CAM_IO_COMMAND: 2764 state_str = "COMMAND"; 2765 break; 2766 case OCS_CAM_IO_DATA: 2767 state_str = "DATA"; 2768 break; 2769 case OCS_CAM_IO_DATA_DONE: 2770 state_str = "DATA_DONE"; 2771 break; 2772 case OCS_CAM_IO_RESP: 2773 state_str = "RESP"; 2774 break; 2775 default: 2776 state_str = "xxx BAD xxx"; 2777 } 2778 ocs_ddump_value(textbuf, "cam_st", "%s", state_str); 2779 if (io->tgt_io.app) { 2780 ocs_ddump_value(textbuf, "cam_flags", "%#x", 2781 ((union ccb *)(io->tgt_io.app))->ccb_h.flags); 2782 ocs_ddump_value(textbuf, "cam_status", "%#x", 2783 ((union ccb *)(io->tgt_io.app))->ccb_h.status); 2784 } 2785 2786 break; 2787 } 2788 default: { 2789 break; 2790 } 2791 } 2792 } 2793 2794 int32_t ocs_scsi_get_block_vaddr(ocs_io_t *io, uint64_t blocknumber, 2795 ocs_scsi_vaddr_len_t addrlen[], 2796 uint32_t max_addrlen, void **dif_vaddr) 2797 { 2798 return -1; 2799 } 2800 2801 uint32_t 2802 ocs_get_crn(ocs_node_t *node, uint8_t *crn, uint64_t lun) 2803 { 2804 uint32_t idx; 2805 struct ocs_lun_crn *lcrn = NULL; 2806 idx = lun % OCS_MAX_LUN; 2807 2808 lcrn = node->ini_node.lun_crn[idx]; 2809 2810 if (lcrn == NULL) { 2811 lcrn = ocs_malloc(node->ocs, sizeof(struct ocs_lun_crn), 2812 M_ZERO|M_NOWAIT); 2813 if (lcrn == NULL) { 2814 return (1); 2815 } 2816 2817 lcrn->lun = lun; 2818 node->ini_node.lun_crn[idx] = lcrn; 2819 } 2820 2821 if (lcrn->lun != lun) { 2822 return (1); 2823 } 2824 2825 if (lcrn->crnseed == 0) 2826 lcrn->crnseed = 1; 2827 2828 *crn = lcrn->crnseed++; 2829 return (0); 2830 } 2831 2832 void 2833 ocs_del_crn(ocs_node_t *node) 2834 { 2835 uint32_t i; 2836 struct ocs_lun_crn *lcrn = NULL; 2837 2838 for(i = 0; i < OCS_MAX_LUN; i++) { 2839 lcrn = node->ini_node.lun_crn[i]; 2840 if (lcrn) { 2841 ocs_free(node->ocs, lcrn, sizeof(*lcrn)); 2842 } 2843 } 2844 2845 return; 2846 } 2847 2848 void 2849 ocs_reset_crn(ocs_node_t *node, uint64_t lun) 2850 { 2851 uint32_t idx; 2852 struct ocs_lun_crn *lcrn = NULL; 2853 idx = lun % OCS_MAX_LUN; 2854 2855 lcrn = node->ini_node.lun_crn[idx]; 2856 if (lcrn) 2857 lcrn->crnseed = 0; 2858 2859 return; 2860 } 2861