1 /* $NetBSD: mhavar.h,v 1.13 2026/01/02 23:33:58 nia Exp $ */ 2 3 /* 4 * Copyright (c) 1994 Peter Galbavy. All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 3. The name of the author may not be used to endorse or promote products 15 * derived from this software without specific prior written permission. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29 /* 30 * ACB. Holds additional information for each SCSI command Comments: We 31 * need a separate scsi command block because we may need to overwrite it 32 * with a request sense command. Basically, we refrain from fiddling with 33 * the scsi_xfer struct (except do the expected updating of return values). 34 * We'll generally update: xs->{flags,resid,error,sense,status} and 35 * occasionally xs->retries. 36 */ 37 struct acb { 38 TAILQ_ENTRY(acb) chain; 39 struct scsipi_xfer *xs; /* SCSI xfer ctrl block from above */ 40 int flags; /* Status */ 41 #define ACB_QNONE 0 42 #define ACB_QFREE 1 43 #define ACB_QREADY 2 44 #define ACB_QNEXUS 3 45 46 #define ACB_QBITS 0x07 47 #define ACB_CHKSENSE 0x08 48 #define ACB_ABORTED 0x10 49 #define ACB_RESET 0x80 50 #define ACB_SETQ(e, q) do (e)->flags = ((e)->flags&~ACB_QBITS)|(q); while(0) 51 struct scsipi_generic cmd; /* SCSI command block */ 52 int clen; 53 char *daddr; /* Saved data pointer */ 54 int dleft; /* Residue */ 55 u_char stat; /* SCSI status byte */ 56 57 /* struct spc_dma_seg dma[SPC_NSEG];*/ /* Physical addresses+len */ 58 }; 59 60 /* 61 * Some info about each (possible) target on the SCSI bus. This should 62 * probably have been a "per target+lunit" structure, but we'll leave it at 63 * this for now. 64 */ 65 struct spc_tinfo { 66 int cmds; /* #commands processed */ 67 int dconns; /* #disconnects */ 68 int touts; /* #timeouts */ 69 int perrs; /* #parity errors */ 70 int senses; /* #request sense commands sent */ 71 ushort lubusy; /* What local units/subr. are busy? */ 72 u_char flags; 73 #define T_NEED_TO_RESET 0x01 /* Should send a BUS_DEV_RESET */ 74 #define T_NEGOTIATE 0x02 /* (Re)Negotiate synchronous options */ 75 #define T_BUSY 0x04 /* Target is busy, i.e. cmd in progress */ 76 #define T_SYNCMODE 0x08 /* sync mode has been negotiated */ 77 #define T_SYNCHOFF 0x10 /* .. */ 78 #define T_RSELECTOFF 0x20 /* .. */ 79 u_char period; /* Period suggestion */ 80 u_char offset; /* Offset suggestion */ 81 u_char width; /* Width suggestion */ 82 }; 83 84 struct mha_softc { 85 device_t sc_dev; 86 volatile void *sc_iobase; 87 volatile u_char *sc_pc; 88 volatile u_short *sc_ps; 89 volatile u_char *sc_pcx; 90 91 struct scsipi_channel sc_channel; 92 struct scsipi_adapter sc_adapter; 93 94 TAILQ_HEAD(, acb) free_list, ready_list, nexus_list; 95 struct acb *sc_nexus; /* current command */ 96 struct acb sc_acb[8]; /* one per target */ 97 struct spc_tinfo sc_tinfo[8]; 98 99 /* Data about the current nexus (updated for every cmd switch) */ 100 u_char *sc_dp; /* Current data pointer */ 101 size_t sc_dleft; /* Data bytes left to transfer */ 102 103 u_char *sc_cp; /* Current command pointer */ 104 size_t sc_cleft; /* Command bytes left to transfer */ 105 106 /* Adapter state */ 107 int sc_phase; /* Copy of what bus phase we are in */ 108 int sc_prevphase; /* Copy of what bus phase we were in */ 109 u_char sc_state; /* State applicable to the adapter */ 110 u_char sc_flags; 111 u_char sc_selid; /* Reselection ID */ 112 volatile u_char sc_spcinitialized; /* */ 113 114 /* Message stuff */ 115 u_char sc_msgpriq; /* Messages we want to send */ 116 u_char sc_msgout; /* What message is on its way out? */ 117 u_char sc_msgoutq; /* Messages sent during last MESSAGE OUT */ 118 u_char sc_lastmsg; /* Message last transmitted */ 119 u_char sc_currmsg; /* Message currently ready to transmit */ 120 #define SPC_MAX_MSG_LEN 8 121 u_char sc_omess[SPC_MAX_MSG_LEN]; 122 u_char *sc_omp; /* Outgoing message pointer */ 123 u_char sc_imess[SPC_MAX_MSG_LEN]; 124 u_char *sc_imp; /* Incoming message pointer */ 125 size_t sc_imlen; 126 127 /* Hardware stuff */ 128 int sc_freq; /* Clock frequency in MHz */ 129 int sc_id; /* our scsi id */ 130 int sc_minsync; /* Minimum sync period / 4 */ 131 int sc_maxsync; /* Maximum sync period / 4 */ 132 133 /* DMA buffer */ 134 bus_dma_tag_t sc_dmat; 135 bus_dma_segment_t sc_dmaseg[1]; 136 int sc_ndmasegs; 137 bus_dmamap_t sc_dmamap; 138 void * sc_dmabuf; 139 u_char *sc_p; 140 u_int32_t sc_dmasize; 141 }; 142 143 /* values for sc_state */ 144 #define SPC_INIT 0x00 145 #define SPC_IDLE 0x01 /* waiting for something to do */ 146 #define ESP_TMP_UNAVAIL 0x02 /* Don't accept SCSI commands */ 147 #define SPC_SELECTING 0x03 /* SCSI command is arbiting */ 148 #define SPC_RESELECTED 0x04 /* Has been reselected */ 149 #define SPC_HASNEXUS 0x05 /* Actively using the SCSI bus */ 150 #define SPC_CLEANING 0x06 151 #define ESP_SBR 0x07 /* Expect a SCSI RST because we commanded it */ 152 #define SPC_CONNECTED 0x08 /* Actively using the SCSI bus */ 153 #define SPC_DISCONNECT 0x09 /* MSG_DISCONNECT received */ 154 #define SPC_CMDCOMPLETE 0x0a /* MSG_CMDCOMPLETE received */ 155 156 157 /* values for sc_flags */ 158 #define SPC_DROP_MSGI 0x01 /* Discard all msgs (parity err detected) */ 159 #define SPC_DOINGDMA 0x02 /* The FIFO data path is active! */ 160 #define SPC_BUSFREE_OK 0x04 /* Bus free phase is OK. */ 161 #define SPC_SYNCHNEGO 0x08 /* Synch negotiation in progress. */ 162 #define SPC_DISCON 0x10 /* Target sent DISCONNECT msg */ 163 #define SPC_ABORTING 0x20 /* Bailing out */ 164 #define ESP_ICCS 0x40 /* Expect status phase results */ 165 #define ESP_WAITI 0x80 /* Waiting for non-DMA data to arrive */ 166 167 168 /* values for sc_msgout */ 169 #define SEND_DEV_RESET 0x01 170 #define SEND_PARITY_ERROR 0x02 171 #define SEND_INIT_DET_ERR 0x04 172 #define SEND_REJECT 0x08 173 #define SEND_IDENTIFY 0x10 174 #define SEND_ABORT 0x20 175 #define SEND_SDTR 0x40 176 #define SEND_WDTR 0x80 177 178 /* SCSI Status codes */ 179 #define ST_GOOD 0x00 180 #define ST_CHKCOND 0x02 181 #define ST_CONDMET 0x04 182 #define ST_BUSY 0x08 183 #define ST_INTERMED 0x10 184 #define ST_INTERMED_CONDMET 0x14 185 #define ST_RESERVATION_CONFLICT 0x18 186 #define ST_CMD_TERM 0x22 187 #define ST_QUEUE_FULL 0x28 188 189 #define ST_MASK 0x3e /* bit 0,6,7 is reserved */ 190 191 /* phase bits */ 192 #define IOI 0x01 193 #define CDI 0x02 194 #define MSGI 0x04 195 196 /* Information transfer phases */ 197 #define DATA_OUT_PHASE (0) 198 #define DATA_IN_PHASE (IOI) 199 #define COMMAND_PHASE (CDI) 200 #define STATUS_PHASE (CDI|IOI) 201 #define MESSAGE_OUT_PHASE (MSGI|CDI) 202 #define MESSAGE_IN_PHASE (MSGI|CDI|IOI) 203 204 #define PHASE_MASK (MSGI|CDI|IOI) 205 206 /* Some pseudo phases for getphase()*/ 207 #define BUSFREE_PHASE 0x100 /* Re/Selection no longer valid */ 208 #define INVALID_PHASE 0x101 /* Re/Selection valid, but no REQ yet */ 209 #define PSEUDO_PHASE 0x100 /* "pseudo" bit */ 210