1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 * Copyright (c) 2017, Joyent, Inc. 25 */ 26 27 #ifndef _SYS_SCSI_SCSI_ADDRESS_H 28 #define _SYS_SCSI_SCSI_ADDRESS_H 29 30 #include <sys/scsi/scsi_types.h> 31 32 #ifdef __cplusplus 33 extern "C" { 34 #endif 35 36 /* 37 * SCSI address definition. 38 * 39 * A scsi_address(9S) structure stores the host adapter routing and 40 * scsi_device(9S) unit-address routing information necessary to reference 41 * a specific SCSI target device logical unit function. 42 * 43 * Host adapter routing information is stored in the scsi_hba_tran(9S) 44 * structure, pointed to by the scsi_address(9S) 'a_hba_tran' field. 45 * 46 * The scsi_device(9S) unit-address routing information (i.e. SCSA's 47 * representation of leaf disk/tape driver's "@unit-address" portion of 48 * a /devices path) is maintained in three different forms: 49 * 50 * SCSI_HBA_ADDR_SPI: In SCSI_HBA_ADDR_SPI mode (default), the SCSA 51 * framework, during initialization, places unit-address property 52 * information, converted to numeric form, directly into the 53 * 'a_target' and 'a_lun' fields of the scsi_address(9S) structure 54 * (embedded in the scsi_device(9S) structure). To maintain 55 * per-scsi_device(9S) state, host adapter drivers often use 56 * 'a_target' and 'a_lun' to index into a large fixed array 57 * (limited by the drivers idea of maximum supported target and 58 * lun). 59 * 60 * NOTE: a_sublun is reserved for internal use only and has never 61 * been part of DDI scsi_address(9S). 62 * 63 * SCSI_HBA_ADDR_COMPLEX: The host adapter driver will maintain 64 * per-unit-address/per-scsi_device(9S) HBA private state by using 65 * scsi_device_hba_private_set(9F) during tran_tgt_init(9E) (using 66 * property interfaces to obtain/convert unit-address information into 67 * a host adapter private form). In SCSI_HBA_ADDR_COMPLEX mode, the SCSA 68 * framework, prior to tran_tgt_init(9E), places a pointer to the 69 * scsi_device(9S) in the 'a.a_sd' scsi_address(9S) field, and uses 70 * 'sd_hba_private' to store per-scsi_device hba private data. 71 * 72 * SCSI_HBA_TRAN_CLONE: SCSI_HBA_TRAN_CLONE is an older method for 73 * supporting devices with non-SPI unit-address. It is still 74 * supported, but its use is discouraged. From a unit-address 75 * perspective, operation is similar to SCSI_HBA_ADDR_COMPLEX, but 76 * per-scsi_device(9S) state is supported via 'cloning' of the 77 * scsi_hba_tran(9S) structure (to provide a per-scsi_device(9S) 78 * version of 'tran_tgt_private'/'tran_sd' accessible via 79 * 'a_hba_tran'). 80 * 81 * NOTE: Compatible evolution of SCSA is constrained by the fact that the 82 * scsi_address(9S) structure is embedded at the base of the scsi_device(9S) 83 * structure, and is structure copied into the base of each allocated 84 * scsi_pkt(9S) structure. 85 * 86 * In general, device unit-address information is used exclusively by 87 * the host adapter driver (the exception being target drivers 88 * communicating with SCSI Parallel Interconnect (SPI) SCSI-1 devices 89 * that embed SCSI logical unit addressing in the CDB). Target drivers 90 * which need to communicate with SPI SCSI-1 devices that embed logical 91 * unit addresses in the CDB must obtain target and logical unit 92 * addresses from the device's properties (SCSI_ADDR_PROP_TARGET and 93 * SCSI_ADDR_PROP_LUN). 94 */ 95 struct scsi_address { 96 struct scsi_hba_tran *a_hba_tran; /* Transport vector */ 97 union { 98 struct { /* SPI: */ 99 ushort_t a_target; /* ua target */ 100 uchar_t a_lun; /* ua lun on target */ 101 uchar_t _a_sublun; /* (private) */ 102 } spi; 103 struct scsi_device *a_sd; /* COMPLEX: (private) */ 104 } a; /* device unit-adddress info */ 105 }; 106 #define a_target a.spi.a_target 107 #define a_lun a.spi.a_lun 108 #define a_sublun a.spi._a_sublun 109 110 /* Device unit-address property names */ 111 #define SCSI_ADDR_PROP_TARGET "target" /* int */ 112 #define SCSI_ADDR_PROP_LUN "lun" /* int */ 113 114 #define SCSI_ADDR_PROP_TARGET_PORT "target-port" /* string */ 115 #define SCSI_ADDR_PROP_LUN64 "lun64" /* int64 */ 116 #define SCSI_ADDR_PROP_SFUNC "sfunc" /* int */ 117 118 #define SCSI_ADDR_PROP_IPORTUA "scsi-iport" /* string */ 119 120 #define SCSI_ADDR_PROP_SATA_PHY "sata-phy" /* int */ 121 122 /* 123 * Addressing property names, values are in string form compatible 124 * with the SCSI_ADDR_PROP_TARGET_PORT part of the related 125 * IEEE-1275 OpenFirmware binding unit-address string. 126 */ 127 #define SCSI_ADDR_PROP_INITIATOR_PORT "initiator-port" 128 #define SCSI_ADDR_PROP_ATTACHED_PORT "attached-port" 129 #define SCSI_ADDR_PROP_BRIDGE_PORT "bridge-port" 130 131 /* 132 * Normalized representation of a scsi_lun (with SCSI-2 lun positioned 133 * for compatibility). 134 */ 135 typedef uint64_t scsi_lun64_t; 136 #define PRIlun64 PRIx64 137 #ifdef _LP64 138 #define SCSI_LUN64_ILLEGAL (-1L) 139 #else /* _LP64 */ 140 #define SCSI_LUN64_ILLEGAL (-1LL) 141 #endif /* _LP64 */ 142 143 /* Structure of a 64-bit SCSI LUN per SCSI standard */ 144 typedef struct scsi_lun { 145 uchar_t sl_lun1_msb; /* format */ 146 uchar_t sl_lun1_lsb; /* first level */ 147 uchar_t sl_lun2_msb; 148 uchar_t sl_lun2_lsb; /* second level */ 149 uchar_t sl_lun3_msb; 150 uchar_t sl_lun3_lsb; /* third level */ 151 uchar_t sl_lun4_msb; 152 uchar_t sl_lun4_lsb; /* fourth level */ 153 } scsi_lun_t; 154 155 /* SCSI standard defined lun addressing methods (in sl_lunX_msb) */ 156 #define SCSI_LUN_AM_MASK 0xC0 /* Address Method Mask */ 157 #define SCSI_LUN_AM_PDEV 0x00 /* Peripheral device AM */ 158 #define SCSI_LUN_AM_FLAT 0x40 /* Flat space AM */ 159 #define SCSI_LUN_AM_LUN 0x80 /* Logical unit AM */ 160 #define SCSI_LUN_AM_EFLAT 0xC0 /* Extended flat space AM */ 161 #define SCSI_LUN_AM_ELUN 0xC0 /* Extended logical unit AM */ 162 163 #ifdef _KERNEL 164 /* SCSI LUN conversion between SCSI_ADDR_PROP_LUN64 and SCSI standard forms */ 165 scsi_lun64_t scsi_lun_to_lun64(scsi_lun_t lun); 166 scsi_lun_t scsi_lun64_to_lun(scsi_lun64_t lun64); 167 168 /* SCSI WWN conversion (property values should be in unit_address form) */ 169 int scsi_wwnstr_to_wwn(const char *wwnstr, uint64_t *wwnp); 170 char *scsi_wwn_to_wwnstr(uint64_t wwn, 171 int unit_address_form, char *wwnstr); 172 void scsi_wwnstr_hexcase(char *wwnstr, int lower_case); 173 const char *scsi_wwnstr_skip_ua_prefix(const char *wwnstr); 174 void scsi_free_wwnstr(char *wwnstr); 175 176 /* 177 * Buffer lengths for SCSI strings. SCSI_WWN_STRLEN is the length of a WWN 178 * that's not in unit-address form. SCSI_WWN_UA_STRLEN includes the 179 * unit-address. SCSI_WWN_BUFLEN provides a buffer that's large enough for all 180 * of these. 181 */ 182 #define SCSI_WWN_STRLEN 16 183 #define SCSI_WWN_UA_STRLEN 17 184 #define SCSI_WWN_BUFLEN SCSI_MAXNAMELEN 185 186 #endif /* _KERNEL */ 187 188 #ifdef __cplusplus 189 } 190 #endif 191 192 #endif /* _SYS_SCSI_SCSI_ADDRESS_H */ 193