1*4198Seschrock /* 2*4198Seschrock * CDDL HEADER START 3*4198Seschrock * 4*4198Seschrock * The contents of this file are subject to the terms of the 5*4198Seschrock * Common Development and Distribution License (the "License"). 6*4198Seschrock * You may not use this file except in compliance with the License. 7*4198Seschrock * 8*4198Seschrock * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9*4198Seschrock * or http://www.opensolaris.org/os/licensing. 10*4198Seschrock * See the License for the specific language governing permissions 11*4198Seschrock * and limitations under the License. 12*4198Seschrock * 13*4198Seschrock * When distributing Covered Code, include this CDDL HEADER in each 14*4198Seschrock * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15*4198Seschrock * If applicable, add the following below this CDDL HEADER, with the 16*4198Seschrock * fields enclosed by brackets "[]" replaced with your own identifying 17*4198Seschrock * information: Portions Copyright [yyyy] [name of copyright owner] 18*4198Seschrock * 19*4198Seschrock * CDDL HEADER END 20*4198Seschrock */ 21*4198Seschrock /* 22*4198Seschrock * Copyright 2007 Sun Microsystems, Inc. All rights reserved. 23*4198Seschrock * Use is subject to license terms. 24*4198Seschrock */ 25*4198Seschrock 26*4198Seschrock #ifndef _DS_SCSI_H 27*4198Seschrock #define _DS_SCSI_H 28*4198Seschrock 29*4198Seschrock #pragma ident "%Z%%M% %I% %E% SMI" 30*4198Seschrock 31*4198Seschrock #include <sys/types.h> 32*4198Seschrock #include <sys/byteorder.h> 33*4198Seschrock #include <sys/scsi/scsi.h> 34*4198Seschrock 35*4198Seschrock #include "ds_impl.h" 36*4198Seschrock 37*4198Seschrock #ifdef __cplusplus 38*4198Seschrock extern "C" { 39*4198Seschrock #endif 40*4198Seschrock 41*4198Seschrock #if !defined(_BIT_FIELDS_LTOH) && !defined(_BIT_FIELDS_HTOL) 42*4198Seschrock #error One of _BIT_FIELDS_LTOH or _BIT_FIELDS_HTOL must be defined 43*4198Seschrock #endif 44*4198Seschrock 45*4198Seschrock /* 46*4198Seschrock * Log page structures 47*4198Seschrock */ 48*4198Seschrock #pragma pack(1) 49*4198Seschrock 50*4198Seschrock typedef struct scsi_log_header { 51*4198Seschrock #if defined(_BIT_FIELDS_LTOH) 52*4198Seschrock uint8_t lh_code : 6, 53*4198Seschrock __reserved : 2; 54*4198Seschrock #else 55*4198Seschrock uint8_t __reserved : 2, 56*4198Seschrock lh_code : 6; 57*4198Seschrock #endif 58*4198Seschrock uint8_t __reserved2; 59*4198Seschrock uint16_t lh_length; 60*4198Seschrock } scsi_log_header_t; 61*4198Seschrock 62*4198Seschrock typedef struct scsi_log_parameter_header { 63*4198Seschrock uint16_t lph_param; 64*4198Seschrock #if defined(_BIT_FIELDS_LTOH) 65*4198Seschrock uint8_t lph_lp : 1, 66*4198Seschrock lph_lbin : 1, 67*4198Seschrock lph_tmc : 2, 68*4198Seschrock lph_etc : 1, 69*4198Seschrock lph_tsd : 1, 70*4198Seschrock lph_ds : 1, 71*4198Seschrock lph_du : 1; 72*4198Seschrock #else 73*4198Seschrock uint8_t lph_du : 1, 74*4198Seschrock lph_ds : 1, 75*4198Seschrock lph_tsd : 1, 76*4198Seschrock lph_etc : 1, 77*4198Seschrock lph_tmc : 2, 78*4198Seschrock lph_lbin : 1, 79*4198Seschrock lph_lp : 1; 80*4198Seschrock #endif 81*4198Seschrock uint8_t lph_length; 82*4198Seschrock } scsi_log_parameter_header_t; 83*4198Seschrock 84*4198Seschrock typedef struct scsi_supported_log_pages { 85*4198Seschrock scsi_log_header_t slp_hdr; 86*4198Seschrock uchar_t slp_pages[1]; 87*4198Seschrock } scsi_supported_log_pages_t; 88*4198Seschrock 89*4198Seschrock typedef struct scsi_ie_log_param { 90*4198Seschrock scsi_log_parameter_header_t ie_hdr; 91*4198Seschrock uchar_t ie_asc; 92*4198Seschrock uchar_t ie_ascq; 93*4198Seschrock } scsi_ie_log_param_t; 94*4198Seschrock 95*4198Seschrock /* 96*4198Seschrock * The SCSI-3 SPC document states that IE log page (0x2F) parameter 0 97*4198Seschrock * must have a length of at least 4 (including the length byte). 98*4198Seschrock */ 99*4198Seschrock #define LOGPARAM_IE_MIN_LEN 2 /* the asc and ascq fields */ 100*4198Seschrock 101*4198Seschrock #define INVALID_TEMPERATURE 0xff 102*4198Seschrock 103*4198Seschrock #define LOGPARAM_IE 0x0000 104*4198Seschrock 105*4198Seschrock typedef struct scsi_temp_log_param { 106*4198Seschrock scsi_log_parameter_header_t t_hdr; 107*4198Seschrock uchar_t __reserved; 108*4198Seschrock uchar_t t_temp; 109*4198Seschrock } scsi_temp_log_param_t; 110*4198Seschrock 111*4198Seschrock typedef struct scsi_selftest_log_param { 112*4198Seschrock scsi_log_parameter_header_t st_hdr; 113*4198Seschrock #if defined(_BIT_FIELDS_LTOH) 114*4198Seschrock uint8_t st_results : 4, 115*4198Seschrock __reserved1 : 1, 116*4198Seschrock st_testcode : 3; 117*4198Seschrock #else 118*4198Seschrock uint8_t st_testcode : 3, 119*4198Seschrock __reserved1 : 1, 120*4198Seschrock st_results : 4; 121*4198Seschrock #endif 122*4198Seschrock uint8_t st_number; 123*4198Seschrock uint16_t st_timestamp; 124*4198Seschrock uint64_t st_lba; 125*4198Seschrock #if defined(_BIT_FIELDS_LTOH) 126*4198Seschrock uint8_t st_sensekey : 4, 127*4198Seschrock __reserved2 : 4; 128*4198Seschrock #else 129*4198Seschrock uint8_t __reserved2 : 4, 130*4198Seschrock st_sensekey : 4; 131*4198Seschrock #endif 132*4198Seschrock uint8_t st_asc; 133*4198Seschrock uint8_t st_ascq; 134*4198Seschrock uint8_t st_vendor; 135*4198Seschrock } scsi_selftest_log_param_t; 136*4198Seschrock 137*4198Seschrock /* The results field of the self-test log parameter */ 138*4198Seschrock #define SELFTEST_OK 0x0 139*4198Seschrock #define SELFTEST_ABORT_REQUEST 0x1 140*4198Seschrock #define SELFTEST_ABORT_OTHER 0x2 141*4198Seschrock #define SELFTEST_FAILURE_INCOMPLETE 0x3 142*4198Seschrock #define SELFTEST_FAILURE_SEG_UNKNOWN 0x4 143*4198Seschrock #define SELFTEST_FAILURE_SEG_FIRST 0x5 144*4198Seschrock #define SELFTEST_FAILURE_SEG_SECOND 0x6 145*4198Seschrock #define SELFTEST_FAILURE_SEG_OTHER 0x7 146*4198Seschrock #define SELFTEST_INPROGRESS 0xf 147*4198Seschrock 148*4198Seschrock #define SELFTEST_COMPLETE(code) \ 149*4198Seschrock ((code) == SELFTEST_OK || \ 150*4198Seschrock ((code) >= SELFTEST_FAILURE_INCOMPLETE && \ 151*4198Seschrock ((code) <= SELFTEST_FAILURE_SEG_OTHER))) 152*4198Seschrock 153*4198Seschrock #define LOGPARAM_TEMP_CURTEMP 0x0000 154*4198Seschrock #define LOGPARAM_TEMP_REFTEMP 0x0001 155*4198Seschrock 156*4198Seschrock #define LOGPARAM_TEMP_LEN \ 157*4198Seschrock (sizeof (scsi_temp_log_param_t) - \ 158*4198Seschrock sizeof (scsi_log_parameter_header_t)) 159*4198Seschrock 160*4198Seschrock /* 161*4198Seschrock * Mode sense/select page header information 162*4198Seschrock */ 163*4198Seschrock typedef struct scsi_ms_header { 164*4198Seschrock struct mode_header ms_header; 165*4198Seschrock struct block_descriptor ms_descriptor; 166*4198Seschrock } scsi_ms_header_t; 167*4198Seschrock 168*4198Seschrock typedef struct scsi_ms_header_g1 { 169*4198Seschrock struct mode_header_g1 ms_header; 170*4198Seschrock struct block_descriptor ms_descriptor; 171*4198Seschrock } scsi_ms_header_g1_t; 172*4198Seschrock 173*4198Seschrock typedef struct scsi_ms_hdrs { 174*4198Seschrock int ms_length; 175*4198Seschrock union { 176*4198Seschrock scsi_ms_header_t g0; 177*4198Seschrock scsi_ms_header_g1_t g1; 178*4198Seschrock } ms_hdr; 179*4198Seschrock } scsi_ms_hdrs_t; 180*4198Seschrock 181*4198Seschrock typedef struct scsi_ie_page { 182*4198Seschrock struct mode_page ie_mp; 183*4198Seschrock #if defined(_BIT_FIELDS_LTOH) 184*4198Seschrock uint8_t ie_logerr : 1, /* Errors should be logged */ 185*4198Seschrock __reserved1 : 1, 186*4198Seschrock ie_test : 1, /* Enable test gen of IEs */ 187*4198Seschrock ie_dexcpt : 1, /* Disable exceptions */ 188*4198Seschrock ie_ewasc : 1, /* Enable warning generation */ 189*4198Seschrock ie_ebf : 1, /* enable backgrnd functions */ 190*4198Seschrock __reserved2 : 1, 191*4198Seschrock ie_perf : 1; /* No delays during excptns */ 192*4198Seschrock uint8_t ie_mrie : 4, /* Method/reporting excptons */ 193*4198Seschrock __reserved3 : 4; 194*4198Seschrock #else 195*4198Seschrock uint8_t ie_perf : 1, /* No delays during excptons */ 196*4198Seschrock __reserved2 : 1, 197*4198Seschrock ie_ebf : 1, /* enable background funcs */ 198*4198Seschrock ie_ewasc : 1, /* Enable warning generation */ 199*4198Seschrock ie_dexcpt : 1, /* Disable exceptions */ 200*4198Seschrock ie_test : 1, /* Enable test gen of IEs */ 201*4198Seschrock __reserved1 : 1, 202*4198Seschrock ie_logerr : 1; /* Errors should be logged */ 203*4198Seschrock uint8_t __reserved3 : 4, 204*4198Seschrock ie_mrie : 4; /* Method of report excptns */ 205*4198Seschrock #endif 206*4198Seschrock uint32_t ie_interval_timer; /* reporting interval for IEs */ 207*4198Seschrock uint32_t ie_report_count; /* # of times to report an IE */ 208*4198Seschrock } scsi_ie_page_t; 209*4198Seschrock 210*4198Seschrock #pragma pack() 211*4198Seschrock 212*4198Seschrock #define MODEPAGE_INFO_EXCPT_LEN (sizeof (scsi_ie_page_t)) 213*4198Seschrock 214*4198Seschrock #define IEC_IE_ENABLED(ies) ((ies).ie_dexcpt == 0) 215*4198Seschrock #define IEC_IE_CHANGEABLE(ies) ((ies).ie_dexcpt == 1) 216*4198Seschrock #define IEC_MRIE_CHANGEABLE(ies) ((ies).ie_mrie == 0xf) 217*4198Seschrock #define IEC_PERF_CHANGEABLE(ies) ((ies).ie_perf == 1) 218*4198Seschrock #define IEC_EWASC_CHANGEABLE(ies) ((ies).ie_ewasc == 1) 219*4198Seschrock #define IEC_TEST_CHANGEABLE(ies) ((ies).ie_test == 1) 220*4198Seschrock #define IEC_RPTCNT_CHANGEABLE(ies) ((ies).ie_report_count == BE_32(0xffffffff)) 221*4198Seschrock #define IEC_LOGERR_CHANGEABLE(ies) ((ies).ie_logerr == 1) 222*4198Seschrock 223*4198Seschrock /* 224*4198Seschrock * Values for the MRIE field of the informational exceptions control mode page 225*4198Seschrock */ 226*4198Seschrock #define IE_REPORT_NONE 0 227*4198Seschrock #define IE_REPORT_ASYNCH 1 228*4198Seschrock #define IE_REPORT_UNIT_ATTN 2 229*4198Seschrock #define IE_REPORT_RECOV_ERR_COND 3 230*4198Seschrock #define IE_REPORT_RECOV_ERR_ALWAYS 4 231*4198Seschrock #define IE_REPORT_NO_SENSE 5 232*4198Seschrock #define IE_REPORT_ON_REQUEST 6 233*4198Seschrock 234*4198Seschrock /* 235*4198Seschrock * Constants in support of the CONTROL MODE mode page (page 0xA) 236*4198Seschrock */ 237*4198Seschrock #define MODEPAGE_CTRL_MODE_LEN (sizeof (struct mode_control_scsi3)) 238*4198Seschrock #define GLTSD_CHANGEABLE(chg) ((chg).gltsd == 1) 239*4198Seschrock 240*4198Seschrock #define LOGPAGE_SELFTEST_MIN_PARAM_CODE 0x0001 241*4198Seschrock #define LOGPAGE_SELFTEST_MAX_PARAM_CODE 0x0014 242*4198Seschrock 243*4198Seschrock #define LOGPAGE_SELFTEST_PARAM_LEN \ 244*4198Seschrock ((sizeof (scsi_selftest_log_param_t)) - \ 245*4198Seschrock (sizeof (scsi_log_parameter_header_t))) 246*4198Seschrock 247*4198Seschrock /* 248*4198Seschrock * Macro to extract the length of a mode sense page 249*4198Seschrock * as returned by a target. 250*4198Seschrock */ 251*4198Seschrock #define MODESENSE_PAGE_LEN(p) (((int)((struct mode_page *)p)->length) + \ 252*4198Seschrock sizeof (struct mode_page)) 253*4198Seschrock 254*4198Seschrock /* 255*4198Seschrock * Mode Select options 256*4198Seschrock */ 257*4198Seschrock #define MODE_SELECT_SP 0x01 258*4198Seschrock #define MODE_SELECT_PF 0x10 259*4198Seschrock 260*4198Seschrock 261*4198Seschrock /* 262*4198Seschrock * Mode Sense Page Control 263*4198Seschrock */ 264*4198Seschrock #define PC_CURRENT (0 << 6) 265*4198Seschrock #define PC_CHANGEABLE (1 << 6) 266*4198Seschrock #define PC_DEFAULT (2 << 6) 267*4198Seschrock #define PC_SAVED (3 << 6) 268*4198Seschrock 269*4198Seschrock /* 270*4198Seschrock * Log Sense Page Control 271*4198Seschrock */ 272*4198Seschrock #define PC_CUMULATIVE (1 << 6) 273*4198Seschrock 274*4198Seschrock /* 275*4198Seschrock * LOG page codes 276*4198Seschrock */ 277*4198Seschrock #define LOGPAGE_SUPP_LIST 0x00 278*4198Seschrock #define LOGPAGE_TEMP 0x0d 279*4198Seschrock #define LOGPAGE_SELFTEST 0x10 280*4198Seschrock #define LOGPAGE_IE 0x2f 281*4198Seschrock 282*4198Seschrock /* ASC constants */ 283*4198Seschrock #define ASC_INVALID_OPCODE 0x20 284*4198Seschrock #define ASC_INVALID_CDB_FIELD 0x24 285*4198Seschrock #define ASC_FAILURE_PREDICTION_THRESHOLD_EXCEEDED 0x5d 286*4198Seschrock 287*4198Seschrock /* ASCQ constants */ 288*4198Seschrock #define ASCQ_INVALID_OPCODE 0 289*4198Seschrock 290*4198Seschrock /* Error tests */ 291*4198Seschrock #define SCSI_INVALID_OPCODE(s, a, aq) \ 292*4198Seschrock (((s) == KEY_ILLEGAL_REQUEST) && ((a) == ASC_INVALID_OPCODE) && \ 293*4198Seschrock ((aq) == ASCQ_INVALID_OPCODE)) 294*4198Seschrock 295*4198Seschrock #define MODE_PAGE_UNSUPPORTED(s, a, aq) \ 296*4198Seschrock (((s) == KEY_ILLEGAL_REQUEST) && ((a) == ASC_INVALID_CDB_FIELD)) 297*4198Seschrock 298*4198Seschrock /* command length to use */ 299*4198Seschrock #define MODE_CMD_LEN_UNKNOWN 0 300*4198Seschrock #define MODE_CMD_LEN_6 1 301*4198Seschrock #define MODE_CMD_LEN_10 2 302*4198Seschrock 303*4198Seschrock /* supported modepages bitmask */ 304*4198Seschrock #define MODEPAGE_SUPP_IEC 0x1 305*4198Seschrock 306*4198Seschrock /* supported logpages bitmask */ 307*4198Seschrock #define LOGPAGE_SUPP_IE 0x1 308*4198Seschrock #define LOGPAGE_SUPP_TEMP 0x2 309*4198Seschrock #define LOGPAGE_SUPP_SELFTEST 0x4 310*4198Seschrock 311*4198Seschrock #define MSG_BUFLEN 256 312*4198Seschrock 313*4198Seschrock /* 314*4198Seschrock * For SCSI commands which want to accept arbitrary length responses, we need to 315*4198Seschrock * allocate an appropriate sized buffer. The maximum length is USHRT_MAX, 316*4198Seschrock * because some devices return nothing if the buffer length is too big. 317*4198Seschrock */ 318*4198Seschrock #define MAX_BUFLEN(type) (USHRT_MAX - sizeof (type)) 319*4198Seschrock 320*4198Seschrock extern ds_transport_t ds_scsi_uscsi_transport; 321*4198Seschrock extern ds_transport_t ds_scsi_sim_transport; 322*4198Seschrock 323*4198Seschrock #ifdef __cplusplus 324*4198Seschrock } 325*4198Seschrock #endif 326*4198Seschrock 327*4198Seschrock #endif /* _DS_SCSI_H */ 328