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