isp_target.h revision 160978
155372Smjacob/* $FreeBSD: head/sys/dev/isp/isp_target.h 160978 2006-08-04 20:20:00Z mjacob $ */ 2139749Simp/*- 355372Smjacob * Qlogic Target Mode Structure and Flag Definitions 455372Smjacob * 555372Smjacob * Copyright (c) 1997, 1998 655372Smjacob * Patrick Stirling 755372Smjacob * pms@psconsult.com 855372Smjacob * All rights reserved. 955372Smjacob * 10154704Smjacob * Additonal Copyright (c) 1997-2006 by Matthew Jacob 1155372Smjacob * All rights reserved. 1255372Smjacob * 1355372Smjacob * Redistribution and use in source and binary forms, with or without 1455372Smjacob * modification, are permitted provided that the following conditions 1555372Smjacob * are met: 1655372Smjacob * 1. Redistributions of source code must retain the above copyright 1755372Smjacob * notice immediately at the beginning of the file, without modification, 1855372Smjacob * this list of conditions, and the following disclaimer. 1966189Smjacob * 2. The name of the author may not be used to endorse or promote products 2055372Smjacob * derived from this software without specific prior written permission. 2155372Smjacob * 2255372Smjacob * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 2355372Smjacob * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 2455372Smjacob * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2555372Smjacob * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR 2655372Smjacob * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2755372Smjacob * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 28154704Smjacob * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 29154704Smjacob * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 3055372Smjacob * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 3155372Smjacob * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 3255372Smjacob * SUCH DAMAGE. 3355372Smjacob * 3455372Smjacob */ 3574231Smjacob#ifndef _ISP_TARGET_H 3674231Smjacob#define _ISP_TARGET_H 3755372Smjacob 38120016Smjacob#define QLTM_SENSELEN 18 /* non-FC cards only */ 3955372Smjacob#define QLTM_SVALID 0x80 4055372Smjacob 4155372Smjacob/* 4255372Smjacob * Structure for Enable Lun and Modify Lun queue entries 4355372Smjacob */ 4455372Smjacobtypedef struct { 4555372Smjacob isphdr_t le_header; 46155704Smjacob uint32_t le_reserved; 47155704Smjacob uint8_t le_lun; 48155704Smjacob uint8_t le_rsvd; 49155704Smjacob uint8_t le_ops; /* Modify LUN only */ 50155704Smjacob uint8_t le_tgt; /* Not for FC */ 51155704Smjacob uint32_t le_flags; /* Not for FC */ 52155704Smjacob uint8_t le_status; 53155704Smjacob uint8_t le_reserved2; 54155704Smjacob uint8_t le_cmd_count; 55155704Smjacob uint8_t le_in_count; 56155704Smjacob uint8_t le_cdb6len; /* Not for FC */ 57155704Smjacob uint8_t le_cdb7len; /* Not for FC */ 58155704Smjacob uint16_t le_timeout; 59155704Smjacob uint16_t le_reserved3[20]; 6055372Smjacob} lun_entry_t; 6155372Smjacob 6255372Smjacob/* 6355372Smjacob * le_flags values 6455372Smjacob */ 6575195Smjacob#define LUN_TQAE 0x00000002 /* bit1 Tagged Queue Action Enable */ 6655372Smjacob#define LUN_DSSM 0x01000000 /* bit24 Disable Sending SDP Message */ 6761771Smjacob#define LUN_DISAD 0x02000000 /* bit25 Disable autodisconnect */ 6855372Smjacob#define LUN_DM 0x40000000 /* bit30 Disconnects Mandatory */ 6955372Smjacob 7055372Smjacob/* 7155372Smjacob * le_ops values 7255372Smjacob */ 7355372Smjacob#define LUN_CCINCR 0x01 /* increment command count */ 7455372Smjacob#define LUN_CCDECR 0x02 /* decrement command count */ 7555372Smjacob#define LUN_ININCR 0x40 /* increment immed. notify count */ 7655372Smjacob#define LUN_INDECR 0x80 /* decrement immed. notify count */ 7755372Smjacob 7855372Smjacob/* 7955372Smjacob * le_status values 8055372Smjacob */ 8155372Smjacob#define LUN_OK 0x01 /* we be rockin' */ 8255372Smjacob#define LUN_ERR 0x04 /* request completed with error */ 8355372Smjacob#define LUN_INVAL 0x06 /* invalid request */ 8455372Smjacob#define LUN_NOCAP 0x16 /* can't provide requested capability */ 8555372Smjacob#define LUN_ENABLED 0x3E /* LUN already enabled */ 8655372Smjacob 8755372Smjacob/* 8855372Smjacob * Immediate Notify Entry structure 8955372Smjacob */ 9055372Smjacob#define IN_MSGLEN 8 /* 8 bytes */ 9155372Smjacob#define IN_RSVDLEN 8 /* 8 words */ 9255372Smjacobtypedef struct { 9355372Smjacob isphdr_t in_header; 94155704Smjacob uint32_t in_reserved; 95155704Smjacob uint8_t in_lun; /* lun */ 96155704Smjacob uint8_t in_iid; /* initiator */ 97155704Smjacob uint8_t in_reserved2; 98155704Smjacob uint8_t in_tgt; /* target */ 99155704Smjacob uint32_t in_flags; 100155704Smjacob uint8_t in_status; 101155704Smjacob uint8_t in_rsvd2; 102155704Smjacob uint8_t in_tag_val; /* tag value */ 103155704Smjacob uint8_t in_tag_type; /* tag type */ 104155704Smjacob uint16_t in_seqid; /* sequence id */ 105155704Smjacob uint8_t in_msg[IN_MSGLEN]; /* SCSI message bytes */ 106155704Smjacob uint16_t in_reserved3[IN_RSVDLEN]; 107155704Smjacob uint8_t in_sense[QLTM_SENSELEN];/* suggested sense data */ 10855372Smjacob} in_entry_t; 10955372Smjacob 11055372Smjacobtypedef struct { 11155372Smjacob isphdr_t in_header; 112155704Smjacob uint32_t in_reserved; 113155704Smjacob uint8_t in_lun; /* lun */ 114155704Smjacob uint8_t in_iid; /* initiator */ 115155704Smjacob uint16_t in_scclun; 116155704Smjacob uint32_t in_reserved2; 117155704Smjacob uint16_t in_status; 118155704Smjacob uint16_t in_task_flags; 119155704Smjacob uint16_t in_seqid; /* sequence id */ 12055372Smjacob} in_fcentry_t; 12155372Smjacob 122154704Smjacobtypedef struct { 123154704Smjacob isphdr_t in_header; 124155704Smjacob uint32_t in_reserved; 125155704Smjacob uint16_t in_iid; /* initiator */ 126155704Smjacob uint16_t in_scclun; 127155704Smjacob uint32_t in_reserved2; 128155704Smjacob uint16_t in_status; 129155704Smjacob uint16_t in_task_flags; 130155704Smjacob uint16_t in_seqid; /* sequence id */ 131154704Smjacob} in_fcentry_e_t; 132154704Smjacob 13355372Smjacob/* 13455372Smjacob * Values for the in_status field 13555372Smjacob */ 13663390Smjacob#define IN_REJECT 0x0D /* Message Reject message received */ 13755372Smjacob#define IN_RESET 0x0E /* Bus Reset occurred */ 13855372Smjacob#define IN_NO_RCAP 0x16 /* requested capability not available */ 13955372Smjacob#define IN_IDE_RECEIVED 0x33 /* Initiator Detected Error msg received */ 14055372Smjacob#define IN_RSRC_UNAVAIL 0x34 /* resource unavailable */ 14155372Smjacob#define IN_MSG_RECEIVED 0x36 /* SCSI message received */ 14255372Smjacob#define IN_ABORT_TASK 0x20 /* task named in RX_ID is being aborted (FC) */ 14355372Smjacob#define IN_PORT_LOGOUT 0x29 /* port has logged out (FC) */ 14455372Smjacob#define IN_PORT_CHANGED 0x2A /* port changed */ 14555372Smjacob#define IN_GLOBAL_LOGO 0x2E /* all ports logged out */ 14663390Smjacob#define IN_NO_NEXUS 0x3B /* Nexus not established */ 14755372Smjacob 14855372Smjacob/* 14955372Smjacob * Values for the in_task_flags field- should only get one at a time! 15055372Smjacob */ 151160978Smjacob#define TASK_FLAGS_RESERVED_MASK (0xe700) 152120016Smjacob#define TASK_FLAGS_CLEAR_ACA (1<<14) 153120016Smjacob#define TASK_FLAGS_TARGET_RESET (1<<13) 154120016Smjacob#define TASK_FLAGS_LUN_RESET (1<<12) 15555372Smjacob#define TASK_FLAGS_CLEAR_TASK_SET (1<<10) 156120016Smjacob#define TASK_FLAGS_ABORT_TASK_SET (1<<9) 15755372Smjacob 158120016Smjacob#ifndef MSG_ABORT 159120016Smjacob#define MSG_ABORT 0x06 160120016Smjacob#endif 161120016Smjacob#ifndef MSG_BUS_DEV_RESET 162120016Smjacob#define MSG_BUS_DEV_RESET 0x0c 163120016Smjacob#endif 16455372Smjacob#ifndef MSG_ABORT_TAG 165120016Smjacob#define MSG_ABORT_TAG 0x0d 16655372Smjacob#endif 16755372Smjacob#ifndef MSG_CLEAR_QUEUE 16855372Smjacob#define MSG_CLEAR_QUEUE 0x0e 16955372Smjacob#endif 17055372Smjacob#ifndef MSG_REL_RECOVERY 17155372Smjacob#define MSG_REL_RECOVERY 0x10 17255372Smjacob#endif 17355372Smjacob#ifndef MSG_TERM_IO_PROC 17455372Smjacob#define MSG_TERM_IO_PROC 0x11 17555372Smjacob#endif 176120016Smjacob#ifndef MSG_LUN_RESET 177120016Smjacob#define MSG_LUN_RESET 0x17 178120016Smjacob#endif 17955372Smjacob 18055372Smjacob/* 18155372Smjacob * Notify Acknowledge Entry structure 18255372Smjacob */ 18355372Smjacob#define NA_RSVDLEN 22 18455372Smjacobtypedef struct { 18555372Smjacob isphdr_t na_header; 186155704Smjacob uint32_t na_reserved; 187155704Smjacob uint8_t na_lun; /* lun */ 188155704Smjacob uint8_t na_iid; /* initiator */ 189155704Smjacob uint8_t na_reserved2; 190155704Smjacob uint8_t na_tgt; /* target */ 191155704Smjacob uint32_t na_flags; 192155704Smjacob uint8_t na_status; 193155704Smjacob uint8_t na_event; 194155704Smjacob uint16_t na_seqid; /* sequence id */ 195155704Smjacob uint16_t na_reserved3[NA_RSVDLEN]; 19655372Smjacob} na_entry_t; 19755372Smjacob 19855372Smjacob/* 19955372Smjacob * Value for the na_event field 20055372Smjacob */ 20155372Smjacob#define NA_RST_CLRD 0x80 /* Clear an async event notification */ 20259453Smjacob#define NA_OK 0x01 /* Notify Acknowledge Succeeded */ 20359453Smjacob#define NA_INVALID 0x06 /* Invalid Notify Acknowledge */ 20455372Smjacob 20555372Smjacob#define NA2_RSVDLEN 21 20655372Smjacobtypedef struct { 20755372Smjacob isphdr_t na_header; 208155704Smjacob uint32_t na_reserved; 209160978Smjacob uint8_t na_reserved1; 210160978Smjacob uint8_t na_iid; /* initiator loop id */ 211160978Smjacob uint16_t na_response; 212155704Smjacob uint16_t na_flags; 213155704Smjacob uint16_t na_reserved2; 214155704Smjacob uint16_t na_status; 215155704Smjacob uint16_t na_task_flags; 216155704Smjacob uint16_t na_seqid; /* sequence id */ 217155704Smjacob uint16_t na_reserved3[NA2_RSVDLEN]; 21855372Smjacob} na_fcentry_t; 219154704Smjacob 220154704Smjacobtypedef struct { 221154704Smjacob isphdr_t na_header; 222155704Smjacob uint32_t na_reserved; 223160978Smjacob uint16_t na_iid; /* initiator loop id */ 224160978Smjacob uint16_t na_response; /* response code */ 225155704Smjacob uint16_t na_flags; 226155704Smjacob uint16_t na_reserved2; 227155704Smjacob uint16_t na_status; 228155704Smjacob uint16_t na_task_flags; 229155704Smjacob uint16_t na_seqid; /* sequence id */ 230155704Smjacob uint16_t na_reserved3[NA2_RSVDLEN]; 231154704Smjacob} na_fcentry_e_t; 232154704Smjacob 23355372Smjacob#define NAFC_RCOUNT 0x80 /* increment resource count */ 23455372Smjacob#define NAFC_RST_CLRD 0x20 /* Clear LIP Reset */ 235160978Smjacob#define NAFC_TVALID 0x10 /* task mangement response code is valid */ 236160978Smjacob 23755372Smjacob/* 23855372Smjacob * Accept Target I/O Entry structure 23955372Smjacob */ 24055372Smjacob#define ATIO_CDBLEN 26 24155372Smjacob 24255372Smjacobtypedef struct { 24355372Smjacob isphdr_t at_header; 244155704Smjacob uint16_t at_reserved; 245155704Smjacob uint16_t at_handle; 246155704Smjacob uint8_t at_lun; /* lun */ 247155704Smjacob uint8_t at_iid; /* initiator */ 248155704Smjacob uint8_t at_cdblen; /* cdb length */ 249155704Smjacob uint8_t at_tgt; /* target */ 250155704Smjacob uint32_t at_flags; 251155704Smjacob uint8_t at_status; /* firmware status */ 252155704Smjacob uint8_t at_scsi_status; /* scsi status */ 253155704Smjacob uint8_t at_tag_val; /* tag value */ 254155704Smjacob uint8_t at_tag_type; /* tag type */ 255155704Smjacob uint8_t at_cdb[ATIO_CDBLEN]; /* received CDB */ 256155704Smjacob uint8_t at_sense[QLTM_SENSELEN];/* suggested sense data */ 25755372Smjacob} at_entry_t; 25855372Smjacob 25955372Smjacob/* 26055372Smjacob * at_flags values 26155372Smjacob */ 26255372Smjacob#define AT_NODISC 0x00008000 /* disconnect disabled */ 26375195Smjacob#define AT_TQAE 0x00000002 /* Tagged Queue Action enabled */ 26455372Smjacob 26555372Smjacob/* 26655372Smjacob * at_status values 26755372Smjacob */ 26855372Smjacob#define AT_PATH_INVALID 0x07 /* ATIO sent to firmware for disabled lun */ 26955372Smjacob#define AT_RESET 0x0E /* SCSI Bus Reset Occurred */ 27055372Smjacob#define AT_PHASE_ERROR 0x14 /* Bus phase sequence error */ 27155372Smjacob#define AT_NOCAP 0x16 /* Requested capability not available */ 27255372Smjacob#define AT_BDR_MSG 0x17 /* Bus Device Reset msg received */ 27355372Smjacob#define AT_CDB 0x3D /* CDB received */ 27455372Smjacob/* 27575195Smjacob * Macros to create and fetch and test concatenated handle and tag value macros 27675195Smjacob */ 27775195Smjacob 278140652Smjacob#define AT_MAKE_TAGID(tid, inst, aep) \ 279140652Smjacob tid = aep->at_handle; \ 280140652Smjacob if (aep->at_flags & AT_TQAE) { \ 281140652Smjacob tid |= (aep->at_tag_val << 16); \ 282140652Smjacob tid |= (1 << 24); \ 283140652Smjacob } \ 284154704Smjacob tid |= (GET_BUS_VAL(aep->at_iid) << 25); \ 285154704Smjacob tid |= (inst << 26) 28675195Smjacob 287154704Smjacob#define CT_MAKE_TAGID(tid, bus, inst, ct) \ 288140652Smjacob tid = ct->ct_fwhandle; \ 289140652Smjacob if (ct->ct_flags & CT_TQAE) { \ 290140652Smjacob tid |= (ct->ct_tag_val << 16); \ 291140652Smjacob tid |= (1 << 24); \ 292140652Smjacob } \ 293154704Smjacob tid |= ((bus & 0x1) << 25); \ 294154704Smjacob tid |= (inst << 26) 29575195Smjacob 296140652Smjacob#define AT_HAS_TAG(val) ((val) & (1 << 24)) 297140652Smjacob#define AT_GET_TAG(val) (((val) >> 16) & 0xff) 298154704Smjacob#define AT_GET_INST(val) (((val) >> 26) & 0x3f) 299154704Smjacob#define AT_GET_BUS(val) (((val) >> 25) & 0x1) 300140652Smjacob#define AT_GET_HANDLE(val) ((val) & 0xffff) 30175195Smjacob 302140652Smjacob#define IN_MAKE_TAGID(tid, inst, inp) \ 303140652Smjacob tid = inp->in_seqid; \ 304140652Smjacob tid |= (inp->in_tag_val << 16); \ 305140652Smjacob tid |= (1 << 24); \ 306154704Smjacob tid |= (GET_BUS_VAL(inp->in_iid) << 25); \ 307154704Smjacob tid |= (inst << 26) 308140652Smjacob 309140652Smjacob#define TAG_INSERT_INST(tid, inst) \ 310154704Smjacob tid &= ~(0x3ffffff); \ 311154704Smjacob tid |= (inst << 26) 312140652Smjacob 313154704Smjacob#define TAG_INSERT_BUS(tid, bus) \ 314154704Smjacob tid &= ~(1 << 25); \ 315154704Smjacob tid |= (bus << 25) 316154704Smjacob 31775195Smjacob/* 31855372Smjacob * Accept Target I/O Entry structure, Type 2 31955372Smjacob */ 32055372Smjacob#define ATIO2_CDBLEN 16 32155372Smjacob 32255372Smjacobtypedef struct { 32355372Smjacob isphdr_t at_header; 324155704Smjacob uint32_t at_reserved; 325155704Smjacob uint8_t at_lun; /* lun or reserved */ 326155704Smjacob uint8_t at_iid; /* initiator */ 327155704Smjacob uint16_t at_rxid; /* response ID */ 328155704Smjacob uint16_t at_flags; 329155704Smjacob uint16_t at_status; /* firmware status */ 330155704Smjacob uint8_t at_crn; /* command reference number */ 331155704Smjacob uint8_t at_taskcodes; 332155704Smjacob uint8_t at_taskflags; 333155704Smjacob uint8_t at_execodes; 334155704Smjacob uint8_t at_cdb[ATIO2_CDBLEN]; /* received CDB */ 335155704Smjacob uint32_t at_datalen; /* allocated data len */ 336155704Smjacob uint16_t at_scclun; /* SCC Lun or reserved */ 337155704Smjacob uint16_t at_wwpn[4]; /* WWPN of initiator */ 338155704Smjacob uint16_t at_reserved2[6]; 339155704Smjacob uint16_t at_oxid; 34055372Smjacob} at2_entry_t; 34155372Smjacob 342154704Smjacobtypedef struct { 343154704Smjacob isphdr_t at_header; 344155704Smjacob uint32_t at_reserved; 345155704Smjacob uint16_t at_iid; /* initiator */ 346155704Smjacob uint16_t at_rxid; /* response ID */ 347155704Smjacob uint16_t at_flags; 348155704Smjacob uint16_t at_status; /* firmware status */ 349155704Smjacob uint8_t at_crn; /* command reference number */ 350155704Smjacob uint8_t at_taskcodes; 351155704Smjacob uint8_t at_taskflags; 352155704Smjacob uint8_t at_execodes; 353155704Smjacob uint8_t at_cdb[ATIO2_CDBLEN]; /* received CDB */ 354155704Smjacob uint32_t at_datalen; /* allocated data len */ 355155704Smjacob uint16_t at_scclun; /* SCC Lun or reserved */ 356155704Smjacob uint16_t at_wwpn[4]; /* WWPN of initiator */ 357155704Smjacob uint16_t at_reserved2[6]; 358155704Smjacob uint16_t at_oxid; 359154704Smjacob} at2e_entry_t; 360154704Smjacob 36170457Smjacob#define ATIO2_WWPN_OFFSET 0x2A 36270457Smjacob#define ATIO2_OXID_OFFSET 0x3E 36370457Smjacob 36455372Smjacob#define ATIO2_TC_ATTR_MASK 0x7 36555372Smjacob#define ATIO2_TC_ATTR_SIMPLEQ 0 36655372Smjacob#define ATIO2_TC_ATTR_HEADOFQ 1 36755372Smjacob#define ATIO2_TC_ATTR_ORDERED 2 36855372Smjacob#define ATIO2_TC_ATTR_ACAQ 4 36955372Smjacob#define ATIO2_TC_ATTR_UNTAGGED 5 37055372Smjacob 371120016Smjacob#define ATIO2_EX_WRITE 0x1 372120016Smjacob#define ATIO2_EX_READ 0x2 373140652Smjacob/* 374140652Smjacob * Macros to create and fetch and test concatenated handle and tag value macros 375140652Smjacob */ 376140652Smjacob#define AT2_MAKE_TAGID(tid, inst, aep) \ 377140652Smjacob tid = aep->at_rxid; \ 378140652Smjacob tid |= (inst << 16) 379120016Smjacob 380140652Smjacob#define CT2_MAKE_TAGID(tid, inst, ct) \ 381140652Smjacob tid = ct->ct_rxid; \ 382140652Smjacob tid |= (inst << 16) 383140652Smjacob 384140652Smjacob#define AT2_HAS_TAG(val) 1 385140652Smjacob#define AT2_GET_TAG(val) ((val) & 0xffff) 386140652Smjacob#define AT2_GET_INST(val) ((val) >> 16) 387140652Smjacob#define AT2_GET_HANDLE AT2_GET_TAG 388140652Smjacob 389154704Smjacob#define FC_HAS_TAG AT2_HAS_TAG 390154704Smjacob#define FC_GET_TAG AT2_GET_TAG 391154704Smjacob#define FC_GET_INST AT2_GET_INST 392154704Smjacob#define FC_GET_HANDLE AT2_GET_HANDLE 393154704Smjacob 394157943Smjacob#define IN_FC_MAKE_TAGID(tid, inst, seqid) \ 395157943Smjacob tid = seqid; \ 396140652Smjacob tid |= (inst << 16) 397140652Smjacob 398140652Smjacob#define FC_TAG_INSERT_INST(tid, inst) \ 399140652Smjacob tid &= ~0xffff; \ 400140652Smjacob tid |= (inst << 16) 401140652Smjacob 402140652Smjacob 40355372Smjacob/* 40455372Smjacob * Continue Target I/O Entry structure 40555372Smjacob * Request from driver. The response from the 40655372Smjacob * ISP firmware is the same except that the last 18 40755372Smjacob * bytes are overwritten by suggested sense data if 40855372Smjacob * the 'autosense valid' bit is set in the status byte. 40955372Smjacob */ 41055372Smjacobtypedef struct { 41155372Smjacob isphdr_t ct_header; 412155704Smjacob uint16_t ct_reserved; 41373319Smjacob#define ct_syshandle ct_reserved /* we use this */ 414155704Smjacob uint16_t ct_fwhandle; /* required by f/w */ 415155704Smjacob uint8_t ct_lun; /* lun */ 416155704Smjacob uint8_t ct_iid; /* initiator id */ 417155704Smjacob uint8_t ct_reserved2; 418155704Smjacob uint8_t ct_tgt; /* our target id */ 419155704Smjacob uint32_t ct_flags; 420155704Smjacob uint8_t ct_status; /* isp status */ 421155704Smjacob uint8_t ct_scsi_status; /* scsi status */ 422155704Smjacob uint8_t ct_tag_val; /* tag value */ 423155704Smjacob uint8_t ct_tag_type; /* tag type */ 424155704Smjacob uint32_t ct_xfrlen; /* transfer length */ 425155704Smjacob uint32_t ct_resid; /* residual length */ 426155704Smjacob uint16_t ct_timeout; 427155704Smjacob uint16_t ct_seg_count; 42887635Smjacob /* 42987635Smjacob * This is so we can share tag name space with 43087635Smjacob * CTIO{2,3,4} with the minimum of pain. 43187635Smjacob */ 43287635Smjacob union { 43387635Smjacob ispds_t ct_a[ISP_RQDSEG]; 43487635Smjacob } _u; 43587635Smjacob#define ct_dataseg _u.ct_a 43655372Smjacob} ct_entry_t; 43755372Smjacob 43855372Smjacob/* 43956005Smjacob * For some of the dual port SCSI adapters, port (bus #) is reported 44056005Smjacob * in the MSbit of ct_iid. Bit fields are a bit too awkward here. 44156005Smjacob * 44256005Smjacob * Note that this does not apply to FC adapters at all which can and 443154704Smjacob * do report IIDs between 0x81 && 0xfe (or 0x7ff) which represent devices 444154704Smjacob * that have logged in across a SCSI fabric. 44556005Smjacob */ 44656005Smjacob#define GET_IID_VAL(x) (x & 0x3f) 44756005Smjacob#define GET_BUS_VAL(x) ((x >> 7) & 0x1) 44883005Smjacob#define SET_IID_VAL(y, x) y = ((y & ~0x3f) | (x & 0x3f)) 44983005Smjacob#define SET_BUS_VAL(y, x) y = ((y & 0x3f) | ((x & 0x1) << 7)) 45056005Smjacob 45156005Smjacob/* 45255372Smjacob * ct_flags values 45355372Smjacob */ 45475195Smjacob#define CT_TQAE 0x00000002 /* bit 1, Tagged Queue Action enable */ 45555372Smjacob#define CT_DATA_IN 0x00000040 /* bits 6&7, Data direction */ 45655372Smjacob#define CT_DATA_OUT 0x00000080 /* bits 6&7, Data direction */ 45755372Smjacob#define CT_NO_DATA 0x000000C0 /* bits 6&7, Data direction */ 45855372Smjacob#define CT_CCINCR 0x00000100 /* bit 8, autoincrement atio count */ 45955372Smjacob#define CT_DATAMASK 0x000000C0 /* bits 6&7, Data direction */ 46063390Smjacob#define CT_INISYNCWIDE 0x00004000 /* bit 14, Do Sync/Wide Negotiation */ 46155372Smjacob#define CT_NODISC 0x00008000 /* bit 15, Disconnects disabled */ 46255372Smjacob#define CT_DSDP 0x01000000 /* bit 24, Disable Save Data Pointers */ 46355372Smjacob#define CT_SENDRDP 0x04000000 /* bit 26, Send Restore Pointers msg */ 46455372Smjacob#define CT_SENDSTATUS 0x80000000 /* bit 31, Send SCSI status byte */ 46555372Smjacob 46655372Smjacob/* 46755372Smjacob * ct_status values 46855372Smjacob * - set by the firmware when it returns the CTIO 46955372Smjacob */ 47055372Smjacob#define CT_OK 0x01 /* completed without error */ 47155372Smjacob#define CT_ABORTED 0x02 /* aborted by host */ 47255372Smjacob#define CT_ERR 0x04 /* see sense data for error */ 47355372Smjacob#define CT_INVAL 0x06 /* request for disabled lun */ 47455372Smjacob#define CT_NOPATH 0x07 /* invalid ITL nexus */ 47555372Smjacob#define CT_INVRXID 0x08 /* (FC only) Invalid RX_ID */ 47677365Smjacob#define CT_DATA_OVER 0x09 /* (FC only) Data Overrun */ 47755372Smjacob#define CT_RSELTMO 0x0A /* reselection timeout after 2 tries */ 47855372Smjacob#define CT_TIMEOUT 0x0B /* timed out */ 47955372Smjacob#define CT_RESET 0x0E /* SCSI Bus Reset occurred */ 48063390Smjacob#define CT_PARITY 0x0F /* Uncorrectable Parity Error */ 48177365Smjacob#define CT_BUS_ERROR 0x10 /* (FC Only) DMA PCI Error */ 48263390Smjacob#define CT_PANIC 0x13 /* Unrecoverable Error */ 48355372Smjacob#define CT_PHASE_ERROR 0x14 /* Bus phase sequence error */ 48455372Smjacob#define CT_BDR_MSG 0x17 /* Bus Device Reset msg received */ 48577365Smjacob#define CT_DATA_UNDER 0x15 /* (FC only) Data Underrun */ 48655372Smjacob#define CT_TERMINATED 0x19 /* due to Terminate Transfer mbox cmd */ 48755372Smjacob#define CT_PORTNOTAVAIL 0x28 /* port not available */ 48855372Smjacob#define CT_LOGOUT 0x29 /* port logout */ 48955372Smjacob#define CT_PORTCHANGED 0x2A /* port changed */ 49063390Smjacob#define CT_IDE 0x33 /* Initiator Detected Error */ 49155372Smjacob#define CT_NOACK 0x35 /* Outstanding Immed. Notify. entry */ 492154704Smjacob#define CT_SRR 0x45 /* SRR Received */ 493154704Smjacob#define CT_LUN_RESET 0x48 /* Lun Reset Received */ 49455372Smjacob 49555372Smjacob/* 49655372Smjacob * When the firmware returns a CTIO entry, it may overwrite the last 49755372Smjacob * part of the structure with sense data. This starts at offset 0x2E 49855372Smjacob * into the entry, which is in the middle of ct_dataseg[1]. Rather 49955372Smjacob * than define a new struct for this, I'm just using the sense data 50055372Smjacob * offset. 50155372Smjacob */ 50255372Smjacob#define CTIO_SENSE_OFFSET 0x2E 50355372Smjacob 50455372Smjacob/* 50555372Smjacob * Entry length in u_longs. All entries are the same size so 50655372Smjacob * any one will do as the numerator. 50755372Smjacob */ 508155704Smjacob#define UINT32_ENTRY_SIZE (sizeof(at_entry_t)/sizeof(uint32_t)) 50955372Smjacob 51055372Smjacob/* 51155372Smjacob * QLA2100 CTIO (type 2) entry 51255372Smjacob */ 51355372Smjacob#define MAXRESPLEN 26 51455372Smjacobtypedef struct { 51555372Smjacob isphdr_t ct_header; 516155704Smjacob uint16_t ct_reserved; 517155704Smjacob uint16_t ct_fwhandle; /* just to match CTIO */ 518155704Smjacob uint8_t ct_lun; /* lun */ 519155704Smjacob uint8_t ct_iid; /* initiator id */ 520155704Smjacob uint16_t ct_rxid; /* response ID */ 521155704Smjacob uint16_t ct_flags; 522155704Smjacob uint16_t ct_status; /* isp status */ 523155704Smjacob uint16_t ct_timeout; 524155704Smjacob uint16_t ct_seg_count; 525155704Smjacob uint32_t ct_reloff; /* relative offset */ 52656005Smjacob int32_t ct_resid; /* residual length */ 52755372Smjacob union { 52855372Smjacob /* 52955372Smjacob * The three different modes that the target driver 53087635Smjacob * can set the CTIO{2,3,4} up as. 53155372Smjacob * 53255372Smjacob * The first is for sending FCP_DATA_IUs as well as 53355372Smjacob * (optionally) sending a terminal SCSI status FCP_RSP_IU. 53455372Smjacob * 53555372Smjacob * The second is for sending SCSI sense data in an FCP_RSP_IU. 53655372Smjacob * Note that no FCP_DATA_IUs will be sent. 53755372Smjacob * 53855372Smjacob * The third is for sending FCP_RSP_IUs as built specifically 53955372Smjacob * in system memory as located by the isp_dataseg. 54055372Smjacob */ 54155372Smjacob struct { 542155704Smjacob uint32_t _reserved; 543155704Smjacob uint16_t _reserved2; 544155704Smjacob uint16_t ct_scsi_status; 545155704Smjacob uint32_t ct_xfrlen; 54687635Smjacob union { 54787635Smjacob ispds_t ct_a[ISP_RQDSEG_T2]; /* CTIO2 */ 54887635Smjacob ispds64_t ct_b[ISP_RQDSEG_T3]; /* CTIO3 */ 54987635Smjacob ispdslist_t ct_c; /* CTIO4 */ 55087635Smjacob } _u; 55187635Smjacob#define ct_dataseg _u.ct_a 55287635Smjacob#define ct_dataseg64 _u.ct_b 55387635Smjacob#define ct_dslist _u.ct_c 55455372Smjacob } m0; 55555372Smjacob struct { 556155704Smjacob uint16_t _reserved; 557155704Smjacob uint16_t _reserved2; 558155704Smjacob uint16_t ct_senselen; 559155704Smjacob uint16_t ct_scsi_status; 560155704Smjacob uint16_t ct_resplen; 561155704Smjacob uint8_t ct_resp[MAXRESPLEN]; 56255372Smjacob } m1; 56355372Smjacob struct { 564155704Smjacob uint32_t _reserved; 565155704Smjacob uint16_t _reserved2; 566155704Smjacob uint16_t _reserved3; 567155704Smjacob uint32_t ct_datalen; 56855372Smjacob ispds_t ct_fcp_rsp_iudata; 56955372Smjacob } m2; 57055372Smjacob } rsp; 57155372Smjacob} ct2_entry_t; 57255372Smjacob 573154704Smjacobtypedef struct { 574154704Smjacob isphdr_t ct_header; 575155704Smjacob uint16_t ct_reserved; 576155704Smjacob uint16_t ct_fwhandle; /* just to match CTIO */ 577155704Smjacob uint16_t ct_iid; /* initiator id */ 578155704Smjacob uint16_t ct_rxid; /* response ID */ 579155704Smjacob uint16_t ct_flags; 580155704Smjacob uint16_t ct_status; /* isp status */ 581155704Smjacob uint16_t ct_timeout; 582155704Smjacob uint16_t ct_seg_count; 583155704Smjacob uint32_t ct_reloff; /* relative offset */ 584154704Smjacob int32_t ct_resid; /* residual length */ 585154704Smjacob union { 586154704Smjacob struct { 587155704Smjacob uint32_t _reserved; 588155704Smjacob uint16_t _reserved2; 589155704Smjacob uint16_t ct_scsi_status; 590155704Smjacob uint32_t ct_xfrlen; 591154704Smjacob union { 592154704Smjacob ispds_t ct_a[ISP_RQDSEG_T2]; /* CTIO2 */ 593154704Smjacob ispds64_t ct_b[ISP_RQDSEG_T3]; /* CTIO3 */ 594154704Smjacob ispdslist_t ct_c; /* CTIO4 */ 595154704Smjacob } _u; 596154704Smjacob } m0; 597154704Smjacob struct { 598155704Smjacob uint16_t _reserved; 599155704Smjacob uint16_t _reserved2; 600155704Smjacob uint16_t ct_senselen; 601155704Smjacob uint16_t ct_scsi_status; 602155704Smjacob uint16_t ct_resplen; 603155704Smjacob uint8_t ct_resp[MAXRESPLEN]; 604154704Smjacob } m1; 605154704Smjacob struct { 606155704Smjacob uint32_t _reserved; 607155704Smjacob uint16_t _reserved2; 608155704Smjacob uint16_t _reserved3; 609155704Smjacob uint32_t ct_datalen; 610154704Smjacob ispds_t ct_fcp_rsp_iudata; 611154704Smjacob } m2; 612154704Smjacob } rsp; 613154704Smjacob} ct2e_entry_t; 614154704Smjacob 61555372Smjacob/* 61655372Smjacob * ct_flags values for CTIO2 61755372Smjacob */ 61855372Smjacob#define CT2_FLAG_MMASK 0x0003 61955372Smjacob#define CT2_FLAG_MODE0 0x0000 62055372Smjacob#define CT2_FLAG_MODE1 0x0001 62155372Smjacob#define CT2_FLAG_MODE2 0x0002 62255372Smjacob#define CT2_DATA_IN CT_DATA_IN 62355372Smjacob#define CT2_DATA_OUT CT_DATA_OUT 62455372Smjacob#define CT2_NO_DATA CT_NO_DATA 62555372Smjacob#define CT2_DATAMASK CT_DATAMASK 62655372Smjacob#define CT2_CCINCR 0x0100 62755372Smjacob#define CT2_FASTPOST 0x0200 628120016Smjacob#define CT2_TERMINATE 0x4000 62955372Smjacob#define CT2_SENDSTATUS 0x8000 63055372Smjacob 63155372Smjacob/* 63255372Smjacob * ct_status values are (mostly) the same as that for ct_entry. 63355372Smjacob */ 63455372Smjacob 63555372Smjacob/* 63655372Smjacob * ct_scsi_status values- the low 8 bits are the normal SCSI status 63755372Smjacob * we know and love. The upper 8 bits are validity markers for FCP_RSP_IU 63855372Smjacob * fields. 63955372Smjacob */ 64055372Smjacob#define CT2_RSPLEN_VALID 0x0100 64155372Smjacob#define CT2_SNSLEN_VALID 0x0200 64255372Smjacob#define CT2_DATA_OVER 0x0400 64355372Smjacob#define CT2_DATA_UNDER 0x0800 64455372Smjacob 64555372Smjacob/* 64655372Smjacob * Debug macros 64755372Smjacob */ 64855372Smjacob 64955372Smjacob#define ISP_TDQE(isp, msg, idx, arg) \ 65064089Smjacob if (isp->isp_dblev & ISP_LOGTDEBUG2) isp_print_qentry(isp, msg, idx, arg) 65155372Smjacob 65255372Smjacob/* 65387635Smjacob * The functions below are for the publicly available 65487635Smjacob * target mode functions that are internal to the Qlogic driver. 65555372Smjacob */ 65655372Smjacob 65755372Smjacob/* 65855372Smjacob * This function handles new response queue entry appropriate for target mode. 65955372Smjacob */ 660155704Smjacobint isp_target_notify(ispsoftc_t *, void *, uint16_t *); 66155372Smjacob 66255372Smjacob/* 663154704Smjacob * This function externalizes the ability to acknowledge an Immediate Notify 664154704Smjacob * request. 665154704Smjacob */ 666155704Smjacobvoid isp_notify_ack(ispsoftc_t *, void *); 667154704Smjacob 668154704Smjacob/* 66955372Smjacob * Enable/Disable/Modify a logical unit. 67077365Smjacob * (softc, cmd, bus, tgt, lun, cmd_cnt, inotify_cnt, opaque) 67155372Smjacob */ 67298283Smjacob#define DFLT_CMND_CNT 0xfe /* unmonitored */ 673157943Smjacob#define DFLT_INOT_CNT 0xfe /* unmonitored */ 674155704Smjacobint isp_lun_cmd(ispsoftc_t *, int, int, int, int, int, int, uint32_t); 67555372Smjacob 67655372Smjacob/* 67755372Smjacob * General request queue 'put' routine for target mode entries. 67855372Smjacob */ 679155704Smjacobint isp_target_put_entry(ispsoftc_t *isp, void *); 68055372Smjacob 68155372Smjacob/* 68255372Smjacob * General routine to put back an ATIO entry- 68355372Smjacob * used for replenishing f/w resource counts. 68475195Smjacob * The argument is a pointer to a source ATIO 68575195Smjacob * or ATIO2. 68655372Smjacob */ 687155704Smjacobint isp_target_put_atio(ispsoftc_t *, void *); 68855372Smjacob 68955372Smjacob/* 69055372Smjacob * General routine to send a final CTIO for a command- used mostly for 69155372Smjacob * local responses. 69255372Smjacob */ 693155704Smjacobint isp_endcmd(ispsoftc_t *, void *, uint32_t, uint16_t); 69456005Smjacob#define ECMD_SVALID 0x100 69555372Smjacob 69655372Smjacob/* 69755372Smjacob * Handle an asynchronous event 69898283Smjacob * 69998283Smjacob * Return nonzero if the interrupt that generated this event has been dismissed. 70055372Smjacob */ 701155704Smjacobint isp_target_async(ispsoftc_t *, int, int); 70255372Smjacob 70374231Smjacob#endif /* _ISP_TARGET_H */ 704