1/******************************************************************************* 2 * 3 * This file contains the Linux/SCSI LLD virtual SCSI initiator driver 4 * for emulated SAS initiator ports 5 * 6 * © Copyright 2011-2013 Datera, Inc. 7 * 8 * Licensed to the Linux Foundation under the General Public License (GPL) version 2. 9 * 10 * Author: Nicholas A. Bellinger <nab@risingtidesystems.com> 11 * 12 * This program is free software; you can redistribute it and/or modify 13 * it under the terms of the GNU General Public License as published by 14 * the Free Software Foundation; either version 2 of the License, or 15 * (at your option) any later version. 16 * 17 * This program is distributed in the hope that it will be useful, 18 * but WITHOUT ANY WARRANTY; without even the implied warranty of 19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 20 * GNU General Public License for more details. 21 ****************************************************************************/ 22 23#include <linux/module.h> 24#include <linux/moduleparam.h> 25#include <linux/init.h> 26#include <linux/slab.h> 27#include <linux/types.h> 28#include <linux/configfs.h> 29#include <scsi/scsi.h> 30#include <scsi/scsi_tcq.h> 31#include <scsi/scsi_host.h> 32#include <scsi/scsi_device.h> 33#include <scsi/scsi_cmnd.h> 34 35#include <target/target_core_base.h> 36#include <target/target_core_fabric.h> 37#include <target/target_core_fabric_configfs.h> 38#include <target/target_core_configfs.h> 39 40#include "tcm_loop.h" 41 42#define to_tcm_loop_hba(hba) container_of(hba, struct tcm_loop_hba, dev) 43 44/* Local pointer to allocated TCM configfs fabric module */ 45static struct target_fabric_configfs *tcm_loop_fabric_configfs; 46 47static struct workqueue_struct *tcm_loop_workqueue; 48static struct kmem_cache *tcm_loop_cmd_cache; 49 50static int tcm_loop_hba_no_cnt; 51 52static int tcm_loop_queue_status(struct se_cmd *se_cmd); 53 54/* 55 * Called from struct target_core_fabric_ops->check_stop_free() 56 */ 57static int tcm_loop_check_stop_free(struct se_cmd *se_cmd) 58{ 59 /* 60 * Do not release struct se_cmd's containing a valid TMR 61 * pointer. These will be released directly in tcm_loop_device_reset() 62 * with transport_generic_free_cmd(). 63 */ 64 if (se_cmd->se_cmd_flags & SCF_SCSI_TMR_CDB) 65 return 0; 66 /* 67 * Release the struct se_cmd, which will make a callback to release 68 * struct tcm_loop_cmd * in tcm_loop_deallocate_core_cmd() 69 */ 70 transport_generic_free_cmd(se_cmd, 0); 71 return 1; 72} 73 74static void tcm_loop_release_cmd(struct se_cmd *se_cmd) 75{ 76 struct tcm_loop_cmd *tl_cmd = container_of(se_cmd, 77 struct tcm_loop_cmd, tl_se_cmd); 78 79 kmem_cache_free(tcm_loop_cmd_cache, tl_cmd); 80} 81 82static int tcm_loop_show_info(struct seq_file *m, struct Scsi_Host *host) 83{ 84 seq_printf(m, "tcm_loop_proc_info()\n"); 85 return 0; 86} 87 88static int tcm_loop_driver_probe(struct device *); 89static int tcm_loop_driver_remove(struct device *); 90 91static int pseudo_lld_bus_match(struct device *dev, 92 struct device_driver *dev_driver) 93{ 94 return 1; 95} 96 97static struct bus_type tcm_loop_lld_bus = { 98 .name = "tcm_loop_bus", 99 .match = pseudo_lld_bus_match, 100 .probe = tcm_loop_driver_probe, 101 .remove = tcm_loop_driver_remove, 102}; 103 104static struct device_driver tcm_loop_driverfs = { 105 .name = "tcm_loop", 106 .bus = &tcm_loop_lld_bus, 107}; 108/* 109 * Used with root_device_register() in tcm_loop_alloc_core_bus() below 110 */ 111struct device *tcm_loop_primary; 112 113/* 114 * Copied from drivers/scsi/libfc/fc_fcp.c:fc_change_queue_depth() and 115 * drivers/scsi/libiscsi.c:iscsi_change_queue_depth() 116 */ 117static int tcm_loop_change_queue_depth( 118 struct scsi_device *sdev, 119 int depth, 120 int reason) 121{ 122 switch (reason) { 123 case SCSI_QDEPTH_DEFAULT: 124 scsi_adjust_queue_depth(sdev, scsi_get_tag_type(sdev), depth); 125 break; 126 case SCSI_QDEPTH_QFULL: 127 scsi_track_queue_full(sdev, depth); 128 break; 129 case SCSI_QDEPTH_RAMP_UP: 130 scsi_adjust_queue_depth(sdev, scsi_get_tag_type(sdev), depth); 131 break; 132 default: 133 return -EOPNOTSUPP; 134 } 135 return sdev->queue_depth; 136} 137 138static int tcm_loop_change_queue_type(struct scsi_device *sdev, int tag) 139{ 140 if (sdev->tagged_supported) { 141 scsi_set_tag_type(sdev, tag); 142 143 if (tag) 144 scsi_activate_tcq(sdev, sdev->queue_depth); 145 else 146 scsi_deactivate_tcq(sdev, sdev->queue_depth); 147 } else 148 tag = 0; 149 150 return tag; 151} 152 153/* 154 * Locate the SAM Task Attr from struct scsi_cmnd * 155 */ 156static int tcm_loop_sam_attr(struct scsi_cmnd *sc, int tag) 157{ 158 if (sc->device->tagged_supported && 159 sc->device->ordered_tags && tag >= 0) 160 return MSG_ORDERED_TAG; 161 162 return MSG_SIMPLE_TAG; 163} 164 165static void tcm_loop_submission_work(struct work_struct *work) 166{ 167 struct tcm_loop_cmd *tl_cmd = 168 container_of(work, struct tcm_loop_cmd, work); 169 struct se_cmd *se_cmd = &tl_cmd->tl_se_cmd; 170 struct scsi_cmnd *sc = tl_cmd->sc; 171 struct tcm_loop_nexus *tl_nexus; 172 struct tcm_loop_hba *tl_hba; 173 struct tcm_loop_tpg *tl_tpg; 174 struct scatterlist *sgl_bidi = NULL; 175 u32 sgl_bidi_count = 0, transfer_length; 176 int rc; 177 178 tl_hba = *(struct tcm_loop_hba **)shost_priv(sc->device->host); 179 tl_tpg = &tl_hba->tl_hba_tpgs[sc->device->id]; 180 181 /* 182 * Ensure that this tl_tpg reference from the incoming sc->device->id 183 * has already been configured via tcm_loop_make_naa_tpg(). 184 */ 185 if (!tl_tpg->tl_hba) { 186 set_host_byte(sc, DID_NO_CONNECT); 187 goto out_done; 188 } 189 if (tl_tpg->tl_transport_status == TCM_TRANSPORT_OFFLINE) { 190 set_host_byte(sc, DID_TRANSPORT_DISRUPTED); 191 goto out_done; 192 } 193 tl_nexus = tl_hba->tl_nexus; 194 if (!tl_nexus) { 195 scmd_printk(KERN_ERR, sc, "TCM_Loop I_T Nexus" 196 " does not exist\n"); 197 set_host_byte(sc, DID_ERROR); 198 goto out_done; 199 } 200 if (scsi_bidi_cmnd(sc)) { 201 struct scsi_data_buffer *sdb = scsi_in(sc); 202 203 sgl_bidi = sdb->table.sgl; 204 sgl_bidi_count = sdb->table.nents; 205 se_cmd->se_cmd_flags |= SCF_BIDI; 206 207 } 208 209 transfer_length = scsi_transfer_length(sc); 210 if (!scsi_prot_sg_count(sc) && 211 scsi_get_prot_op(sc) != SCSI_PROT_NORMAL) { 212 se_cmd->prot_pto = true; 213 /* 214 * loopback transport doesn't support 215 * WRITE_GENERATE, READ_STRIP protection 216 * information operations, go ahead unprotected. 217 */ 218 transfer_length = scsi_bufflen(sc); 219 } 220 221 rc = target_submit_cmd_map_sgls(se_cmd, tl_nexus->se_sess, sc->cmnd, 222 &tl_cmd->tl_sense_buf[0], tl_cmd->sc->device->lun, 223 transfer_length, tcm_loop_sam_attr(sc, tl_cmd->sc_cmd_tag), 224 sc->sc_data_direction, 0, 225 scsi_sglist(sc), scsi_sg_count(sc), 226 sgl_bidi, sgl_bidi_count, 227 scsi_prot_sglist(sc), scsi_prot_sg_count(sc)); 228 if (rc < 0) { 229 set_host_byte(sc, DID_NO_CONNECT); 230 goto out_done; 231 } 232 return; 233 234out_done: 235 kmem_cache_free(tcm_loop_cmd_cache, tl_cmd); 236 sc->scsi_done(sc); 237 return; 238} 239 240/* 241 * ->queuecommand can be and usually is called from interrupt context, so 242 * defer the actual submission to a workqueue. 243 */ 244static int tcm_loop_queuecommand(struct Scsi_Host *sh, struct scsi_cmnd *sc) 245{ 246 struct tcm_loop_cmd *tl_cmd; 247 248 pr_debug("tcm_loop_queuecommand() %d:%d:%d:%llu got CDB: 0x%02x" 249 " scsi_buf_len: %u\n", sc->device->host->host_no, 250 sc->device->id, sc->device->channel, sc->device->lun, 251 sc->cmnd[0], scsi_bufflen(sc)); 252 253 tl_cmd = kmem_cache_zalloc(tcm_loop_cmd_cache, GFP_ATOMIC); 254 if (!tl_cmd) { 255 pr_err("Unable to allocate struct tcm_loop_cmd\n"); 256 set_host_byte(sc, DID_ERROR); 257 sc->scsi_done(sc); 258 return 0; 259 } 260 261 tl_cmd->sc = sc; 262 tl_cmd->sc_cmd_tag = sc->request->tag; 263 INIT_WORK(&tl_cmd->work, tcm_loop_submission_work); 264 queue_work(tcm_loop_workqueue, &tl_cmd->work); 265 return 0; 266} 267 268/* 269 * Called from SCSI EH process context to issue a LUN_RESET TMR 270 * to struct scsi_device 271 */ 272static int tcm_loop_issue_tmr(struct tcm_loop_tpg *tl_tpg, 273 struct tcm_loop_nexus *tl_nexus, 274 int lun, int task, enum tcm_tmreq_table tmr) 275{ 276 struct se_cmd *se_cmd = NULL; 277 struct se_session *se_sess; 278 struct se_portal_group *se_tpg; 279 struct tcm_loop_cmd *tl_cmd = NULL; 280 struct tcm_loop_tmr *tl_tmr = NULL; 281 int ret = TMR_FUNCTION_FAILED, rc; 282 283 tl_cmd = kmem_cache_zalloc(tcm_loop_cmd_cache, GFP_KERNEL); 284 if (!tl_cmd) { 285 pr_err("Unable to allocate memory for tl_cmd\n"); 286 return ret; 287 } 288 289 tl_tmr = kzalloc(sizeof(struct tcm_loop_tmr), GFP_KERNEL); 290 if (!tl_tmr) { 291 pr_err("Unable to allocate memory for tl_tmr\n"); 292 goto release; 293 } 294 init_waitqueue_head(&tl_tmr->tl_tmr_wait); 295 296 se_cmd = &tl_cmd->tl_se_cmd; 297 se_tpg = &tl_tpg->tl_se_tpg; 298 se_sess = tl_nexus->se_sess; 299 /* 300 * Initialize struct se_cmd descriptor from target_core_mod infrastructure 301 */ 302 transport_init_se_cmd(se_cmd, se_tpg->se_tpg_tfo, se_sess, 0, 303 DMA_NONE, MSG_SIMPLE_TAG, 304 &tl_cmd->tl_sense_buf[0]); 305 306 rc = core_tmr_alloc_req(se_cmd, tl_tmr, tmr, GFP_KERNEL); 307 if (rc < 0) 308 goto release; 309 310 if (tmr == TMR_ABORT_TASK) 311 se_cmd->se_tmr_req->ref_task_tag = task; 312 313 /* 314 * Locate the underlying TCM struct se_lun 315 */ 316 if (transport_lookup_tmr_lun(se_cmd, lun) < 0) { 317 ret = TMR_LUN_DOES_NOT_EXIST; 318 goto release; 319 } 320 /* 321 * Queue the TMR to TCM Core and sleep waiting for 322 * tcm_loop_queue_tm_rsp() to wake us up. 323 */ 324 transport_generic_handle_tmr(se_cmd); 325 wait_event(tl_tmr->tl_tmr_wait, atomic_read(&tl_tmr->tmr_complete)); 326 /* 327 * The TMR LUN_RESET has completed, check the response status and 328 * then release allocations. 329 */ 330 ret = se_cmd->se_tmr_req->response; 331release: 332 if (se_cmd) 333 transport_generic_free_cmd(se_cmd, 1); 334 else 335 kmem_cache_free(tcm_loop_cmd_cache, tl_cmd); 336 kfree(tl_tmr); 337 return ret; 338} 339 340static int tcm_loop_abort_task(struct scsi_cmnd *sc) 341{ 342 struct tcm_loop_hba *tl_hba; 343 struct tcm_loop_nexus *tl_nexus; 344 struct tcm_loop_tpg *tl_tpg; 345 int ret = FAILED; 346 347 /* 348 * Locate the tcm_loop_hba_t pointer 349 */ 350 tl_hba = *(struct tcm_loop_hba **)shost_priv(sc->device->host); 351 /* 352 * Locate the tl_nexus and se_sess pointers 353 */ 354 tl_nexus = tl_hba->tl_nexus; 355 if (!tl_nexus) { 356 pr_err("Unable to perform device reset without" 357 " active I_T Nexus\n"); 358 return FAILED; 359 } 360 361 /* 362 * Locate the tl_tpg pointer from TargetID in sc->device->id 363 */ 364 tl_tpg = &tl_hba->tl_hba_tpgs[sc->device->id]; 365 ret = tcm_loop_issue_tmr(tl_tpg, tl_nexus, sc->device->lun, 366 sc->request->tag, TMR_ABORT_TASK); 367 return (ret == TMR_FUNCTION_COMPLETE) ? SUCCESS : FAILED; 368} 369 370/* 371 * Called from SCSI EH process context to issue a LUN_RESET TMR 372 * to struct scsi_device 373 */ 374static int tcm_loop_device_reset(struct scsi_cmnd *sc) 375{ 376 struct tcm_loop_hba *tl_hba; 377 struct tcm_loop_nexus *tl_nexus; 378 struct tcm_loop_tpg *tl_tpg; 379 int ret = FAILED; 380 381 /* 382 * Locate the tcm_loop_hba_t pointer 383 */ 384 tl_hba = *(struct tcm_loop_hba **)shost_priv(sc->device->host); 385 /* 386 * Locate the tl_nexus and se_sess pointers 387 */ 388 tl_nexus = tl_hba->tl_nexus; 389 if (!tl_nexus) { 390 pr_err("Unable to perform device reset without" 391 " active I_T Nexus\n"); 392 return FAILED; 393 } 394 /* 395 * Locate the tl_tpg pointer from TargetID in sc->device->id 396 */ 397 tl_tpg = &tl_hba->tl_hba_tpgs[sc->device->id]; 398 ret = tcm_loop_issue_tmr(tl_tpg, tl_nexus, sc->device->lun, 399 0, TMR_LUN_RESET); 400 return (ret == TMR_FUNCTION_COMPLETE) ? SUCCESS : FAILED; 401} 402 403static int tcm_loop_target_reset(struct scsi_cmnd *sc) 404{ 405 struct tcm_loop_hba *tl_hba; 406 struct tcm_loop_tpg *tl_tpg; 407 408 /* 409 * Locate the tcm_loop_hba_t pointer 410 */ 411 tl_hba = *(struct tcm_loop_hba **)shost_priv(sc->device->host); 412 if (!tl_hba) { 413 pr_err("Unable to perform device reset without" 414 " active I_T Nexus\n"); 415 return FAILED; 416 } 417 /* 418 * Locate the tl_tpg pointer from TargetID in sc->device->id 419 */ 420 tl_tpg = &tl_hba->tl_hba_tpgs[sc->device->id]; 421 if (tl_tpg) { 422 tl_tpg->tl_transport_status = TCM_TRANSPORT_ONLINE; 423 return SUCCESS; 424 } 425 return FAILED; 426} 427 428static int tcm_loop_slave_alloc(struct scsi_device *sd) 429{ 430 set_bit(QUEUE_FLAG_BIDI, &sd->request_queue->queue_flags); 431 return 0; 432} 433 434static int tcm_loop_slave_configure(struct scsi_device *sd) 435{ 436 if (sd->tagged_supported) { 437 scsi_activate_tcq(sd, sd->queue_depth); 438 scsi_adjust_queue_depth(sd, MSG_SIMPLE_TAG, 439 sd->host->cmd_per_lun); 440 } else { 441 scsi_adjust_queue_depth(sd, 0, 442 sd->host->cmd_per_lun); 443 } 444 445 return 0; 446} 447 448static struct scsi_host_template tcm_loop_driver_template = { 449 .show_info = tcm_loop_show_info, 450 .proc_name = "tcm_loopback", 451 .name = "TCM_Loopback", 452 .queuecommand = tcm_loop_queuecommand, 453 .change_queue_depth = tcm_loop_change_queue_depth, 454 .change_queue_type = tcm_loop_change_queue_type, 455 .eh_abort_handler = tcm_loop_abort_task, 456 .eh_device_reset_handler = tcm_loop_device_reset, 457 .eh_target_reset_handler = tcm_loop_target_reset, 458 .can_queue = 1024, 459 .this_id = -1, 460 .sg_tablesize = 256, 461 .cmd_per_lun = 1024, 462 .max_sectors = 0xFFFF, 463 .use_clustering = DISABLE_CLUSTERING, 464 .slave_alloc = tcm_loop_slave_alloc, 465 .slave_configure = tcm_loop_slave_configure, 466 .module = THIS_MODULE, 467}; 468 469static int tcm_loop_driver_probe(struct device *dev) 470{ 471 struct tcm_loop_hba *tl_hba; 472 struct Scsi_Host *sh; 473 int error, host_prot; 474 475 tl_hba = to_tcm_loop_hba(dev); 476 477 sh = scsi_host_alloc(&tcm_loop_driver_template, 478 sizeof(struct tcm_loop_hba)); 479 if (!sh) { 480 pr_err("Unable to allocate struct scsi_host\n"); 481 return -ENODEV; 482 } 483 tl_hba->sh = sh; 484 485 /* 486 * Assign the struct tcm_loop_hba pointer to struct Scsi_Host->hostdata 487 */ 488 *((struct tcm_loop_hba **)sh->hostdata) = tl_hba; 489 /* 490 * Setup single ID, Channel and LUN for now.. 491 */ 492 sh->max_id = 2; 493 sh->max_lun = 0; 494 sh->max_channel = 0; 495 sh->max_cmd_len = TL_SCSI_MAX_CMD_LEN; 496 497 host_prot = SHOST_DIF_TYPE1_PROTECTION | SHOST_DIF_TYPE2_PROTECTION | 498 SHOST_DIF_TYPE3_PROTECTION | SHOST_DIX_TYPE1_PROTECTION | 499 SHOST_DIX_TYPE2_PROTECTION | SHOST_DIX_TYPE3_PROTECTION; 500 501 scsi_host_set_prot(sh, host_prot); 502 scsi_host_set_guard(sh, SHOST_DIX_GUARD_CRC); 503 504 error = scsi_add_host(sh, &tl_hba->dev); 505 if (error) { 506 pr_err("%s: scsi_add_host failed\n", __func__); 507 scsi_host_put(sh); 508 return -ENODEV; 509 } 510 return 0; 511} 512 513static int tcm_loop_driver_remove(struct device *dev) 514{ 515 struct tcm_loop_hba *tl_hba; 516 struct Scsi_Host *sh; 517 518 tl_hba = to_tcm_loop_hba(dev); 519 sh = tl_hba->sh; 520 521 scsi_remove_host(sh); 522 scsi_host_put(sh); 523 return 0; 524} 525 526static void tcm_loop_release_adapter(struct device *dev) 527{ 528 struct tcm_loop_hba *tl_hba = to_tcm_loop_hba(dev); 529 530 kfree(tl_hba); 531} 532 533/* 534 * Called from tcm_loop_make_scsi_hba() in tcm_loop_configfs.c 535 */ 536static int tcm_loop_setup_hba_bus(struct tcm_loop_hba *tl_hba, int tcm_loop_host_id) 537{ 538 int ret; 539 540 tl_hba->dev.bus = &tcm_loop_lld_bus; 541 tl_hba->dev.parent = tcm_loop_primary; 542 tl_hba->dev.release = &tcm_loop_release_adapter; 543 dev_set_name(&tl_hba->dev, "tcm_loop_adapter_%d", tcm_loop_host_id); 544 545 ret = device_register(&tl_hba->dev); 546 if (ret) { 547 pr_err("device_register() failed for" 548 " tl_hba->dev: %d\n", ret); 549 return -ENODEV; 550 } 551 552 return 0; 553} 554 555/* 556 * Called from tcm_loop_fabric_init() in tcl_loop_fabric.c to load the emulated 557 * tcm_loop SCSI bus. 558 */ 559static int tcm_loop_alloc_core_bus(void) 560{ 561 int ret; 562 563 tcm_loop_primary = root_device_register("tcm_loop_0"); 564 if (IS_ERR(tcm_loop_primary)) { 565 pr_err("Unable to allocate tcm_loop_primary\n"); 566 return PTR_ERR(tcm_loop_primary); 567 } 568 569 ret = bus_register(&tcm_loop_lld_bus); 570 if (ret) { 571 pr_err("bus_register() failed for tcm_loop_lld_bus\n"); 572 goto dev_unreg; 573 } 574 575 ret = driver_register(&tcm_loop_driverfs); 576 if (ret) { 577 pr_err("driver_register() failed for" 578 "tcm_loop_driverfs\n"); 579 goto bus_unreg; 580 } 581 582 pr_debug("Initialized TCM Loop Core Bus\n"); 583 return ret; 584 585bus_unreg: 586 bus_unregister(&tcm_loop_lld_bus); 587dev_unreg: 588 root_device_unregister(tcm_loop_primary); 589 return ret; 590} 591 592static void tcm_loop_release_core_bus(void) 593{ 594 driver_unregister(&tcm_loop_driverfs); 595 bus_unregister(&tcm_loop_lld_bus); 596 root_device_unregister(tcm_loop_primary); 597 598 pr_debug("Releasing TCM Loop Core BUS\n"); 599} 600 601static char *tcm_loop_get_fabric_name(void) 602{ 603 return "loopback"; 604} 605 606static u8 tcm_loop_get_fabric_proto_ident(struct se_portal_group *se_tpg) 607{ 608 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 609 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 610 /* 611 * tl_proto_id is set at tcm_loop_configfs.c:tcm_loop_make_scsi_hba() 612 * time based on the protocol dependent prefix of the passed configfs group. 613 * 614 * Based upon tl_proto_id, TCM_Loop emulates the requested fabric 615 * ProtocolID using target_core_fabric_lib.c symbols. 616 */ 617 switch (tl_hba->tl_proto_id) { 618 case SCSI_PROTOCOL_SAS: 619 return sas_get_fabric_proto_ident(se_tpg); 620 case SCSI_PROTOCOL_FCP: 621 return fc_get_fabric_proto_ident(se_tpg); 622 case SCSI_PROTOCOL_ISCSI: 623 return iscsi_get_fabric_proto_ident(se_tpg); 624 default: 625 pr_err("Unknown tl_proto_id: 0x%02x, using" 626 " SAS emulation\n", tl_hba->tl_proto_id); 627 break; 628 } 629 630 return sas_get_fabric_proto_ident(se_tpg); 631} 632 633static char *tcm_loop_get_endpoint_wwn(struct se_portal_group *se_tpg) 634{ 635 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 636 /* 637 * Return the passed NAA identifier for the SAS Target Port 638 */ 639 return &tl_tpg->tl_hba->tl_wwn_address[0]; 640} 641 642static u16 tcm_loop_get_tag(struct se_portal_group *se_tpg) 643{ 644 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 645 /* 646 * This Tag is used when forming SCSI Name identifier in EVPD=1 0x83 647 * to represent the SCSI Target Port. 648 */ 649 return tl_tpg->tl_tpgt; 650} 651 652static u32 tcm_loop_get_default_depth(struct se_portal_group *se_tpg) 653{ 654 return 1; 655} 656 657static u32 tcm_loop_get_pr_transport_id( 658 struct se_portal_group *se_tpg, 659 struct se_node_acl *se_nacl, 660 struct t10_pr_registration *pr_reg, 661 int *format_code, 662 unsigned char *buf) 663{ 664 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 665 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 666 667 switch (tl_hba->tl_proto_id) { 668 case SCSI_PROTOCOL_SAS: 669 return sas_get_pr_transport_id(se_tpg, se_nacl, pr_reg, 670 format_code, buf); 671 case SCSI_PROTOCOL_FCP: 672 return fc_get_pr_transport_id(se_tpg, se_nacl, pr_reg, 673 format_code, buf); 674 case SCSI_PROTOCOL_ISCSI: 675 return iscsi_get_pr_transport_id(se_tpg, se_nacl, pr_reg, 676 format_code, buf); 677 default: 678 pr_err("Unknown tl_proto_id: 0x%02x, using" 679 " SAS emulation\n", tl_hba->tl_proto_id); 680 break; 681 } 682 683 return sas_get_pr_transport_id(se_tpg, se_nacl, pr_reg, 684 format_code, buf); 685} 686 687static u32 tcm_loop_get_pr_transport_id_len( 688 struct se_portal_group *se_tpg, 689 struct se_node_acl *se_nacl, 690 struct t10_pr_registration *pr_reg, 691 int *format_code) 692{ 693 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 694 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 695 696 switch (tl_hba->tl_proto_id) { 697 case SCSI_PROTOCOL_SAS: 698 return sas_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg, 699 format_code); 700 case SCSI_PROTOCOL_FCP: 701 return fc_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg, 702 format_code); 703 case SCSI_PROTOCOL_ISCSI: 704 return iscsi_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg, 705 format_code); 706 default: 707 pr_err("Unknown tl_proto_id: 0x%02x, using" 708 " SAS emulation\n", tl_hba->tl_proto_id); 709 break; 710 } 711 712 return sas_get_pr_transport_id_len(se_tpg, se_nacl, pr_reg, 713 format_code); 714} 715 716/* 717 * Used for handling SCSI fabric dependent TransportIDs in SPC-3 and above 718 * Persistent Reservation SPEC_I_PT=1 and PROUT REGISTER_AND_MOVE operations. 719 */ 720static char *tcm_loop_parse_pr_out_transport_id( 721 struct se_portal_group *se_tpg, 722 const char *buf, 723 u32 *out_tid_len, 724 char **port_nexus_ptr) 725{ 726 struct tcm_loop_tpg *tl_tpg = se_tpg->se_tpg_fabric_ptr; 727 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 728 729 switch (tl_hba->tl_proto_id) { 730 case SCSI_PROTOCOL_SAS: 731 return sas_parse_pr_out_transport_id(se_tpg, buf, out_tid_len, 732 port_nexus_ptr); 733 case SCSI_PROTOCOL_FCP: 734 return fc_parse_pr_out_transport_id(se_tpg, buf, out_tid_len, 735 port_nexus_ptr); 736 case SCSI_PROTOCOL_ISCSI: 737 return iscsi_parse_pr_out_transport_id(se_tpg, buf, out_tid_len, 738 port_nexus_ptr); 739 default: 740 pr_err("Unknown tl_proto_id: 0x%02x, using" 741 " SAS emulation\n", tl_hba->tl_proto_id); 742 break; 743 } 744 745 return sas_parse_pr_out_transport_id(se_tpg, buf, out_tid_len, 746 port_nexus_ptr); 747} 748 749/* 750 * Returning (1) here allows for target_core_mod struct se_node_acl to be generated 751 * based upon the incoming fabric dependent SCSI Initiator Port 752 */ 753static int tcm_loop_check_demo_mode(struct se_portal_group *se_tpg) 754{ 755 return 1; 756} 757 758static int tcm_loop_check_demo_mode_cache(struct se_portal_group *se_tpg) 759{ 760 return 0; 761} 762 763/* 764 * Allow I_T Nexus full READ-WRITE access without explict Initiator Node ACLs for 765 * local virtual Linux/SCSI LLD passthrough into VM hypervisor guest 766 */ 767static int tcm_loop_check_demo_mode_write_protect(struct se_portal_group *se_tpg) 768{ 769 return 0; 770} 771 772/* 773 * Because TCM_Loop does not use explict ACLs and MappedLUNs, this will 774 * never be called for TCM_Loop by target_core_fabric_configfs.c code. 775 * It has been added here as a nop for target_fabric_tf_ops_check() 776 */ 777static int tcm_loop_check_prod_mode_write_protect(struct se_portal_group *se_tpg) 778{ 779 return 0; 780} 781 782static struct se_node_acl *tcm_loop_tpg_alloc_fabric_acl( 783 struct se_portal_group *se_tpg) 784{ 785 struct tcm_loop_nacl *tl_nacl; 786 787 tl_nacl = kzalloc(sizeof(struct tcm_loop_nacl), GFP_KERNEL); 788 if (!tl_nacl) { 789 pr_err("Unable to allocate struct tcm_loop_nacl\n"); 790 return NULL; 791 } 792 793 return &tl_nacl->se_node_acl; 794} 795 796static void tcm_loop_tpg_release_fabric_acl( 797 struct se_portal_group *se_tpg, 798 struct se_node_acl *se_nacl) 799{ 800 struct tcm_loop_nacl *tl_nacl = container_of(se_nacl, 801 struct tcm_loop_nacl, se_node_acl); 802 803 kfree(tl_nacl); 804} 805 806static u32 tcm_loop_get_inst_index(struct se_portal_group *se_tpg) 807{ 808 return 1; 809} 810 811static u32 tcm_loop_sess_get_index(struct se_session *se_sess) 812{ 813 return 1; 814} 815 816static void tcm_loop_set_default_node_attributes(struct se_node_acl *se_acl) 817{ 818 return; 819} 820 821static u32 tcm_loop_get_task_tag(struct se_cmd *se_cmd) 822{ 823 struct tcm_loop_cmd *tl_cmd = container_of(se_cmd, 824 struct tcm_loop_cmd, tl_se_cmd); 825 826 return tl_cmd->sc_cmd_tag; 827} 828 829static int tcm_loop_get_cmd_state(struct se_cmd *se_cmd) 830{ 831 struct tcm_loop_cmd *tl_cmd = container_of(se_cmd, 832 struct tcm_loop_cmd, tl_se_cmd); 833 834 return tl_cmd->sc_cmd_state; 835} 836 837static int tcm_loop_shutdown_session(struct se_session *se_sess) 838{ 839 return 0; 840} 841 842static void tcm_loop_close_session(struct se_session *se_sess) 843{ 844 return; 845}; 846 847static int tcm_loop_write_pending(struct se_cmd *se_cmd) 848{ 849 /* 850 * Since Linux/SCSI has already sent down a struct scsi_cmnd 851 * sc->sc_data_direction of DMA_TO_DEVICE with struct scatterlist array 852 * memory, and memory has already been mapped to struct se_cmd->t_mem_list 853 * format with transport_generic_map_mem_to_cmd(). 854 * 855 * We now tell TCM to add this WRITE CDB directly into the TCM storage 856 * object execution queue. 857 */ 858 target_execute_cmd(se_cmd); 859 return 0; 860} 861 862static int tcm_loop_write_pending_status(struct se_cmd *se_cmd) 863{ 864 return 0; 865} 866 867static int tcm_loop_queue_data_in(struct se_cmd *se_cmd) 868{ 869 struct tcm_loop_cmd *tl_cmd = container_of(se_cmd, 870 struct tcm_loop_cmd, tl_se_cmd); 871 struct scsi_cmnd *sc = tl_cmd->sc; 872 873 pr_debug("tcm_loop_queue_data_in() called for scsi_cmnd: %p" 874 " cdb: 0x%02x\n", sc, sc->cmnd[0]); 875 876 sc->result = SAM_STAT_GOOD; 877 set_host_byte(sc, DID_OK); 878 if ((se_cmd->se_cmd_flags & SCF_OVERFLOW_BIT) || 879 (se_cmd->se_cmd_flags & SCF_UNDERFLOW_BIT)) 880 scsi_set_resid(sc, se_cmd->residual_count); 881 sc->scsi_done(sc); 882 return 0; 883} 884 885static int tcm_loop_queue_status(struct se_cmd *se_cmd) 886{ 887 struct tcm_loop_cmd *tl_cmd = container_of(se_cmd, 888 struct tcm_loop_cmd, tl_se_cmd); 889 struct scsi_cmnd *sc = tl_cmd->sc; 890 891 pr_debug("tcm_loop_queue_status() called for scsi_cmnd: %p" 892 " cdb: 0x%02x\n", sc, sc->cmnd[0]); 893 894 if (se_cmd->sense_buffer && 895 ((se_cmd->se_cmd_flags & SCF_TRANSPORT_TASK_SENSE) || 896 (se_cmd->se_cmd_flags & SCF_EMULATED_TASK_SENSE))) { 897 898 memcpy(sc->sense_buffer, se_cmd->sense_buffer, 899 SCSI_SENSE_BUFFERSIZE); 900 sc->result = SAM_STAT_CHECK_CONDITION; 901 set_driver_byte(sc, DRIVER_SENSE); 902 } else 903 sc->result = se_cmd->scsi_status; 904 905 set_host_byte(sc, DID_OK); 906 if ((se_cmd->se_cmd_flags & SCF_OVERFLOW_BIT) || 907 (se_cmd->se_cmd_flags & SCF_UNDERFLOW_BIT)) 908 scsi_set_resid(sc, se_cmd->residual_count); 909 sc->scsi_done(sc); 910 return 0; 911} 912 913static void tcm_loop_queue_tm_rsp(struct se_cmd *se_cmd) 914{ 915 struct se_tmr_req *se_tmr = se_cmd->se_tmr_req; 916 struct tcm_loop_tmr *tl_tmr = se_tmr->fabric_tmr_ptr; 917 /* 918 * The SCSI EH thread will be sleeping on se_tmr->tl_tmr_wait, go ahead 919 * and wake up the wait_queue_head_t in tcm_loop_device_reset() 920 */ 921 atomic_set(&tl_tmr->tmr_complete, 1); 922 wake_up(&tl_tmr->tl_tmr_wait); 923} 924 925static void tcm_loop_aborted_task(struct se_cmd *se_cmd) 926{ 927 return; 928} 929 930static char *tcm_loop_dump_proto_id(struct tcm_loop_hba *tl_hba) 931{ 932 switch (tl_hba->tl_proto_id) { 933 case SCSI_PROTOCOL_SAS: 934 return "SAS"; 935 case SCSI_PROTOCOL_FCP: 936 return "FCP"; 937 case SCSI_PROTOCOL_ISCSI: 938 return "iSCSI"; 939 default: 940 break; 941 } 942 943 return "Unknown"; 944} 945 946/* Start items for tcm_loop_port_cit */ 947 948static int tcm_loop_port_link( 949 struct se_portal_group *se_tpg, 950 struct se_lun *lun) 951{ 952 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 953 struct tcm_loop_tpg, tl_se_tpg); 954 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 955 956 atomic_inc_mb(&tl_tpg->tl_tpg_port_count); 957 /* 958 * Add Linux/SCSI struct scsi_device by HCTL 959 */ 960 scsi_add_device(tl_hba->sh, 0, tl_tpg->tl_tpgt, lun->unpacked_lun); 961 962 pr_debug("TCM_Loop_ConfigFS: Port Link Successful\n"); 963 return 0; 964} 965 966static void tcm_loop_port_unlink( 967 struct se_portal_group *se_tpg, 968 struct se_lun *se_lun) 969{ 970 struct scsi_device *sd; 971 struct tcm_loop_hba *tl_hba; 972 struct tcm_loop_tpg *tl_tpg; 973 974 tl_tpg = container_of(se_tpg, struct tcm_loop_tpg, tl_se_tpg); 975 tl_hba = tl_tpg->tl_hba; 976 977 sd = scsi_device_lookup(tl_hba->sh, 0, tl_tpg->tl_tpgt, 978 se_lun->unpacked_lun); 979 if (!sd) { 980 pr_err("Unable to locate struct scsi_device for %d:%d:" 981 "%d\n", 0, tl_tpg->tl_tpgt, se_lun->unpacked_lun); 982 return; 983 } 984 /* 985 * Remove Linux/SCSI struct scsi_device by HCTL 986 */ 987 scsi_remove_device(sd); 988 scsi_device_put(sd); 989 990 atomic_dec_mb(&tl_tpg->tl_tpg_port_count); 991 992 pr_debug("TCM_Loop_ConfigFS: Port Unlink Successful\n"); 993} 994 995/* End items for tcm_loop_port_cit */ 996 997/* Start items for tcm_loop_nexus_cit */ 998 999static int tcm_loop_make_nexus( 1000 struct tcm_loop_tpg *tl_tpg, 1001 const char *name) 1002{ 1003 struct se_portal_group *se_tpg; 1004 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 1005 struct tcm_loop_nexus *tl_nexus; 1006 int ret = -ENOMEM; 1007 1008 if (tl_tpg->tl_hba->tl_nexus) { 1009 pr_debug("tl_tpg->tl_hba->tl_nexus already exists\n"); 1010 return -EEXIST; 1011 } 1012 se_tpg = &tl_tpg->tl_se_tpg; 1013 1014 tl_nexus = kzalloc(sizeof(struct tcm_loop_nexus), GFP_KERNEL); 1015 if (!tl_nexus) { 1016 pr_err("Unable to allocate struct tcm_loop_nexus\n"); 1017 return -ENOMEM; 1018 } 1019 /* 1020 * Initialize the struct se_session pointer 1021 */ 1022 tl_nexus->se_sess = transport_init_session(TARGET_PROT_ALL); 1023 if (IS_ERR(tl_nexus->se_sess)) { 1024 ret = PTR_ERR(tl_nexus->se_sess); 1025 goto out; 1026 } 1027 /* 1028 * Since we are running in 'demo mode' this call with generate a 1029 * struct se_node_acl for the tcm_loop struct se_portal_group with the SCSI 1030 * Initiator port name of the passed configfs group 'name'. 1031 */ 1032 tl_nexus->se_sess->se_node_acl = core_tpg_check_initiator_node_acl( 1033 se_tpg, (unsigned char *)name); 1034 if (!tl_nexus->se_sess->se_node_acl) { 1035 transport_free_session(tl_nexus->se_sess); 1036 goto out; 1037 } 1038 /* 1039 * Now, register the SAS I_T Nexus as active with the call to 1040 * transport_register_session() 1041 */ 1042 __transport_register_session(se_tpg, tl_nexus->se_sess->se_node_acl, 1043 tl_nexus->se_sess, tl_nexus); 1044 tl_tpg->tl_hba->tl_nexus = tl_nexus; 1045 pr_debug("TCM_Loop_ConfigFS: Established I_T Nexus to emulated" 1046 " %s Initiator Port: %s\n", tcm_loop_dump_proto_id(tl_hba), 1047 name); 1048 return 0; 1049 1050out: 1051 kfree(tl_nexus); 1052 return ret; 1053} 1054 1055static int tcm_loop_drop_nexus( 1056 struct tcm_loop_tpg *tpg) 1057{ 1058 struct se_session *se_sess; 1059 struct tcm_loop_nexus *tl_nexus; 1060 struct tcm_loop_hba *tl_hba = tpg->tl_hba; 1061 1062 if (!tl_hba) 1063 return -ENODEV; 1064 1065 tl_nexus = tl_hba->tl_nexus; 1066 if (!tl_nexus) 1067 return -ENODEV; 1068 1069 se_sess = tl_nexus->se_sess; 1070 if (!se_sess) 1071 return -ENODEV; 1072 1073 if (atomic_read(&tpg->tl_tpg_port_count)) { 1074 pr_err("Unable to remove TCM_Loop I_T Nexus with" 1075 " active TPG port count: %d\n", 1076 atomic_read(&tpg->tl_tpg_port_count)); 1077 return -EPERM; 1078 } 1079 1080 pr_debug("TCM_Loop_ConfigFS: Removing I_T Nexus to emulated" 1081 " %s Initiator Port: %s\n", tcm_loop_dump_proto_id(tl_hba), 1082 tl_nexus->se_sess->se_node_acl->initiatorname); 1083 /* 1084 * Release the SCSI I_T Nexus to the emulated SAS Target Port 1085 */ 1086 transport_deregister_session(tl_nexus->se_sess); 1087 tpg->tl_hba->tl_nexus = NULL; 1088 kfree(tl_nexus); 1089 return 0; 1090} 1091 1092/* End items for tcm_loop_nexus_cit */ 1093 1094static ssize_t tcm_loop_tpg_show_nexus( 1095 struct se_portal_group *se_tpg, 1096 char *page) 1097{ 1098 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 1099 struct tcm_loop_tpg, tl_se_tpg); 1100 struct tcm_loop_nexus *tl_nexus; 1101 ssize_t ret; 1102 1103 tl_nexus = tl_tpg->tl_hba->tl_nexus; 1104 if (!tl_nexus) 1105 return -ENODEV; 1106 1107 ret = snprintf(page, PAGE_SIZE, "%s\n", 1108 tl_nexus->se_sess->se_node_acl->initiatorname); 1109 1110 return ret; 1111} 1112 1113static ssize_t tcm_loop_tpg_store_nexus( 1114 struct se_portal_group *se_tpg, 1115 const char *page, 1116 size_t count) 1117{ 1118 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 1119 struct tcm_loop_tpg, tl_se_tpg); 1120 struct tcm_loop_hba *tl_hba = tl_tpg->tl_hba; 1121 unsigned char i_port[TL_WWN_ADDR_LEN], *ptr, *port_ptr; 1122 int ret; 1123 /* 1124 * Shutdown the active I_T nexus if 'NULL' is passed.. 1125 */ 1126 if (!strncmp(page, "NULL", 4)) { 1127 ret = tcm_loop_drop_nexus(tl_tpg); 1128 return (!ret) ? count : ret; 1129 } 1130 /* 1131 * Otherwise make sure the passed virtual Initiator port WWN matches 1132 * the fabric protocol_id set in tcm_loop_make_scsi_hba(), and call 1133 * tcm_loop_make_nexus() 1134 */ 1135 if (strlen(page) >= TL_WWN_ADDR_LEN) { 1136 pr_err("Emulated NAA Sas Address: %s, exceeds" 1137 " max: %d\n", page, TL_WWN_ADDR_LEN); 1138 return -EINVAL; 1139 } 1140 snprintf(&i_port[0], TL_WWN_ADDR_LEN, "%s", page); 1141 1142 ptr = strstr(i_port, "naa."); 1143 if (ptr) { 1144 if (tl_hba->tl_proto_id != SCSI_PROTOCOL_SAS) { 1145 pr_err("Passed SAS Initiator Port %s does not" 1146 " match target port protoid: %s\n", i_port, 1147 tcm_loop_dump_proto_id(tl_hba)); 1148 return -EINVAL; 1149 } 1150 port_ptr = &i_port[0]; 1151 goto check_newline; 1152 } 1153 ptr = strstr(i_port, "fc."); 1154 if (ptr) { 1155 if (tl_hba->tl_proto_id != SCSI_PROTOCOL_FCP) { 1156 pr_err("Passed FCP Initiator Port %s does not" 1157 " match target port protoid: %s\n", i_port, 1158 tcm_loop_dump_proto_id(tl_hba)); 1159 return -EINVAL; 1160 } 1161 port_ptr = &i_port[3]; /* Skip over "fc." */ 1162 goto check_newline; 1163 } 1164 ptr = strstr(i_port, "iqn."); 1165 if (ptr) { 1166 if (tl_hba->tl_proto_id != SCSI_PROTOCOL_ISCSI) { 1167 pr_err("Passed iSCSI Initiator Port %s does not" 1168 " match target port protoid: %s\n", i_port, 1169 tcm_loop_dump_proto_id(tl_hba)); 1170 return -EINVAL; 1171 } 1172 port_ptr = &i_port[0]; 1173 goto check_newline; 1174 } 1175 pr_err("Unable to locate prefix for emulated Initiator Port:" 1176 " %s\n", i_port); 1177 return -EINVAL; 1178 /* 1179 * Clear any trailing newline for the NAA WWN 1180 */ 1181check_newline: 1182 if (i_port[strlen(i_port)-1] == '\n') 1183 i_port[strlen(i_port)-1] = '\0'; 1184 1185 ret = tcm_loop_make_nexus(tl_tpg, port_ptr); 1186 if (ret < 0) 1187 return ret; 1188 1189 return count; 1190} 1191 1192TF_TPG_BASE_ATTR(tcm_loop, nexus, S_IRUGO | S_IWUSR); 1193 1194static ssize_t tcm_loop_tpg_show_transport_status( 1195 struct se_portal_group *se_tpg, 1196 char *page) 1197{ 1198 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 1199 struct tcm_loop_tpg, tl_se_tpg); 1200 const char *status = NULL; 1201 ssize_t ret = -EINVAL; 1202 1203 switch (tl_tpg->tl_transport_status) { 1204 case TCM_TRANSPORT_ONLINE: 1205 status = "online"; 1206 break; 1207 case TCM_TRANSPORT_OFFLINE: 1208 status = "offline"; 1209 break; 1210 default: 1211 break; 1212 } 1213 1214 if (status) 1215 ret = snprintf(page, PAGE_SIZE, "%s\n", status); 1216 1217 return ret; 1218} 1219 1220static ssize_t tcm_loop_tpg_store_transport_status( 1221 struct se_portal_group *se_tpg, 1222 const char *page, 1223 size_t count) 1224{ 1225 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 1226 struct tcm_loop_tpg, tl_se_tpg); 1227 1228 if (!strncmp(page, "online", 6)) { 1229 tl_tpg->tl_transport_status = TCM_TRANSPORT_ONLINE; 1230 return count; 1231 } 1232 if (!strncmp(page, "offline", 7)) { 1233 tl_tpg->tl_transport_status = TCM_TRANSPORT_OFFLINE; 1234 return count; 1235 } 1236 return -EINVAL; 1237} 1238 1239TF_TPG_BASE_ATTR(tcm_loop, transport_status, S_IRUGO | S_IWUSR); 1240 1241static struct configfs_attribute *tcm_loop_tpg_attrs[] = { 1242 &tcm_loop_tpg_nexus.attr, 1243 &tcm_loop_tpg_transport_status.attr, 1244 NULL, 1245}; 1246 1247/* Start items for tcm_loop_naa_cit */ 1248 1249static struct se_portal_group *tcm_loop_make_naa_tpg( 1250 struct se_wwn *wwn, 1251 struct config_group *group, 1252 const char *name) 1253{ 1254 struct tcm_loop_hba *tl_hba = container_of(wwn, 1255 struct tcm_loop_hba, tl_hba_wwn); 1256 struct tcm_loop_tpg *tl_tpg; 1257 char *tpgt_str, *end_ptr; 1258 int ret; 1259 unsigned short int tpgt; 1260 1261 tpgt_str = strstr(name, "tpgt_"); 1262 if (!tpgt_str) { 1263 pr_err("Unable to locate \"tpgt_#\" directory" 1264 " group\n"); 1265 return ERR_PTR(-EINVAL); 1266 } 1267 tpgt_str += 5; /* Skip ahead of "tpgt_" */ 1268 tpgt = (unsigned short int) simple_strtoul(tpgt_str, &end_ptr, 0); 1269 1270 if (tpgt >= TL_TPGS_PER_HBA) { 1271 pr_err("Passed tpgt: %hu exceeds TL_TPGS_PER_HBA:" 1272 " %u\n", tpgt, TL_TPGS_PER_HBA); 1273 return ERR_PTR(-EINVAL); 1274 } 1275 tl_tpg = &tl_hba->tl_hba_tpgs[tpgt]; 1276 tl_tpg->tl_hba = tl_hba; 1277 tl_tpg->tl_tpgt = tpgt; 1278 /* 1279 * Register the tl_tpg as a emulated SAS TCM Target Endpoint 1280 */ 1281 ret = core_tpg_register(&tcm_loop_fabric_configfs->tf_ops, 1282 wwn, &tl_tpg->tl_se_tpg, tl_tpg, 1283 TRANSPORT_TPG_TYPE_NORMAL); 1284 if (ret < 0) 1285 return ERR_PTR(-ENOMEM); 1286 1287 pr_debug("TCM_Loop_ConfigFS: Allocated Emulated %s" 1288 " Target Port %s,t,0x%04x\n", tcm_loop_dump_proto_id(tl_hba), 1289 config_item_name(&wwn->wwn_group.cg_item), tpgt); 1290 1291 return &tl_tpg->tl_se_tpg; 1292} 1293 1294static void tcm_loop_drop_naa_tpg( 1295 struct se_portal_group *se_tpg) 1296{ 1297 struct se_wwn *wwn = se_tpg->se_tpg_wwn; 1298 struct tcm_loop_tpg *tl_tpg = container_of(se_tpg, 1299 struct tcm_loop_tpg, tl_se_tpg); 1300 struct tcm_loop_hba *tl_hba; 1301 unsigned short tpgt; 1302 1303 tl_hba = tl_tpg->tl_hba; 1304 tpgt = tl_tpg->tl_tpgt; 1305 /* 1306 * Release the I_T Nexus for the Virtual SAS link if present 1307 */ 1308 tcm_loop_drop_nexus(tl_tpg); 1309 /* 1310 * Deregister the tl_tpg as a emulated SAS TCM Target Endpoint 1311 */ 1312 core_tpg_deregister(se_tpg); 1313 1314 tl_tpg->tl_hba = NULL; 1315 tl_tpg->tl_tpgt = 0; 1316 1317 pr_debug("TCM_Loop_ConfigFS: Deallocated Emulated %s" 1318 " Target Port %s,t,0x%04x\n", tcm_loop_dump_proto_id(tl_hba), 1319 config_item_name(&wwn->wwn_group.cg_item), tpgt); 1320} 1321 1322/* End items for tcm_loop_naa_cit */ 1323 1324/* Start items for tcm_loop_cit */ 1325 1326static struct se_wwn *tcm_loop_make_scsi_hba( 1327 struct target_fabric_configfs *tf, 1328 struct config_group *group, 1329 const char *name) 1330{ 1331 struct tcm_loop_hba *tl_hba; 1332 struct Scsi_Host *sh; 1333 char *ptr; 1334 int ret, off = 0; 1335 1336 tl_hba = kzalloc(sizeof(struct tcm_loop_hba), GFP_KERNEL); 1337 if (!tl_hba) { 1338 pr_err("Unable to allocate struct tcm_loop_hba\n"); 1339 return ERR_PTR(-ENOMEM); 1340 } 1341 /* 1342 * Determine the emulated Protocol Identifier and Target Port Name 1343 * based on the incoming configfs directory name. 1344 */ 1345 ptr = strstr(name, "naa."); 1346 if (ptr) { 1347 tl_hba->tl_proto_id = SCSI_PROTOCOL_SAS; 1348 goto check_len; 1349 } 1350 ptr = strstr(name, "fc."); 1351 if (ptr) { 1352 tl_hba->tl_proto_id = SCSI_PROTOCOL_FCP; 1353 off = 3; /* Skip over "fc." */ 1354 goto check_len; 1355 } 1356 ptr = strstr(name, "iqn."); 1357 if (!ptr) { 1358 pr_err("Unable to locate prefix for emulated Target " 1359 "Port: %s\n", name); 1360 ret = -EINVAL; 1361 goto out; 1362 } 1363 tl_hba->tl_proto_id = SCSI_PROTOCOL_ISCSI; 1364 1365check_len: 1366 if (strlen(name) >= TL_WWN_ADDR_LEN) { 1367 pr_err("Emulated NAA %s Address: %s, exceeds" 1368 " max: %d\n", name, tcm_loop_dump_proto_id(tl_hba), 1369 TL_WWN_ADDR_LEN); 1370 ret = -EINVAL; 1371 goto out; 1372 } 1373 snprintf(&tl_hba->tl_wwn_address[0], TL_WWN_ADDR_LEN, "%s", &name[off]); 1374 1375 /* 1376 * Call device_register(tl_hba->dev) to register the emulated 1377 * Linux/SCSI LLD of type struct Scsi_Host at tl_hba->sh after 1378 * device_register() callbacks in tcm_loop_driver_probe() 1379 */ 1380 ret = tcm_loop_setup_hba_bus(tl_hba, tcm_loop_hba_no_cnt); 1381 if (ret) 1382 goto out; 1383 1384 sh = tl_hba->sh; 1385 tcm_loop_hba_no_cnt++; 1386 pr_debug("TCM_Loop_ConfigFS: Allocated emulated Target" 1387 " %s Address: %s at Linux/SCSI Host ID: %d\n", 1388 tcm_loop_dump_proto_id(tl_hba), name, sh->host_no); 1389 1390 return &tl_hba->tl_hba_wwn; 1391out: 1392 kfree(tl_hba); 1393 return ERR_PTR(ret); 1394} 1395 1396static void tcm_loop_drop_scsi_hba( 1397 struct se_wwn *wwn) 1398{ 1399 struct tcm_loop_hba *tl_hba = container_of(wwn, 1400 struct tcm_loop_hba, tl_hba_wwn); 1401 1402 pr_debug("TCM_Loop_ConfigFS: Deallocating emulated Target" 1403 " SAS Address: %s at Linux/SCSI Host ID: %d\n", 1404 tl_hba->tl_wwn_address, tl_hba->sh->host_no); 1405 /* 1406 * Call device_unregister() on the original tl_hba->dev. 1407 * tcm_loop_fabric_scsi.c:tcm_loop_release_adapter() will 1408 * release *tl_hba; 1409 */ 1410 device_unregister(&tl_hba->dev); 1411} 1412 1413/* Start items for tcm_loop_cit */ 1414static ssize_t tcm_loop_wwn_show_attr_version( 1415 struct target_fabric_configfs *tf, 1416 char *page) 1417{ 1418 return sprintf(page, "TCM Loopback Fabric module %s\n", TCM_LOOP_VERSION); 1419} 1420 1421TF_WWN_ATTR_RO(tcm_loop, version); 1422 1423static struct configfs_attribute *tcm_loop_wwn_attrs[] = { 1424 &tcm_loop_wwn_version.attr, 1425 NULL, 1426}; 1427 1428/* End items for tcm_loop_cit */ 1429 1430static int tcm_loop_register_configfs(void) 1431{ 1432 struct target_fabric_configfs *fabric; 1433 int ret; 1434 /* 1435 * Set the TCM Loop HBA counter to zero 1436 */ 1437 tcm_loop_hba_no_cnt = 0; 1438 /* 1439 * Register the top level struct config_item_type with TCM core 1440 */ 1441 fabric = target_fabric_configfs_init(THIS_MODULE, "loopback"); 1442 if (IS_ERR(fabric)) { 1443 pr_err("tcm_loop_register_configfs() failed!\n"); 1444 return PTR_ERR(fabric); 1445 } 1446 /* 1447 * Setup the fabric API of function pointers used by target_core_mod 1448 */ 1449 fabric->tf_ops.get_fabric_name = &tcm_loop_get_fabric_name; 1450 fabric->tf_ops.get_fabric_proto_ident = &tcm_loop_get_fabric_proto_ident; 1451 fabric->tf_ops.tpg_get_wwn = &tcm_loop_get_endpoint_wwn; 1452 fabric->tf_ops.tpg_get_tag = &tcm_loop_get_tag; 1453 fabric->tf_ops.tpg_get_default_depth = &tcm_loop_get_default_depth; 1454 fabric->tf_ops.tpg_get_pr_transport_id = &tcm_loop_get_pr_transport_id; 1455 fabric->tf_ops.tpg_get_pr_transport_id_len = 1456 &tcm_loop_get_pr_transport_id_len; 1457 fabric->tf_ops.tpg_parse_pr_out_transport_id = 1458 &tcm_loop_parse_pr_out_transport_id; 1459 fabric->tf_ops.tpg_check_demo_mode = &tcm_loop_check_demo_mode; 1460 fabric->tf_ops.tpg_check_demo_mode_cache = 1461 &tcm_loop_check_demo_mode_cache; 1462 fabric->tf_ops.tpg_check_demo_mode_write_protect = 1463 &tcm_loop_check_demo_mode_write_protect; 1464 fabric->tf_ops.tpg_check_prod_mode_write_protect = 1465 &tcm_loop_check_prod_mode_write_protect; 1466 /* 1467 * The TCM loopback fabric module runs in demo-mode to a local 1468 * virtual SCSI device, so fabric dependent initator ACLs are 1469 * not required. 1470 */ 1471 fabric->tf_ops.tpg_alloc_fabric_acl = &tcm_loop_tpg_alloc_fabric_acl; 1472 fabric->tf_ops.tpg_release_fabric_acl = 1473 &tcm_loop_tpg_release_fabric_acl; 1474 fabric->tf_ops.tpg_get_inst_index = &tcm_loop_get_inst_index; 1475 /* 1476 * Used for setting up remaining TCM resources in process context 1477 */ 1478 fabric->tf_ops.check_stop_free = &tcm_loop_check_stop_free; 1479 fabric->tf_ops.release_cmd = &tcm_loop_release_cmd; 1480 fabric->tf_ops.shutdown_session = &tcm_loop_shutdown_session; 1481 fabric->tf_ops.close_session = &tcm_loop_close_session; 1482 fabric->tf_ops.sess_get_index = &tcm_loop_sess_get_index; 1483 fabric->tf_ops.sess_get_initiator_sid = NULL; 1484 fabric->tf_ops.write_pending = &tcm_loop_write_pending; 1485 fabric->tf_ops.write_pending_status = &tcm_loop_write_pending_status; 1486 /* 1487 * Not used for TCM loopback 1488 */ 1489 fabric->tf_ops.set_default_node_attributes = 1490 &tcm_loop_set_default_node_attributes; 1491 fabric->tf_ops.get_task_tag = &tcm_loop_get_task_tag; 1492 fabric->tf_ops.get_cmd_state = &tcm_loop_get_cmd_state; 1493 fabric->tf_ops.queue_data_in = &tcm_loop_queue_data_in; 1494 fabric->tf_ops.queue_status = &tcm_loop_queue_status; 1495 fabric->tf_ops.queue_tm_rsp = &tcm_loop_queue_tm_rsp; 1496 fabric->tf_ops.aborted_task = &tcm_loop_aborted_task; 1497 1498 /* 1499 * Setup function pointers for generic logic in target_core_fabric_configfs.c 1500 */ 1501 fabric->tf_ops.fabric_make_wwn = &tcm_loop_make_scsi_hba; 1502 fabric->tf_ops.fabric_drop_wwn = &tcm_loop_drop_scsi_hba; 1503 fabric->tf_ops.fabric_make_tpg = &tcm_loop_make_naa_tpg; 1504 fabric->tf_ops.fabric_drop_tpg = &tcm_loop_drop_naa_tpg; 1505 /* 1506 * fabric_post_link() and fabric_pre_unlink() are used for 1507 * registration and release of TCM Loop Virtual SCSI LUNs. 1508 */ 1509 fabric->tf_ops.fabric_post_link = &tcm_loop_port_link; 1510 fabric->tf_ops.fabric_pre_unlink = &tcm_loop_port_unlink; 1511 fabric->tf_ops.fabric_make_np = NULL; 1512 fabric->tf_ops.fabric_drop_np = NULL; 1513 /* 1514 * Setup default attribute lists for various fabric->tf_cit_tmpl 1515 */ 1516 fabric->tf_cit_tmpl.tfc_wwn_cit.ct_attrs = tcm_loop_wwn_attrs; 1517 fabric->tf_cit_tmpl.tfc_tpg_base_cit.ct_attrs = tcm_loop_tpg_attrs; 1518 fabric->tf_cit_tmpl.tfc_tpg_attrib_cit.ct_attrs = NULL; 1519 fabric->tf_cit_tmpl.tfc_tpg_param_cit.ct_attrs = NULL; 1520 fabric->tf_cit_tmpl.tfc_tpg_np_base_cit.ct_attrs = NULL; 1521 /* 1522 * Once fabric->tf_ops has been setup, now register the fabric for 1523 * use within TCM 1524 */ 1525 ret = target_fabric_configfs_register(fabric); 1526 if (ret < 0) { 1527 pr_err("target_fabric_configfs_register() for" 1528 " TCM_Loop failed!\n"); 1529 target_fabric_configfs_free(fabric); 1530 return -1; 1531 } 1532 /* 1533 * Setup our local pointer to *fabric. 1534 */ 1535 tcm_loop_fabric_configfs = fabric; 1536 pr_debug("TCM_LOOP[0] - Set fabric ->" 1537 " tcm_loop_fabric_configfs\n"); 1538 return 0; 1539} 1540 1541static void tcm_loop_deregister_configfs(void) 1542{ 1543 if (!tcm_loop_fabric_configfs) 1544 return; 1545 1546 target_fabric_configfs_deregister(tcm_loop_fabric_configfs); 1547 tcm_loop_fabric_configfs = NULL; 1548 pr_debug("TCM_LOOP[0] - Cleared" 1549 " tcm_loop_fabric_configfs\n"); 1550} 1551 1552static int __init tcm_loop_fabric_init(void) 1553{ 1554 int ret = -ENOMEM; 1555 1556 tcm_loop_workqueue = alloc_workqueue("tcm_loop", 0, 0); 1557 if (!tcm_loop_workqueue) 1558 goto out; 1559 1560 tcm_loop_cmd_cache = kmem_cache_create("tcm_loop_cmd_cache", 1561 sizeof(struct tcm_loop_cmd), 1562 __alignof__(struct tcm_loop_cmd), 1563 0, NULL); 1564 if (!tcm_loop_cmd_cache) { 1565 pr_debug("kmem_cache_create() for" 1566 " tcm_loop_cmd_cache failed\n"); 1567 goto out_destroy_workqueue; 1568 } 1569 1570 ret = tcm_loop_alloc_core_bus(); 1571 if (ret) 1572 goto out_destroy_cache; 1573 1574 ret = tcm_loop_register_configfs(); 1575 if (ret) 1576 goto out_release_core_bus; 1577 1578 return 0; 1579 1580out_release_core_bus: 1581 tcm_loop_release_core_bus(); 1582out_destroy_cache: 1583 kmem_cache_destroy(tcm_loop_cmd_cache); 1584out_destroy_workqueue: 1585 destroy_workqueue(tcm_loop_workqueue); 1586out: 1587 return ret; 1588} 1589 1590static void __exit tcm_loop_fabric_exit(void) 1591{ 1592 tcm_loop_deregister_configfs(); 1593 tcm_loop_release_core_bus(); 1594 kmem_cache_destroy(tcm_loop_cmd_cache); 1595 destroy_workqueue(tcm_loop_workqueue); 1596} 1597 1598MODULE_DESCRIPTION("TCM loopback virtual Linux/SCSI fabric module"); 1599MODULE_AUTHOR("Nicholas A. Bellinger <nab@risingtidesystems.com>"); 1600MODULE_LICENSE("GPL"); 1601module_init(tcm_loop_fabric_init); 1602module_exit(tcm_loop_fabric_exit); 1603