Deleted Added
full compact
ctl.c (268556) ctl.c (268673)
1/*-
2 * Copyright (c) 2003-2009 Silicon Graphics International Corp.
3 * Copyright (c) 2012 The FreeBSD Foundation
4 * All rights reserved.
5 *
6 * Portions of this software were developed by Edward Tomasz Napierala
7 * under sponsorship from the FreeBSD Foundation.
8 *

--- 28 unchanged lines hidden (view full) ---

37 * CAM Target Layer, a SCSI device emulation subsystem.
38 *
39 * Author: Ken Merry <ken@FreeBSD.org>
40 */
41
42#define _CTL_C
43
44#include <sys/cdefs.h>
1/*-
2 * Copyright (c) 2003-2009 Silicon Graphics International Corp.
3 * Copyright (c) 2012 The FreeBSD Foundation
4 * All rights reserved.
5 *
6 * Portions of this software were developed by Edward Tomasz Napierala
7 * under sponsorship from the FreeBSD Foundation.
8 *

--- 28 unchanged lines hidden (view full) ---

37 * CAM Target Layer, a SCSI device emulation subsystem.
38 *
39 * Author: Ken Merry <ken@FreeBSD.org>
40 */
41
42#define _CTL_C
43
44#include <sys/cdefs.h>
45__FBSDID("$FreeBSD: stable/10/sys/cam/ctl/ctl.c 268556 2014-07-12 04:34:39Z mav $");
45__FBSDID("$FreeBSD: stable/10/sys/cam/ctl/ctl.c 268673 2014-07-15 16:49:35Z mav $");
46
47#include <sys/param.h>
48#include <sys/systm.h>
49#include <sys/kernel.h>
50#include <sys/types.h>
51#include <sys/kthread.h>
52#include <sys/bio.h>
53#include <sys/fcntl.h>

--- 24 unchanged lines hidden (view full) ---

78#include <cam/ctl/ctl_private.h>
79#include <cam/ctl/ctl_debug.h>
80#include <cam/ctl/ctl_scsi_all.h>
81#include <cam/ctl/ctl_error.h>
82
83struct ctl_softc *control_softc = NULL;
84
85/*
46
47#include <sys/param.h>
48#include <sys/systm.h>
49#include <sys/kernel.h>
50#include <sys/types.h>
51#include <sys/kthread.h>
52#include <sys/bio.h>
53#include <sys/fcntl.h>

--- 24 unchanged lines hidden (view full) ---

78#include <cam/ctl/ctl_private.h>
79#include <cam/ctl/ctl_debug.h>
80#include <cam/ctl/ctl_scsi_all.h>
81#include <cam/ctl/ctl_error.h>
82
83struct ctl_softc *control_softc = NULL;
84
85/*
86 * Use the serial number and device ID provided by the backend, rather than
87 * making up our own.
88 */
89#define CTL_USE_BACKEND_SN
90
91/*
92 * Size and alignment macros needed for Copan-specific HA hardware. These
93 * can go away when the HA code is re-written, and uses busdma for any
94 * hardware.
95 */
96#define CTL_ALIGN_8B(target, source, type) \
97 if (((uint32_t)source & 0x7) != 0) \
98 target = (type)(source + (0x8 - ((uint32_t)source & 0x7)));\
99 else \

--- 9375 unchanged lines hidden (view full) ---

9475 return (CTL_RETVAL_COMPLETE);
9476}
9477
9478static int
9479ctl_inquiry_evpd_serial(struct ctl_scsiio *ctsio, int alloc_len)
9480{
9481 struct scsi_vpd_unit_serial_number *sn_ptr;
9482 struct ctl_lun *lun;
86 * Size and alignment macros needed for Copan-specific HA hardware. These
87 * can go away when the HA code is re-written, and uses busdma for any
88 * hardware.
89 */
90#define CTL_ALIGN_8B(target, source, type) \
91 if (((uint32_t)source & 0x7) != 0) \
92 target = (type)(source + (0x8 - ((uint32_t)source & 0x7)));\
93 else \

--- 9375 unchanged lines hidden (view full) ---

9469 return (CTL_RETVAL_COMPLETE);
9470}
9471
9472static int
9473ctl_inquiry_evpd_serial(struct ctl_scsiio *ctsio, int alloc_len)
9474{
9475 struct scsi_vpd_unit_serial_number *sn_ptr;
9476 struct ctl_lun *lun;
9483#ifndef CTL_USE_BACKEND_SN
9484 char tmpstr[32];
9485#endif
9486
9487 lun = (struct ctl_lun *)ctsio->io_hdr.ctl_private[CTL_PRIV_LUN].ptr;
9488
9489 ctsio->kern_data_ptr = malloc(sizeof(*sn_ptr), M_CTL, M_WAITOK | M_ZERO);
9490 sn_ptr = (struct scsi_vpd_unit_serial_number *)ctsio->kern_data_ptr;
9491 ctsio->kern_sg_entries = 0;
9492
9493 if (sizeof(*sn_ptr) < alloc_len) {

--- 17 unchanged lines hidden (view full) ---

9511 if (lun != NULL)
9512 sn_ptr->device = (SID_QUAL_LU_CONNECTED << 5) |
9513 lun->be_lun->lun_type;
9514 else
9515 sn_ptr->device = (SID_QUAL_LU_OFFLINE << 5) | T_DIRECT;
9516
9517 sn_ptr->page_code = SVPD_UNIT_SERIAL_NUMBER;
9518 sn_ptr->length = ctl_min(sizeof(*sn_ptr) - 4, CTL_SN_LEN);
9477
9478 lun = (struct ctl_lun *)ctsio->io_hdr.ctl_private[CTL_PRIV_LUN].ptr;
9479
9480 ctsio->kern_data_ptr = malloc(sizeof(*sn_ptr), M_CTL, M_WAITOK | M_ZERO);
9481 sn_ptr = (struct scsi_vpd_unit_serial_number *)ctsio->kern_data_ptr;
9482 ctsio->kern_sg_entries = 0;
9483
9484 if (sizeof(*sn_ptr) < alloc_len) {

--- 17 unchanged lines hidden (view full) ---

9502 if (lun != NULL)
9503 sn_ptr->device = (SID_QUAL_LU_CONNECTED << 5) |
9504 lun->be_lun->lun_type;
9505 else
9506 sn_ptr->device = (SID_QUAL_LU_OFFLINE << 5) | T_DIRECT;
9507
9508 sn_ptr->page_code = SVPD_UNIT_SERIAL_NUMBER;
9509 sn_ptr->length = ctl_min(sizeof(*sn_ptr) - 4, CTL_SN_LEN);
9519#ifdef CTL_USE_BACKEND_SN
9520 /*
9521 * If we don't have a LUN, we just leave the serial number as
9522 * all spaces.
9523 */
9524 memset(sn_ptr->serial_num, 0x20, sizeof(sn_ptr->serial_num));
9525 if (lun != NULL) {
9526 strncpy((char *)sn_ptr->serial_num,
9527 (char *)lun->be_lun->serial_num, CTL_SN_LEN);
9528 }
9510 /*
9511 * If we don't have a LUN, we just leave the serial number as
9512 * all spaces.
9513 */
9514 memset(sn_ptr->serial_num, 0x20, sizeof(sn_ptr->serial_num));
9515 if (lun != NULL) {
9516 strncpy((char *)sn_ptr->serial_num,
9517 (char *)lun->be_lun->serial_num, CTL_SN_LEN);
9518 }
9529#else
9530 /*
9531 * Note that we're using a non-unique serial number here,
9532 */
9533 snprintf(tmpstr, sizeof(tmpstr), "MYSERIALNUMIS000");
9534 memset(sn_ptr->serial_num, 0x20, sizeof(sn_ptr->serial_num));
9535 strncpy(sn_ptr->serial_num, tmpstr, ctl_min(CTL_SN_LEN,
9536 ctl_min(sizeof(tmpstr), sizeof(*sn_ptr) - 4)));
9537#endif
9538 ctsio->scsi_status = SCSI_STATUS_OK;
9539
9540 ctsio->io_hdr.flags |= CTL_FLAG_ALLOCATED;
9541 ctsio->be_move_done = ctl_config_move_done;
9542 ctl_datamove((union ctl_io *)ctsio);
9543
9544 return (CTL_RETVAL_COMPLETE);
9545}

--- 5 unchanged lines hidden (view full) ---

9551 struct scsi_vpd_device_id *devid_ptr;
9552 struct scsi_vpd_id_descriptor *desc, *desc1;
9553 struct scsi_vpd_id_descriptor *desc2, *desc3; /* for types 4h and 5h */
9554 struct scsi_vpd_id_t10 *t10id;
9555 struct ctl_softc *ctl_softc;
9556 struct ctl_lun *lun;
9557 struct ctl_frontend *fe;
9558 char *val;
9519 ctsio->scsi_status = SCSI_STATUS_OK;
9520
9521 ctsio->io_hdr.flags |= CTL_FLAG_ALLOCATED;
9522 ctsio->be_move_done = ctl_config_move_done;
9523 ctl_datamove((union ctl_io *)ctsio);
9524
9525 return (CTL_RETVAL_COMPLETE);
9526}

--- 5 unchanged lines hidden (view full) ---

9532 struct scsi_vpd_device_id *devid_ptr;
9533 struct scsi_vpd_id_descriptor *desc, *desc1;
9534 struct scsi_vpd_id_descriptor *desc2, *desc3; /* for types 4h and 5h */
9535 struct scsi_vpd_id_t10 *t10id;
9536 struct ctl_softc *ctl_softc;
9537 struct ctl_lun *lun;
9538 struct ctl_frontend *fe;
9539 char *val;
9559#ifndef CTL_USE_BACKEND_SN
9560 char tmpstr[32];
9561#endif /* CTL_USE_BACKEND_SN */
9562 int devid_len;
9540 int data_len, devid_len;
9563
9564 ctl_softc = control_softc;
9565
9566 fe = ctl_softc->ctl_ports[ctl_port_idx(ctsio->io_hdr.nexus.targ_port)];
9567
9568 if (fe->devid != NULL)
9569 return ((fe->devid)(ctsio, alloc_len));
9570
9571 lun = (struct ctl_lun *)ctsio->io_hdr.ctl_private[CTL_PRIV_LUN].ptr;
9572
9541
9542 ctl_softc = control_softc;
9543
9544 fe = ctl_softc->ctl_ports[ctl_port_idx(ctsio->io_hdr.nexus.targ_port)];
9545
9546 if (fe->devid != NULL)
9547 return ((fe->devid)(ctsio, alloc_len));
9548
9549 lun = (struct ctl_lun *)ctsio->io_hdr.ctl_private[CTL_PRIV_LUN].ptr;
9550
9573 devid_len = sizeof(struct scsi_vpd_device_id) +
9551 if (lun == NULL) {
9552 devid_len = CTL_DEVID_MIN_LEN;
9553 } else {
9554 devid_len = max(CTL_DEVID_MIN_LEN,
9555 strnlen(lun->be_lun->device_id, CTL_DEVID_LEN));
9556 }
9557
9558 data_len = sizeof(struct scsi_vpd_device_id) +
9574 sizeof(struct scsi_vpd_id_descriptor) +
9559 sizeof(struct scsi_vpd_id_descriptor) +
9575 sizeof(struct scsi_vpd_id_t10) + CTL_DEVID_LEN +
9560 sizeof(struct scsi_vpd_id_t10) + devid_len +
9576 sizeof(struct scsi_vpd_id_descriptor) + CTL_WWPN_LEN +
9577 sizeof(struct scsi_vpd_id_descriptor) +
9578 sizeof(struct scsi_vpd_id_rel_trgt_port_id) +
9579 sizeof(struct scsi_vpd_id_descriptor) +
9580 sizeof(struct scsi_vpd_id_trgt_port_grp_id);
9581
9561 sizeof(struct scsi_vpd_id_descriptor) + CTL_WWPN_LEN +
9562 sizeof(struct scsi_vpd_id_descriptor) +
9563 sizeof(struct scsi_vpd_id_rel_trgt_port_id) +
9564 sizeof(struct scsi_vpd_id_descriptor) +
9565 sizeof(struct scsi_vpd_id_trgt_port_grp_id);
9566
9582 ctsio->kern_data_ptr = malloc(devid_len, M_CTL, M_WAITOK | M_ZERO);
9567 ctsio->kern_data_ptr = malloc(data_len, M_CTL, M_WAITOK | M_ZERO);
9583 devid_ptr = (struct scsi_vpd_device_id *)ctsio->kern_data_ptr;
9584 ctsio->kern_sg_entries = 0;
9585
9568 devid_ptr = (struct scsi_vpd_device_id *)ctsio->kern_data_ptr;
9569 ctsio->kern_sg_entries = 0;
9570
9586 if (devid_len < alloc_len) {
9587 ctsio->residual = alloc_len - devid_len;
9588 ctsio->kern_data_len = devid_len;
9589 ctsio->kern_total_len = devid_len;
9571 if (data_len < alloc_len) {
9572 ctsio->residual = alloc_len - data_len;
9573 ctsio->kern_data_len = data_len;
9574 ctsio->kern_total_len = data_len;
9590 } else {
9591 ctsio->residual = 0;
9592 ctsio->kern_data_len = alloc_len;
9593 ctsio->kern_total_len = alloc_len;
9594 }
9595 ctsio->kern_data_resid = 0;
9596 ctsio->kern_rel_offset = 0;
9597 ctsio->kern_sg_entries = 0;
9598
9599 desc = (struct scsi_vpd_id_descriptor *)devid_ptr->desc_list;
9600 t10id = (struct scsi_vpd_id_t10 *)&desc->identifier[0];
9601 desc1 = (struct scsi_vpd_id_descriptor *)(&desc->identifier[0] +
9575 } else {
9576 ctsio->residual = 0;
9577 ctsio->kern_data_len = alloc_len;
9578 ctsio->kern_total_len = alloc_len;
9579 }
9580 ctsio->kern_data_resid = 0;
9581 ctsio->kern_rel_offset = 0;
9582 ctsio->kern_sg_entries = 0;
9583
9584 desc = (struct scsi_vpd_id_descriptor *)devid_ptr->desc_list;
9585 t10id = (struct scsi_vpd_id_t10 *)&desc->identifier[0];
9586 desc1 = (struct scsi_vpd_id_descriptor *)(&desc->identifier[0] +
9602 sizeof(struct scsi_vpd_id_t10) + CTL_DEVID_LEN);
9587 sizeof(struct scsi_vpd_id_t10) + devid_len);
9603 desc2 = (struct scsi_vpd_id_descriptor *)(&desc1->identifier[0] +
9604 CTL_WWPN_LEN);
9605 desc3 = (struct scsi_vpd_id_descriptor *)(&desc2->identifier[0] +
9606 sizeof(struct scsi_vpd_id_rel_trgt_port_id));
9607
9608 /*
9609 * The control device is always connected. The disk device, on the
9610 * other hand, may not be online all the time.
9611 */
9612 if (lun != NULL)
9613 devid_ptr->device = (SID_QUAL_LU_CONNECTED << 5) |
9614 lun->be_lun->lun_type;
9615 else
9616 devid_ptr->device = (SID_QUAL_LU_OFFLINE << 5) | T_DIRECT;
9617
9618 devid_ptr->page_code = SVPD_DEVICE_ID;
9619
9588 desc2 = (struct scsi_vpd_id_descriptor *)(&desc1->identifier[0] +
9589 CTL_WWPN_LEN);
9590 desc3 = (struct scsi_vpd_id_descriptor *)(&desc2->identifier[0] +
9591 sizeof(struct scsi_vpd_id_rel_trgt_port_id));
9592
9593 /*
9594 * The control device is always connected. The disk device, on the
9595 * other hand, may not be online all the time.
9596 */
9597 if (lun != NULL)
9598 devid_ptr->device = (SID_QUAL_LU_CONNECTED << 5) |
9599 lun->be_lun->lun_type;
9600 else
9601 devid_ptr->device = (SID_QUAL_LU_OFFLINE << 5) | T_DIRECT;
9602
9603 devid_ptr->page_code = SVPD_DEVICE_ID;
9604
9620 scsi_ulto2b(devid_len - 4, devid_ptr->length);
9605 scsi_ulto2b(data_len - 4, devid_ptr->length);
9621
9622 /*
9623 * For Fibre channel,
9624 */
9625 if (fe->port_type == CTL_PORT_FC)
9626 {
9627 desc->proto_codeset = (SCSI_PROTO_FC << 4) |
9628 SVPD_ID_CODESET_ASCII;

--- 9 unchanged lines hidden (view full) ---

9638 }
9639 desc2->proto_codeset = desc3->proto_codeset = desc1->proto_codeset;
9640
9641 /*
9642 * We're using a LUN association here. i.e., this device ID is a
9643 * per-LUN identifier.
9644 */
9645 desc->id_type = SVPD_ID_PIV | SVPD_ID_ASSOC_LUN | SVPD_ID_TYPE_T10;
9606
9607 /*
9608 * For Fibre channel,
9609 */
9610 if (fe->port_type == CTL_PORT_FC)
9611 {
9612 desc->proto_codeset = (SCSI_PROTO_FC << 4) |
9613 SVPD_ID_CODESET_ASCII;

--- 9 unchanged lines hidden (view full) ---

9623 }
9624 desc2->proto_codeset = desc3->proto_codeset = desc1->proto_codeset;
9625
9626 /*
9627 * We're using a LUN association here. i.e., this device ID is a
9628 * per-LUN identifier.
9629 */
9630 desc->id_type = SVPD_ID_PIV | SVPD_ID_ASSOC_LUN | SVPD_ID_TYPE_T10;
9646 desc->length = sizeof(*t10id) + CTL_DEVID_LEN;
9631 desc->length = sizeof(*t10id) + devid_len;
9647 if (lun == NULL || (val = ctl_get_opt(lun->be_lun, "vendor")) == NULL) {
9648 strncpy((char *)t10id->vendor, CTL_VENDOR, sizeof(t10id->vendor));
9649 } else {
9650 memset(t10id->vendor, ' ', sizeof(t10id->vendor));
9651 strncpy(t10id->vendor, val,
9652 min(sizeof(t10id->vendor), strlen(val)));
9653 }
9654

--- 40 unchanged lines hidden (view full) ---

9695 desc3->id_type = SVPD_ID_PIV | SVPD_ID_ASSOC_PORT
9696 | SVPD_ID_TYPE_TPORTGRP;
9697 desc3->length = 4;
9698 if (ctsio->io_hdr.nexus.targ_port < CTL_MAX_PORTS || ctl_is_single)
9699 desc3->identifier[3] = 1;
9700 else
9701 desc3->identifier[3] = 2;
9702
9632 if (lun == NULL || (val = ctl_get_opt(lun->be_lun, "vendor")) == NULL) {
9633 strncpy((char *)t10id->vendor, CTL_VENDOR, sizeof(t10id->vendor));
9634 } else {
9635 memset(t10id->vendor, ' ', sizeof(t10id->vendor));
9636 strncpy(t10id->vendor, val,
9637 min(sizeof(t10id->vendor), strlen(val)));
9638 }
9639

--- 40 unchanged lines hidden (view full) ---

9680 desc3->id_type = SVPD_ID_PIV | SVPD_ID_ASSOC_PORT
9681 | SVPD_ID_TYPE_TPORTGRP;
9682 desc3->length = 4;
9683 if (ctsio->io_hdr.nexus.targ_port < CTL_MAX_PORTS || ctl_is_single)
9684 desc3->identifier[3] = 1;
9685 else
9686 desc3->identifier[3] = 2;
9687
9703#ifdef CTL_USE_BACKEND_SN
9704 /*
9705 * If we've actually got a backend, copy the device id from the
9706 * per-LUN data. Otherwise, set it to all spaces.
9707 */
9708 if (lun != NULL) {
9709 /*
9710 * Copy the backend's LUN ID.
9711 */
9712 strncpy((char *)t10id->vendor_spec_id,
9688 /*
9689 * If we've actually got a backend, copy the device id from the
9690 * per-LUN data. Otherwise, set it to all spaces.
9691 */
9692 if (lun != NULL) {
9693 /*
9694 * Copy the backend's LUN ID.
9695 */
9696 strncpy((char *)t10id->vendor_spec_id,
9713 (char *)lun->be_lun->device_id, CTL_DEVID_LEN);
9697 (char *)lun->be_lun->device_id, devid_len);
9714 } else {
9715 /*
9716 * No backend, set this to spaces.
9717 */
9698 } else {
9699 /*
9700 * No backend, set this to spaces.
9701 */
9718 memset(t10id->vendor_spec_id, 0x20, CTL_DEVID_LEN);
9702 memset(t10id->vendor_spec_id, 0x20, devid_len);
9719 }
9703 }
9720#else
9721 snprintf(tmpstr, sizeof(tmpstr), "MYDEVICEIDIS%4d",
9722 (lun != NULL) ? (int)lun->lun : 0);
9723 strncpy(t10id->vendor_spec_id, tmpstr, ctl_min(CTL_DEVID_LEN,
9724 sizeof(tmpstr)));
9725#endif
9726
9727 ctsio->scsi_status = SCSI_STATUS_OK;
9728
9729 ctsio->io_hdr.flags |= CTL_FLAG_ALLOCATED;
9730 ctsio->be_move_done = ctl_config_move_done;
9731 ctl_datamove((union ctl_io *)ctsio);
9732
9733 return (CTL_RETVAL_COMPLETE);

--- 3846 unchanged lines hidden ---
9704
9705 ctsio->scsi_status = SCSI_STATUS_OK;
9706
9707 ctsio->io_hdr.flags |= CTL_FLAG_ALLOCATED;
9708 ctsio->be_move_done = ctl_config_move_done;
9709 ctl_datamove((union ctl_io *)ctsio);
9710
9711 return (CTL_RETVAL_COMPLETE);

--- 3846 unchanged lines hidden ---