xref: /dragonfly/sys/dev/disk/isp/isp.c (revision 0db87cb7)
1 /*-
2  *  Copyright (c) 1997-2009 by Matthew Jacob
3  *  All rights reserved.
4  *
5  *  Redistribution and use in source and binary forms, with or without
6  *  modification, are permitted provided that the following conditions
7  *  are met:
8  *
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  *
15  *  THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16  *  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  *  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  *  ARE DISCLAIMED.  IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
19  *  FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20  *  DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21  *  OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  *  HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23  *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24  *  OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25  *  SUCH DAMAGE.
26  *
27  * $FreeBSD: src/sys/dev/isp/isp.c,v 1.168 2011/11/16 02:52:24 mjacob Exp $
28  */
29 
30 /*
31  * Machine and OS Independent (well, as best as possible)
32  * code for the Qlogic ISP SCSI and FC-SCSI adapters.
33  */
34 
35 /*
36  * Inspiration and ideas about this driver are from Erik Moe's Linux driver
37  * (qlogicisp.c) and Dave Miller's SBus version of same (qlogicisp.c). Some
38  * ideas dredged from the Solaris driver.
39  */
40 
41 /*
42  * Include header file appropriate for platform we're building on.
43  */
44 #include <dev/disk/isp/isp_freebsd.h>
45 
46 /*
47  * General defines
48  */
49 #define	MBOX_DELAY_COUNT	1000000 / 100
50 #define	ISP_MARK_PORTDB(a, b, c)				\
51     isp_prt(isp, ISP_LOGSANCFG, 				\
52 	"Chan %d ISP_MARK_PORTDB@LINE %d", b, __LINE__);	\
53     isp_mark_portdb(a, b, c)
54 
55 /*
56  * Local static data
57  */
58 static const char fconf[] = "Chan %d PortDB[%d] changed:\n current =(0x%x@0x%06x 0x%08x%08x 0x%08x%08x)\n database=(0x%x@0x%06x 0x%08x%08x 0x%08x%08x)";
59 static const char notresp[] = "Not RESPONSE in RESPONSE Queue (type 0x%x) @ idx %d (next %d) nlooked %d";
60 static const char topology[] = "Chan %d WWPN 0x%08x%08x PortID 0x%06x N-Port Handle %d, Connection '%s'";
61 static const char sc4[] = "NVRAM";
62 static const char bun[] = "bad underrun (count %d, resid %d, status %s)";
63 static const char lipd[] = "Chan %d LIP destroyed %d active commands";
64 static const char sacq[] = "unable to acquire scratch area";
65 
66 static const uint8_t alpa_map[] = {
67 	0xef, 0xe8, 0xe4, 0xe2, 0xe1, 0xe0, 0xdc, 0xda,
68 	0xd9, 0xd6, 0xd5, 0xd4, 0xd3, 0xd2, 0xd1, 0xce,
69 	0xcd, 0xcc, 0xcb, 0xca, 0xc9, 0xc7, 0xc6, 0xc5,
70 	0xc3, 0xbc, 0xba, 0xb9, 0xb6, 0xb5, 0xb4, 0xb3,
71 	0xb2, 0xb1, 0xae, 0xad, 0xac, 0xab, 0xaa, 0xa9,
72 	0xa7, 0xa6, 0xa5, 0xa3, 0x9f, 0x9e, 0x9d, 0x9b,
73 	0x98, 0x97, 0x90, 0x8f, 0x88, 0x84, 0x82, 0x81,
74 	0x80, 0x7c, 0x7a, 0x79, 0x76, 0x75, 0x74, 0x73,
75 	0x72, 0x71, 0x6e, 0x6d, 0x6c, 0x6b, 0x6a, 0x69,
76 	0x67, 0x66, 0x65, 0x63, 0x5c, 0x5a, 0x59, 0x56,
77 	0x55, 0x54, 0x53, 0x52, 0x51, 0x4e, 0x4d, 0x4c,
78 	0x4b, 0x4a, 0x49, 0x47, 0x46, 0x45, 0x43, 0x3c,
79 	0x3a, 0x39, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31,
80 	0x2e, 0x2d, 0x2c, 0x2b, 0x2a, 0x29, 0x27, 0x26,
81 	0x25, 0x23, 0x1f, 0x1e, 0x1d, 0x1b, 0x18, 0x17,
82 	0x10, 0x0f, 0x08, 0x04, 0x02, 0x01, 0x00
83 };
84 
85 /*
86  * Local function prototypes.
87  */
88 static int isp_parse_async(ispsoftc_t *, uint16_t);
89 static int isp_parse_async_fc(ispsoftc_t *, uint16_t);
90 static int isp_handle_other_response(ispsoftc_t *, int, isphdr_t *, uint32_t *);
91 static void isp_parse_status(ispsoftc_t *, ispstatusreq_t *, XS_T *, long *); static void
92 isp_parse_status_24xx(ispsoftc_t *, isp24xx_statusreq_t *, XS_T *, long *);
93 static void isp_fastpost_complete(ispsoftc_t *, uint32_t);
94 static int isp_mbox_continue(ispsoftc_t *);
95 static void isp_scsi_init(ispsoftc_t *);
96 static void isp_scsi_channel_init(ispsoftc_t *, int);
97 static void isp_fibre_init(ispsoftc_t *);
98 static void isp_fibre_init_2400(ispsoftc_t *);
99 static void isp_mark_portdb(ispsoftc_t *, int, int);
100 static int isp_plogx(ispsoftc_t *, int, uint16_t, uint32_t, int, int);
101 static int isp_port_login(ispsoftc_t *, uint16_t, uint32_t);
102 static int isp_port_logout(ispsoftc_t *, uint16_t, uint32_t);
103 static int isp_getpdb(ispsoftc_t *, int, uint16_t, isp_pdb_t *, int);
104 static void isp_dump_chip_portdb(ispsoftc_t *, int, int);
105 static uint64_t isp_get_wwn(ispsoftc_t *, int, int, int);
106 static int isp_fclink_test(ispsoftc_t *, int, int);
107 static int isp_pdb_sync(ispsoftc_t *, int);
108 static int isp_scan_loop(ispsoftc_t *, int);
109 static int isp_gid_ft_sns(ispsoftc_t *, int);
110 static int isp_gid_ft_ct_passthru(ispsoftc_t *, int);
111 static int isp_scan_fabric(ispsoftc_t *, int);
112 static int isp_login_device(ispsoftc_t *, int, uint32_t, isp_pdb_t *, uint16_t *);
113 static int isp_register_fc4_type(ispsoftc_t *, int);
114 static int isp_register_fc4_type_24xx(ispsoftc_t *, int);
115 static uint16_t isp_nxt_handle(ispsoftc_t *, int, uint16_t);
116 static void isp_fw_state(ispsoftc_t *, int);
117 static void isp_mboxcmd_qnw(ispsoftc_t *, mbreg_t *, int);
118 static void isp_mboxcmd(ispsoftc_t *, mbreg_t *);
119 
120 static void isp_spi_update(ispsoftc_t *, int);
121 static void isp_setdfltsdparm(ispsoftc_t *);
122 static void isp_setdfltfcparm(ispsoftc_t *, int);
123 static int isp_read_nvram(ispsoftc_t *, int);
124 static int isp_read_nvram_2400(ispsoftc_t *, uint8_t *);
125 static void isp_rdnvram_word(ispsoftc_t *, int, uint16_t *);
126 static void isp_rd_2400_nvram(ispsoftc_t *, uint32_t, uint32_t *);
127 static void isp_parse_nvram_1020(ispsoftc_t *, uint8_t *);
128 static void isp_parse_nvram_1080(ispsoftc_t *, int, uint8_t *);
129 static void isp_parse_nvram_12160(ispsoftc_t *, int, uint8_t *);
130 static void isp_parse_nvram_2100(ispsoftc_t *, uint8_t *);
131 static void isp_parse_nvram_2400(ispsoftc_t *, uint8_t *);
132 
133 /*
134  * Reset Hardware.
135  *
136  * Hit the chip over the head, download new f/w if available and set it running.
137  *
138  * Locking done elsewhere.
139  */
140 
141 void
142 isp_reset(ispsoftc_t *isp, int do_load_defaults)
143 {
144 	mbreg_t mbs;
145 	uint32_t code_org, val;
146 	int loops, i, dodnld = 1;
147 	const char *btype = "????";
148 	static const char dcrc[] = "Downloaded RISC Code Checksum Failure";
149 
150 	isp->isp_state = ISP_NILSTATE;
151 	if (isp->isp_dead) {
152 		isp_shutdown(isp);
153 		ISP_DISABLE_INTS(isp);
154 		return;
155 	}
156 
157 	/*
158 	 * Basic types (SCSI, FibreChannel and PCI or SBus)
159 	 * have been set in the MD code. We figure out more
160 	 * here. Possibly more refined types based upon PCI
161 	 * identification. Chip revision has been gathered.
162 	 *
163 	 * After we've fired this chip up, zero out the conf1 register
164 	 * for SCSI adapters and do other settings for the 2100.
165 	 */
166 
167 	ISP_DISABLE_INTS(isp);
168 
169 	/*
170 	 * Pick an initial maxcmds value which will be used
171 	 * to allocate xflist pointer space. It may be changed
172 	 * later by the firmware.
173 	 */
174 	if (IS_24XX(isp)) {
175 		isp->isp_maxcmds = 4096;
176 	} else if (IS_2322(isp)) {
177 		isp->isp_maxcmds = 2048;
178 	} else if (IS_23XX(isp) || IS_2200(isp)) {
179 		isp->isp_maxcmds = 1024;
180 	} else {
181 		isp->isp_maxcmds = 512;
182 	}
183 
184 	/*
185 	 * Set up DMA for the request and response queues.
186 	 *
187 	 * We do this now so we can use the request queue
188 	 * for dma to load firmware from.
189 	 */
190 	if (ISP_MBOXDMASETUP(isp) != 0) {
191 		isp_prt(isp, ISP_LOGERR, "Cannot setup DMA");
192 		return;
193 	}
194 
195 	/*
196 	 * Set up default request/response queue in-pointer/out-pointer
197 	 * register indices.
198 	 */
199 	if (IS_24XX(isp)) {
200 		isp->isp_rqstinrp = BIU2400_REQINP;
201 		isp->isp_rqstoutrp = BIU2400_REQOUTP;
202 		isp->isp_respinrp = BIU2400_RSPINP;
203 		isp->isp_respoutrp = BIU2400_RSPOUTP;
204 	} else if (IS_23XX(isp)) {
205 		isp->isp_rqstinrp = BIU_REQINP;
206 		isp->isp_rqstoutrp = BIU_REQOUTP;
207 		isp->isp_respinrp = BIU_RSPINP;
208 		isp->isp_respoutrp = BIU_RSPOUTP;
209 	} else {
210 		isp->isp_rqstinrp = INMAILBOX4;
211 		isp->isp_rqstoutrp = OUTMAILBOX4;
212 		isp->isp_respinrp = OUTMAILBOX5;
213 		isp->isp_respoutrp = INMAILBOX5;
214 	}
215 
216 	/*
217 	 * Put the board into PAUSE mode (so we can read the SXP registers
218 	 * or write FPM/FBM registers).
219 	 */
220 	if (IS_24XX(isp)) {
221 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_CLEAR_HOST_INT);
222 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_CLEAR_RISC_INT);
223 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_PAUSE);
224 	} else {
225 		ISP_WRITE(isp, HCCR, HCCR_CMD_PAUSE);
226 	}
227 
228 	if (IS_FC(isp)) {
229 		switch (isp->isp_type) {
230 		case ISP_HA_FC_2100:
231 			btype = "2100";
232 			break;
233 		case ISP_HA_FC_2200:
234 			btype = "2200";
235 			break;
236 		case ISP_HA_FC_2300:
237 			btype = "2300";
238 			break;
239 		case ISP_HA_FC_2312:
240 			btype = "2312";
241 			break;
242 		case ISP_HA_FC_2322:
243 			btype = "2322";
244 			break;
245 		case ISP_HA_FC_2400:
246 			btype = "2422";
247 			break;
248 		case ISP_HA_FC_2500:
249 			btype = "2532";
250 			break;
251 		default:
252 			break;
253 		}
254 
255 		if (!IS_24XX(isp)) {
256 			/*
257 			 * While we're paused, reset the FPM module and FBM
258 			 * fifos.
259 			 */
260 			ISP_WRITE(isp, BIU2100_CSR, BIU2100_FPM0_REGS);
261 			ISP_WRITE(isp, FPM_DIAG_CONFIG, FPM_SOFT_RESET);
262 			ISP_WRITE(isp, BIU2100_CSR, BIU2100_FB_REGS);
263 			ISP_WRITE(isp, FBM_CMD, FBMCMD_FIFO_RESET_ALL);
264 			ISP_WRITE(isp, BIU2100_CSR, BIU2100_RISC_REGS);
265 		}
266 	} else if (IS_1240(isp)) {
267 		sdparam *sdp;
268 
269 		btype = "1240";
270 		isp->isp_clock = 60;
271 		sdp = SDPARAM(isp, 0);
272 		sdp->isp_ultramode = 1;
273 		sdp = SDPARAM(isp, 1);
274 		sdp->isp_ultramode = 1;
275 		/*
276 		 * XXX: Should probably do some bus sensing.
277 		 */
278 	} else if (IS_ULTRA3(isp)) {
279 		sdparam *sdp = isp->isp_param;
280 
281 		isp->isp_clock = 100;
282 
283 		if (IS_10160(isp))
284 			btype = "10160";
285 		else if (IS_12160(isp))
286 			btype = "12160";
287 		else
288 			btype = "<UNKLVD>";
289 		sdp->isp_lvdmode = 1;
290 
291 		if (IS_DUALBUS(isp)) {
292 			sdp++;
293 			sdp->isp_lvdmode = 1;
294 		}
295 	} else if (IS_ULTRA2(isp)) {
296 		static const char m[] = "bus %d is in %s Mode";
297 		uint16_t l;
298 		sdparam *sdp = SDPARAM(isp, 0);
299 
300 		isp->isp_clock = 100;
301 
302 		if (IS_1280(isp))
303 			btype = "1280";
304 		else if (IS_1080(isp))
305 			btype = "1080";
306 		else
307 			btype = "<UNKLVD>";
308 
309 		l = ISP_READ(isp, SXP_PINS_DIFF) & ISP1080_MODE_MASK;
310 		switch (l) {
311 		case ISP1080_LVD_MODE:
312 			sdp->isp_lvdmode = 1;
313 			isp_prt(isp, ISP_LOGCONFIG, m, 0, "LVD");
314 			break;
315 		case ISP1080_HVD_MODE:
316 			sdp->isp_diffmode = 1;
317 			isp_prt(isp, ISP_LOGCONFIG, m, 0, "Differential");
318 			break;
319 		case ISP1080_SE_MODE:
320 			sdp->isp_ultramode = 1;
321 			isp_prt(isp, ISP_LOGCONFIG, m, 0, "Single-Ended");
322 			break;
323 		default:
324 			isp_prt(isp, ISP_LOGERR,
325 			    "unknown mode on bus %d (0x%x)", 0, l);
326 			break;
327 		}
328 
329 		if (IS_DUALBUS(isp)) {
330 			sdp = SDPARAM(isp, 1);
331 			l = ISP_READ(isp, SXP_PINS_DIFF|SXP_BANK1_SELECT);
332 			l &= ISP1080_MODE_MASK;
333 			switch (l) {
334 			case ISP1080_LVD_MODE:
335 				sdp->isp_lvdmode = 1;
336 				isp_prt(isp, ISP_LOGCONFIG, m, 1, "LVD");
337 				break;
338 			case ISP1080_HVD_MODE:
339 				sdp->isp_diffmode = 1;
340 				isp_prt(isp, ISP_LOGCONFIG,
341 				    m, 1, "Differential");
342 				break;
343 			case ISP1080_SE_MODE:
344 				sdp->isp_ultramode = 1;
345 				isp_prt(isp, ISP_LOGCONFIG,
346 				    m, 1, "Single-Ended");
347 				break;
348 			default:
349 				isp_prt(isp, ISP_LOGERR,
350 				    "unknown mode on bus %d (0x%x)", 1, l);
351 				break;
352 			}
353 		}
354 	} else {
355 		sdparam *sdp = SDPARAM(isp, 0);
356 		i = ISP_READ(isp, BIU_CONF0) & BIU_CONF0_HW_MASK;
357 		switch (i) {
358 		default:
359 			isp_prt(isp, ISP_LOGALL, "Unknown Chip Type 0x%x", i);
360 			/* FALLTHROUGH */
361 		case 1:
362 			btype = "1020";
363 			isp->isp_type = ISP_HA_SCSI_1020;
364 			isp->isp_clock = 40;
365 			break;
366 		case 2:
367 			/*
368 			 * Some 1020A chips are Ultra Capable, but don't
369 			 * run the clock rate up for that unless told to
370 			 * do so by the Ultra Capable bits being set.
371 			 */
372 			btype = "1020A";
373 			isp->isp_type = ISP_HA_SCSI_1020A;
374 			isp->isp_clock = 40;
375 			break;
376 		case 3:
377 			btype = "1040";
378 			isp->isp_type = ISP_HA_SCSI_1040;
379 			isp->isp_clock = 60;
380 			break;
381 		case 4:
382 			btype = "1040A";
383 			isp->isp_type = ISP_HA_SCSI_1040A;
384 			isp->isp_clock = 60;
385 			break;
386 		case 5:
387 			btype = "1040B";
388 			isp->isp_type = ISP_HA_SCSI_1040B;
389 			isp->isp_clock = 60;
390 			break;
391 		case 6:
392 			btype = "1040C";
393 			isp->isp_type = ISP_HA_SCSI_1040C;
394 			isp->isp_clock = 60;
395                         break;
396 		}
397 		/*
398 		 * Now, while we're at it, gather info about ultra
399 		 * and/or differential mode.
400 		 */
401 		if (ISP_READ(isp, SXP_PINS_DIFF) & SXP_PINS_DIFF_MODE) {
402 			isp_prt(isp, ISP_LOGCONFIG, "Differential Mode");
403 			sdp->isp_diffmode = 1;
404 		} else {
405 			sdp->isp_diffmode = 0;
406 		}
407 		i = ISP_READ(isp, RISC_PSR);
408 		if (isp->isp_bustype == ISP_BT_SBUS) {
409 			i &= RISC_PSR_SBUS_ULTRA;
410 		} else {
411 			i &= RISC_PSR_PCI_ULTRA;
412 		}
413 		if (i != 0) {
414 			isp_prt(isp, ISP_LOGCONFIG, "Ultra Mode Capable");
415 			sdp->isp_ultramode = 1;
416 			/*
417 			 * If we're in Ultra Mode, we have to be 60MHz clock-
418 			 * even for the SBus version.
419 			 */
420 			isp->isp_clock = 60;
421 		} else {
422 			sdp->isp_ultramode = 0;
423 			/*
424 			 * Clock is known. Gronk.
425 			 */
426 		}
427 
428 		/*
429 		 * Machine dependent clock (if set) overrides
430 		 * our generic determinations.
431 		 */
432 		if (isp->isp_mdvec->dv_clock) {
433 			if (isp->isp_mdvec->dv_clock < isp->isp_clock) {
434 				isp->isp_clock = isp->isp_mdvec->dv_clock;
435 			}
436 		}
437 
438 	}
439 
440 	/*
441 	 * Clear instrumentation
442 	 */
443 	isp->isp_intcnt = isp->isp_intbogus = 0;
444 
445 	/*
446 	 * Do MD specific pre initialization
447 	 */
448 	ISP_RESET0(isp);
449 
450 	/*
451 	 * Hit the chip over the head with hammer,
452 	 * and give it a chance to recover.
453 	 */
454 
455 	if (IS_SCSI(isp)) {
456 		ISP_WRITE(isp, BIU_ICR, BIU_ICR_SOFT_RESET);
457 		/*
458 		 * A slight delay...
459 		 */
460 		ISP_DELAY(100);
461 
462 		/*
463 		 * Clear data && control DMA engines.
464 		 */
465 		ISP_WRITE(isp, CDMA_CONTROL, DMA_CNTRL_CLEAR_CHAN | DMA_CNTRL_RESET_INT);
466 		ISP_WRITE(isp, DDMA_CONTROL, DMA_CNTRL_CLEAR_CHAN | DMA_CNTRL_RESET_INT);
467 
468 
469 	} else if (IS_24XX(isp)) {
470 		/*
471 		 * Stop DMA and wait for it to stop.
472 		 */
473 		ISP_WRITE(isp, BIU2400_CSR, BIU2400_DMA_STOP|(3 << 4));
474 		for (val = loops = 0; loops < 30000; loops++) {
475 			ISP_DELAY(10);
476 			val = ISP_READ(isp, BIU2400_CSR);
477 			if ((val & BIU2400_DMA_ACTIVE) == 0) {
478 				break;
479 			}
480 		}
481 		if (val & BIU2400_DMA_ACTIVE) {
482 			ISP_RESET0(isp);
483 			isp_prt(isp, ISP_LOGERR, "DMA Failed to Stop on Reset");
484 			return;
485 		}
486 		/*
487 		 * Hold it in SOFT_RESET and STOP state for 100us.
488 		 */
489 		ISP_WRITE(isp, BIU2400_CSR, BIU2400_SOFT_RESET|BIU2400_DMA_STOP|(3 << 4));
490 		ISP_DELAY(100);
491 		for (loops = 0; loops < 10000; loops++) {
492 			ISP_DELAY(5);
493 			val = ISP_READ(isp, OUTMAILBOX0);
494 		}
495 		for (val = loops = 0; loops < 500000; loops ++) {
496 			val = ISP_READ(isp, BIU2400_CSR);
497 			if ((val & BIU2400_SOFT_RESET) == 0) {
498 				break;
499 			}
500 		}
501 		if (val & BIU2400_SOFT_RESET) {
502 			ISP_RESET0(isp);
503 			isp_prt(isp, ISP_LOGERR, "Failed to come out of reset");
504 			return;
505 		}
506 	} else {
507 		ISP_WRITE(isp, BIU2100_CSR, BIU2100_SOFT_RESET);
508 		/*
509 		 * A slight delay...
510 		 */
511 		ISP_DELAY(100);
512 
513 		/*
514 		 * Clear data && control DMA engines.
515 		 */
516 		ISP_WRITE(isp, CDMA2100_CONTROL, DMA_CNTRL2100_CLEAR_CHAN | DMA_CNTRL2100_RESET_INT);
517 		ISP_WRITE(isp, TDMA2100_CONTROL, DMA_CNTRL2100_CLEAR_CHAN | DMA_CNTRL2100_RESET_INT);
518 		ISP_WRITE(isp, RDMA2100_CONTROL, DMA_CNTRL2100_CLEAR_CHAN | DMA_CNTRL2100_RESET_INT);
519 	}
520 
521 	/*
522 	 * Wait for ISP to be ready to go...
523 	 */
524 	loops = MBOX_DELAY_COUNT;
525 	for (;;) {
526 		if (IS_SCSI(isp)) {
527 			if (!(ISP_READ(isp, BIU_ICR) & BIU_ICR_SOFT_RESET)) {
528 				break;
529 			}
530 		} else if (IS_24XX(isp)) {
531 			if (ISP_READ(isp, OUTMAILBOX0) == 0) {
532 				break;
533 			}
534 		} else {
535 			if (!(ISP_READ(isp, BIU2100_CSR) & BIU2100_SOFT_RESET))
536 				break;
537 		}
538 		ISP_DELAY(100);
539 		if (--loops < 0) {
540 			ISP_DUMPREGS(isp, "chip reset timed out");
541 			ISP_RESET0(isp);
542 			return;
543 		}
544 	}
545 
546 	/*
547 	 * After we've fired this chip up, zero out the conf1 register
548 	 * for SCSI adapters and other settings for the 2100.
549 	 */
550 
551 	if (IS_SCSI(isp)) {
552 		ISP_WRITE(isp, BIU_CONF1, 0);
553 	} else if (!IS_24XX(isp)) {
554 		ISP_WRITE(isp, BIU2100_CSR, 0);
555 	}
556 
557 	/*
558 	 * Reset RISC Processor
559 	 */
560 	if (IS_24XX(isp)) {
561 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_RESET);
562 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_RELEASE);
563 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_CLEAR_RESET);
564 	} else {
565 		ISP_WRITE(isp, HCCR, HCCR_CMD_RESET);
566 		ISP_DELAY(100);
567 		ISP_WRITE(isp, BIU_SEMA, 0);
568 	}
569 
570 	/*
571 	 * Post-RISC Reset stuff.
572 	 */
573 	if (IS_24XX(isp)) {
574 		for (val = loops = 0; loops < 5000000; loops++) {
575 			ISP_DELAY(5);
576 			val = ISP_READ(isp, OUTMAILBOX0);
577 			if (val == 0) {
578 				break;
579 			}
580 		}
581 		if (val != 0) {
582 			ISP_RESET0(isp);
583 			isp_prt(isp, ISP_LOGERR, "reset didn't clear");
584 			return;
585 		}
586 	} else if (IS_SCSI(isp)) {
587 		uint16_t tmp = isp->isp_mdvec->dv_conf1;
588 		/*
589 		 * Busted FIFO. Turn off all but burst enables.
590 		 */
591 		if (isp->isp_type == ISP_HA_SCSI_1040A) {
592 			tmp &= BIU_BURST_ENABLE;
593 		}
594 		ISP_SETBITS(isp, BIU_CONF1, tmp);
595 		if (tmp & BIU_BURST_ENABLE) {
596 			ISP_SETBITS(isp, CDMA_CONF, DMA_ENABLE_BURST);
597 			ISP_SETBITS(isp, DDMA_CONF, DMA_ENABLE_BURST);
598 		}
599 		if (SDPARAM(isp, 0)->isp_ptisp) {
600 			if (SDPARAM(isp, 0)->isp_ultramode) {
601 				while (ISP_READ(isp, RISC_MTR) != 0x1313) {
602 					ISP_WRITE(isp, RISC_MTR, 0x1313);
603 					ISP_WRITE(isp, HCCR, HCCR_CMD_STEP);
604 				}
605 			} else {
606 				ISP_WRITE(isp, RISC_MTR, 0x1212);
607 			}
608 			/*
609 			 * PTI specific register
610 			 */
611 			ISP_WRITE(isp, RISC_EMB, DUAL_BANK);
612 		} else {
613 			ISP_WRITE(isp, RISC_MTR, 0x1212);
614 		}
615 		ISP_WRITE(isp, HCCR, HCCR_CMD_RELEASE);
616 	} else {
617 		ISP_WRITE(isp, RISC_MTR2100, 0x1212);
618 		if (IS_2200(isp) || IS_23XX(isp)) {
619 			ISP_WRITE(isp, HCCR, HCCR_2X00_DISABLE_PARITY_PAUSE);
620 		}
621 		ISP_WRITE(isp, HCCR, HCCR_CMD_RELEASE);
622 	}
623 
624 	ISP_WRITE(isp, isp->isp_rqstinrp, 0);
625 	ISP_WRITE(isp, isp->isp_rqstoutrp, 0);
626 	ISP_WRITE(isp, isp->isp_respinrp, 0);
627 	ISP_WRITE(isp, isp->isp_respoutrp, 0);
628 	if (IS_24XX(isp)) {
629 		ISP_WRITE(isp, BIU2400_PRI_REQINP, 0);
630 		ISP_WRITE(isp, BIU2400_PRI_REQOUTP, 0);
631 		ISP_WRITE(isp, BIU2400_ATIO_RSPINP, 0);
632 		ISP_WRITE(isp, BIU2400_ATIO_RSPOUTP, 0);
633 	}
634 
635 	/*
636 	 * Do MD specific post initialization
637 	 */
638 	ISP_RESET1(isp);
639 
640 	/*
641 	 * Wait for everything to finish firing up.
642 	 *
643 	 * Avoid doing this on early 2312s because you can generate a PCI
644 	 * parity error (chip breakage).
645 	 */
646 	if (IS_2312(isp) && isp->isp_revision < 2) {
647 		ISP_DELAY(100);
648 	} else {
649 		loops = MBOX_DELAY_COUNT;
650 		while (ISP_READ(isp, OUTMAILBOX0) == MBOX_BUSY) {
651 			ISP_DELAY(100);
652 			if (--loops < 0) {
653 				ISP_RESET0(isp);
654 				isp_prt(isp, ISP_LOGERR,
655 				    "MBOX_BUSY never cleared on reset");
656 				return;
657 			}
658 		}
659 	}
660 
661 	/*
662 	 * Up until this point we've done everything by just reading or
663 	 * setting registers. From this point on we rely on at least *some*
664 	 * kind of firmware running in the card.
665 	 */
666 
667 	/*
668 	 * Do some sanity checking by running a NOP command.
669 	 * If it succeeds, the ROM firmware is now running.
670 	 */
671 	ISP_MEMZERO(&mbs, sizeof (mbs));
672 	mbs.param[0] = MBOX_NO_OP;
673 	mbs.logval = MBLOGALL;
674 	isp_mboxcmd(isp, &mbs);
675 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
676 		isp_prt(isp, ISP_LOGERR, "NOP command failed (%x)", mbs.param[0]);
677 		ISP_RESET0(isp);
678 		return;
679 	}
680 
681 	/*
682 	 * Do some operational tests
683 	 */
684 
685 	if (IS_SCSI(isp) || IS_24XX(isp)) {
686 		ISP_MEMZERO(&mbs, sizeof (mbs));
687 		mbs.param[0] = MBOX_MAILBOX_REG_TEST;
688 		mbs.param[1] = 0xdead;
689 		mbs.param[2] = 0xbeef;
690 		mbs.param[3] = 0xffff;
691 		mbs.param[4] = 0x1111;
692 		mbs.param[5] = 0xa5a5;
693 		mbs.param[6] = 0x0000;
694 		mbs.param[7] = 0x0000;
695 		mbs.logval = MBLOGALL;
696 		isp_mboxcmd(isp, &mbs);
697 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
698 			ISP_RESET0(isp);
699 			return;
700 		}
701 		if (mbs.param[1] != 0xdead || mbs.param[2] != 0xbeef ||
702 		    mbs.param[3] != 0xffff || mbs.param[4] != 0x1111 ||
703 		    mbs.param[5] != 0xa5a5) {
704 			ISP_RESET0(isp);
705 			isp_prt(isp, ISP_LOGERR, "Register Test Failed (0x%x 0x%x 0x%x 0x%x 0x%x)", mbs.param[1], mbs.param[2], mbs.param[3], mbs.param[4], mbs.param[5]);
706 			return;
707 		}
708 
709 	}
710 
711 	/*
712 	 * Download new Firmware, unless requested not to do so.
713 	 * This is made slightly trickier in some cases where the
714 	 * firmware of the ROM revision is newer than the revision
715 	 * compiled into the driver. So, where we used to compare
716 	 * versions of our f/w and the ROM f/w, now we just see
717 	 * whether we have f/w at all and whether a config flag
718 	 * has disabled our download.
719 	 */
720 	if ((isp->isp_mdvec->dv_ispfw == NULL) || (isp->isp_confopts & ISP_CFG_NORELOAD)) {
721 		dodnld = 0;
722 	}
723 
724 	if (IS_24XX(isp)) {
725 		code_org = ISP_CODE_ORG_2400;
726 	} else if (IS_23XX(isp)) {
727 		code_org = ISP_CODE_ORG_2300;
728 	} else {
729 		code_org = ISP_CODE_ORG;
730 	}
731 
732 	if (dodnld && IS_24XX(isp)) {
733 		const uint32_t *ptr = isp->isp_mdvec->dv_ispfw;
734 		int wordload;
735 
736 		/*
737 		 * Keep loading until we run out of f/w.
738 		 */
739 		code_org = ptr[2];	/* 1st load address is our start addr */
740 		wordload = 0;
741 
742 		for (;;) {
743 			uint32_t la, wi, wl;
744 
745 			isp_prt(isp, ISP_LOGDEBUG0, "load 0x%x words of code at load address 0x%x", ptr[3], ptr[2]);
746 
747 			wi = 0;
748 			la = ptr[2];
749 			wl = ptr[3];
750 
751 			while (wi < ptr[3]) {
752 				uint32_t *cp;
753 				uint32_t nw;
754 
755 				nw = ISP_QUEUE_SIZE(RQUEST_QUEUE_LEN(isp)) >> 2;
756 				if (nw > wl) {
757 					nw = wl;
758 				}
759 				cp = isp->isp_rquest;
760 				for (i = 0; i < nw; i++) {
761 					ISP_IOXPUT_32(isp,  ptr[wi++], &cp[i]);
762 					wl--;
763 				}
764 				MEMORYBARRIER(isp, SYNC_REQUEST, 0, ISP_QUEUE_SIZE(RQUEST_QUEUE_LEN(isp)), -1);
765 	again:
766 				ISP_MEMZERO(&mbs, sizeof (mbs));
767 				if (la < 0x10000 && nw < 0x10000) {
768 					mbs.param[0] = MBOX_LOAD_RISC_RAM_2100;
769 					mbs.param[1] = la;
770 					mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
771 					mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
772 					mbs.param[4] = nw;
773 					mbs.param[6] = DMA_WD3(isp->isp_rquest_dma);
774 					mbs.param[7] = DMA_WD2(isp->isp_rquest_dma);
775 					isp_prt(isp, ISP_LOGDEBUG0, "LOAD RISC RAM 2100 %u words at load address 0x%x", nw, la);
776 				} else if (wordload) {
777 					union {
778 						const uint32_t *cp;
779 						uint32_t *np;
780 					} ucd;
781 					ucd.cp = (const uint32_t *)cp;
782 					mbs.param[0] = MBOX_WRITE_RAM_WORD_EXTENDED;
783 					mbs.param[1] = la;
784 					mbs.param[2] = (*ucd.np);
785 					mbs.param[3] = (*ucd.np) >> 16;
786 					mbs.param[8] = la >> 16;
787 					isp->isp_mbxwrk0 = nw - 1;
788 					isp->isp_mbxworkp = ucd.np+1;
789 					isp->isp_mbxwrk1 = (la + 1);
790 					isp->isp_mbxwrk8 = (la + 1) >> 16;
791 					isp_prt(isp, ISP_LOGDEBUG0, "WRITE RAM WORD EXTENDED %u words at load address 0x%x", nw, la);
792 				} else {
793 					mbs.param[0] = MBOX_LOAD_RISC_RAM;
794 					mbs.param[1] = la;
795 					mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
796 					mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
797 					mbs.param[4] = nw >> 16;
798 					mbs.param[5] = nw;
799 					mbs.param[6] = DMA_WD3(isp->isp_rquest_dma);
800 					mbs.param[7] = DMA_WD2(isp->isp_rquest_dma);
801 					mbs.param[8] = la >> 16;
802 					isp_prt(isp, ISP_LOGDEBUG0, "LOAD RISC RAM %u words at load address 0x%x", nw, la);
803 				}
804 				mbs.logval = MBLOGALL;
805 				isp_mboxcmd(isp, &mbs);
806 				if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
807 					if (mbs.param[0] == MBOX_HOST_INTERFACE_ERROR) {
808 						isp_prt(isp, ISP_LOGERR, "switching to word load");
809 						wordload = 1;
810 						goto again;
811 					}
812 					isp_prt(isp, ISP_LOGERR, "F/W Risc Ram Load Failed");
813 					ISP_RESET0(isp);
814 					return;
815 				}
816 				la += nw;
817 			}
818 
819 			if (ptr[1] == 0) {
820 				break;
821 			}
822 			ptr += ptr[3];
823 		}
824 		isp->isp_loaded_fw = 1;
825 	} else if (dodnld && IS_23XX(isp)) {
826 		const uint16_t *ptr = isp->isp_mdvec->dv_ispfw;
827 		uint16_t wi, wl, segno;
828 		uint32_t la;
829 
830 		la = code_org;
831 		segno = 0;
832 
833 		for (;;) {
834 			uint32_t nxtaddr;
835 
836 			isp_prt(isp, ISP_LOGDEBUG0, "load 0x%x words of code at load address 0x%x", ptr[3], la);
837 
838 			wi = 0;
839 			wl = ptr[3];
840 
841 			while (wi < ptr[3]) {
842 				uint16_t *cp;
843 				uint16_t nw;
844 
845 				nw = ISP_QUEUE_SIZE(RQUEST_QUEUE_LEN(isp)) >> 1;
846 				if (nw > wl) {
847 					nw = wl;
848 				}
849 				if (nw > (1 << 15)) {
850 					nw = 1 << 15;
851 				}
852 				cp = isp->isp_rquest;
853 				for (i = 0; i < nw; i++) {
854 					ISP_IOXPUT_16(isp,  ptr[wi++], &cp[i]);
855 					wl--;
856 				}
857 				MEMORYBARRIER(isp, SYNC_REQUEST, 0, ISP_QUEUE_SIZE(RQUEST_QUEUE_LEN(isp)), -1);
858 				ISP_MEMZERO(&mbs, sizeof (mbs));
859 				if (la < 0x10000) {
860 					mbs.param[0] = MBOX_LOAD_RISC_RAM_2100;
861 					mbs.param[1] = la;
862 					mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
863 					mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
864 					mbs.param[4] = nw;
865 					mbs.param[6] = DMA_WD3(isp->isp_rquest_dma);
866 					mbs.param[7] = DMA_WD2(isp->isp_rquest_dma);
867 					isp_prt(isp, ISP_LOGDEBUG1, "LOAD RISC RAM 2100 %u words at load address 0x%x\n", nw, la);
868 				} else {
869 					mbs.param[0] = MBOX_LOAD_RISC_RAM;
870 					mbs.param[1] = la;
871 					mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
872 					mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
873 					mbs.param[4] = nw;
874 					mbs.param[6] = DMA_WD3(isp->isp_rquest_dma);
875 					mbs.param[7] = DMA_WD2(isp->isp_rquest_dma);
876 					mbs.param[8] = la >> 16;
877 					isp_prt(isp, ISP_LOGDEBUG1, "LOAD RISC RAM %u words at load address 0x%x\n", nw, la);
878 				}
879 				mbs.logval = MBLOGALL;
880 				isp_mboxcmd(isp, &mbs);
881 				if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
882 					isp_prt(isp, ISP_LOGERR, "F/W Risc Ram Load Failed");
883 					ISP_RESET0(isp);
884 					return;
885 				}
886 				la += nw;
887 			}
888 
889 			if (!IS_2322(isp)) {
890 				break;
891 			}
892 
893 			if (++segno == 3) {
894 				break;
895 			}
896 
897 			/*
898 			 * If we're a 2322, the firmware actually comes in
899 			 * three chunks. We loaded the first at the code_org
900 			 * address. The other two chunks, which follow right
901 			 * after each other in memory here, get loaded at
902 			 * addresses specfied at offset 0x9..0xB.
903 			 */
904 
905 			nxtaddr = ptr[3];
906 			ptr = &ptr[nxtaddr];
907 			la = ptr[5] | ((ptr[4] & 0x3f) << 16);
908 		}
909 		isp->isp_loaded_fw = 1;
910 	} else if (dodnld) {
911 		union {
912 			const uint16_t *cp;
913 			uint16_t *np;
914 		} ucd;
915 		ucd.cp = isp->isp_mdvec->dv_ispfw;
916 		isp->isp_mbxworkp = &ucd.np[1];
917 		isp->isp_mbxwrk0 = ucd.np[3] - 1;
918 		isp->isp_mbxwrk1 = code_org + 1;
919 		ISP_MEMZERO(&mbs, sizeof (mbs));
920 		mbs.param[0] = MBOX_WRITE_RAM_WORD;
921 		mbs.param[1] = code_org;
922 		mbs.param[2] = ucd.np[0];
923 		mbs.logval = MBLOGNONE;
924 		isp_prt(isp, ISP_LOGDEBUG1, "WRITE RAM %u words at load address 0x%x\n", ucd.np[3], code_org);
925 		isp_mboxcmd(isp, &mbs);
926 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
927 			isp_prt(isp, ISP_LOGERR, "F/W download failed at word %d", isp->isp_mbxwrk1 - code_org);
928 			ISP_RESET0(isp);
929 			return;
930 		}
931 	} else {
932 		isp->isp_loaded_fw = 0;
933 		isp_prt(isp, ISP_LOGDEBUG2, "skipping f/w download");
934 	}
935 
936 	/*
937 	 * If we loaded firmware, verify its checksum
938 	 */
939 	if (isp->isp_loaded_fw) {
940 		ISP_MEMZERO(&mbs, sizeof (mbs));
941 		mbs.param[0] = MBOX_VERIFY_CHECKSUM;
942 		if (IS_24XX(isp)) {
943 			mbs.param[1] = code_org >> 16;
944 			mbs.param[2] = code_org;
945 		} else {
946 			mbs.param[1] = code_org;
947 		}
948 		isp_mboxcmd(isp, &mbs);
949 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
950 			isp_prt(isp, ISP_LOGERR, dcrc);
951 			ISP_RESET0(isp);
952 			return;
953 		}
954 	}
955 
956 	/*
957 	 * Now start it rolling.
958 	 *
959 	 * If we didn't actually download f/w,
960 	 * we still need to (re)start it.
961 	 */
962 
963 
964 	MBSINIT(&mbs, MBOX_EXEC_FIRMWARE, MBLOGALL, 1000000);
965 	if (IS_24XX(isp)) {
966 		mbs.param[1] = code_org >> 16;
967 		mbs.param[2] = code_org;
968 		if (isp->isp_loaded_fw) {
969 			mbs.param[3] = 0;
970 		} else {
971 			mbs.param[3] = 1;
972 		}
973 		if (IS_25XX(isp)) {
974 			mbs.ibits |= 0x10;
975 		}
976 	} else if (IS_2322(isp)) {
977 		mbs.param[1] = code_org;
978 		if (isp->isp_loaded_fw) {
979 			mbs.param[2] = 0;
980 		} else {
981 			mbs.param[2] = 1;
982 		}
983 	} else {
984 		mbs.param[1] = code_org;
985 	}
986 	isp_mboxcmd(isp, &mbs);
987 	if (IS_2322(isp) || IS_24XX(isp)) {
988 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
989 			ISP_RESET0(isp);
990 			return;
991 		}
992 	}
993 
994 	/*
995 	 * Give it a chance to finish starting up.
996 	 * Give the 24XX more time.
997 	 */
998 	if (IS_24XX(isp)) {
999 		ISP_DELAY(500000);
1000 		/*
1001 		 * Check to see if the 24XX firmware really started.
1002 		 */
1003 		if (mbs.param[1] == 0xdead) {
1004 			isp_prt(isp, ISP_LOGERR, "f/w didn't *really* start");
1005 			ISP_RESET0(isp);
1006 			return;
1007 		}
1008 	} else {
1009 		ISP_DELAY(250000);
1010 		if (IS_SCSI(isp)) {
1011 			/*
1012 			 * Set CLOCK RATE, but only if asked to.
1013 			 */
1014 			if (isp->isp_clock) {
1015 				mbs.param[0] = MBOX_SET_CLOCK_RATE;
1016 				mbs.param[1] = isp->isp_clock;
1017 				mbs.logval = MBLOGNONE;
1018 				isp_mboxcmd(isp, &mbs);
1019 				/* we will try not to care if this fails */
1020 			}
1021 		}
1022 	}
1023 
1024 	/*
1025 	 * Ask the chip for the current firmware version.
1026 	 * This should prove that the new firmware is working.
1027 	 */
1028 	MBSINIT(&mbs, MBOX_ABOUT_FIRMWARE, MBLOGALL, 0);
1029 	isp_mboxcmd(isp, &mbs);
1030 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1031 		ISP_RESET0(isp);
1032 		return;
1033 	}
1034 
1035 	/*
1036 	 * The SBus firmware that we are using apparently does not return
1037 	 * major, minor, micro revisions in the mailbox registers, which
1038 	 * is really, really, annoying.
1039 	 */
1040 	if (ISP_SBUS_SUPPORTED && isp->isp_bustype == ISP_BT_SBUS) {
1041 		if (dodnld) {
1042 #ifdef	ISP_TARGET_MODE
1043 			isp->isp_fwrev[0] = 7;
1044 			isp->isp_fwrev[1] = 55;
1045 #else
1046 			isp->isp_fwrev[0] = 1;
1047 			isp->isp_fwrev[1] = 37;
1048 #endif
1049 			isp->isp_fwrev[2] = 0;
1050 		}
1051 	} else {
1052 		isp->isp_fwrev[0] = mbs.param[1];
1053 		isp->isp_fwrev[1] = mbs.param[2];
1054 		isp->isp_fwrev[2] = mbs.param[3];
1055 	}
1056 
1057 	isp_prt(isp, ISP_LOGCONFIG, "Board Type %s, Chip Revision 0x%x, %s F/W Revision %d.%d.%d",
1058 	    btype, isp->isp_revision, dodnld? "loaded" : "resident", isp->isp_fwrev[0], isp->isp_fwrev[1], isp->isp_fwrev[2]);
1059 
1060 	if (IS_FC(isp)) {
1061 		/*
1062 		 * We do not believe firmware attributes for 2100 code less
1063 		 * than 1.17.0, unless it's the firmware we specifically
1064 		 * are loading.
1065 		 *
1066 		 * Note that all 22XX and later f/w is greater than 1.X.0.
1067 		 */
1068 		if ((ISP_FW_OLDER_THAN(isp, 1, 17, 1))) {
1069 #ifdef	USE_SMALLER_2100_FIRMWARE
1070 			isp->isp_fwattr = ISP_FW_ATTR_SCCLUN;
1071 #else
1072 			isp->isp_fwattr = 0;
1073 #endif
1074 		} else {
1075 			isp->isp_fwattr = mbs.param[6];
1076 			isp_prt(isp, ISP_LOGDEBUG0, "Firmware Attributes = 0x%x", mbs.param[6]);
1077 		}
1078 	} else {
1079 #ifndef	ISP_TARGET_MODE
1080 		isp->isp_fwattr = ISP_FW_ATTR_TMODE;
1081 #else
1082 		isp->isp_fwattr = 0;
1083 #endif
1084 	}
1085 
1086 	if (!IS_24XX(isp)) {
1087 		MBSINIT(&mbs, MBOX_GET_FIRMWARE_STATUS, MBLOGALL, 0);
1088 		isp_mboxcmd(isp, &mbs);
1089 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1090 			ISP_RESET0(isp);
1091 			return;
1092 		}
1093 		if (isp->isp_maxcmds >= mbs.param[2]) {
1094 			isp->isp_maxcmds = mbs.param[2];
1095 		}
1096 	}
1097 	isp_prt(isp, ISP_LOGCONFIG, "%d max I/O command limit set", isp->isp_maxcmds);
1098 
1099 	/*
1100 	 * If we don't have Multi-ID f/w loaded, we need to restrict channels to one.
1101 	 * Only make this check for non-SCSI cards (I'm not sure firmware attributes
1102 	 * work for them).
1103 	 */
1104 	if (IS_FC(isp) && ISP_CAP_MULTI_ID(isp) == 0 && isp->isp_nchan > 1) {
1105 		isp_prt(isp, ISP_LOGWARN, "non-MULTIID f/w loaded, only can enable 1 of %d channels", isp->isp_nchan);
1106 		isp->isp_nchan = 1;
1107 	}
1108 
1109 	for (i = 0; i < isp->isp_nchan; i++) {
1110 		isp_fw_state(isp, i);
1111 	}
1112 	if (isp->isp_dead) {
1113 		isp_shutdown(isp);
1114 		ISP_DISABLE_INTS(isp);
1115 		return;
1116 	}
1117 
1118 	isp->isp_state = ISP_RESETSTATE;
1119 
1120 	/*
1121 	 * Okay- now that we have new firmware running, we now (re)set our
1122 	 * notion of how many luns we support. This is somewhat tricky because
1123 	 * if we haven't loaded firmware, we sometimes do not have an easy way
1124 	 * of knowing how many luns we support.
1125 	 *
1126 	 * Expanded lun firmware gives you 32 luns for SCSI cards and
1127 	 * 16384 luns for Fibre Channel cards.
1128 	 *
1129 	 * It turns out that even for QLogic 2100s with ROM 1.10 and above
1130 	 * we do get a firmware attributes word returned in mailbox register 6.
1131 	 *
1132 	 * Because the lun is in a different position in the Request Queue
1133 	 * Entry structure for Fibre Channel with expanded lun firmware, we
1134 	 * can only support one lun (lun zero) when we don't know what kind
1135 	 * of firmware we're running.
1136 	 */
1137 	if (IS_SCSI(isp)) {
1138 		if (dodnld) {
1139 			if (IS_ULTRA2(isp) || IS_ULTRA3(isp)) {
1140 				isp->isp_maxluns = 32;
1141 			} else {
1142 				isp->isp_maxluns = 8;
1143 			}
1144 		} else {
1145 			isp->isp_maxluns = 8;
1146 		}
1147 	} else {
1148 		if (ISP_CAP_SCCFW(isp)) {
1149 			isp->isp_maxluns = 16384;
1150 		} else {
1151 			isp->isp_maxluns = 16;
1152 		}
1153 	}
1154 
1155 	/*
1156 	 * We get some default values established. As a side
1157 	 * effect, NVRAM is read here (unless overriden by
1158 	 * a configuration flag).
1159 	 */
1160 	if (do_load_defaults) {
1161 		if (IS_SCSI(isp)) {
1162 			isp_setdfltsdparm(isp);
1163 		} else {
1164 			for (i = 0; i < isp->isp_nchan; i++) {
1165 				isp_setdfltfcparm(isp, i);
1166 			}
1167 		}
1168 	}
1169 }
1170 
1171 /*
1172  * Initialize Parameters of Hardware to a known state.
1173  *
1174  * Locks are held before coming here.
1175  */
1176 
1177 void
1178 isp_init(ispsoftc_t *isp)
1179 {
1180 	if (IS_FC(isp)) {
1181 		if (IS_24XX(isp)) {
1182 			isp_fibre_init_2400(isp);
1183 		} else {
1184 			isp_fibre_init(isp);
1185 		}
1186 	} else {
1187 		isp_scsi_init(isp);
1188 	}
1189 	GET_NANOTIME(&isp->isp_init_time);
1190 }
1191 
1192 static void
1193 isp_scsi_init(ispsoftc_t *isp)
1194 {
1195 	sdparam *sdp_chan0, *sdp_chan1;
1196 	mbreg_t mbs;
1197 
1198 	sdp_chan0 = SDPARAM(isp, 0);
1199 	sdp_chan1 = sdp_chan0;
1200 	if (IS_DUALBUS(isp)) {
1201 		sdp_chan1 = SDPARAM(isp, 1);
1202 	}
1203 
1204 	/* First do overall per-card settings. */
1205 
1206 	/*
1207 	 * If we have fast memory timing enabled, turn it on.
1208 	 */
1209 	if (sdp_chan0->isp_fast_mttr) {
1210 		ISP_WRITE(isp, RISC_MTR, 0x1313);
1211 	}
1212 
1213 	/*
1214 	 * Set Retry Delay and Count.
1215 	 * You set both channels at the same time.
1216 	 */
1217 	MBSINIT(&mbs, MBOX_SET_RETRY_COUNT, MBLOGALL, 0);
1218 	mbs.param[1] = sdp_chan0->isp_retry_count;
1219 	mbs.param[2] = sdp_chan0->isp_retry_delay;
1220 	mbs.param[6] = sdp_chan1->isp_retry_count;
1221 	mbs.param[7] = sdp_chan1->isp_retry_delay;
1222 	isp_mboxcmd(isp, &mbs);
1223 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1224 		return;
1225 	}
1226 
1227 	/*
1228 	 * Set ASYNC DATA SETUP time. This is very important.
1229 	 */
1230 	MBSINIT(&mbs, MBOX_SET_ASYNC_DATA_SETUP_TIME, MBLOGALL, 0);
1231 	mbs.param[1] = sdp_chan0->isp_async_data_setup;
1232 	mbs.param[2] = sdp_chan1->isp_async_data_setup;
1233 	isp_mboxcmd(isp, &mbs);
1234 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1235 		return;
1236 	}
1237 
1238 	/*
1239 	 * Set ACTIVE Negation State.
1240 	 */
1241 	MBSINIT(&mbs, MBOX_SET_ACT_NEG_STATE, MBLOGNONE, 0);
1242 	mbs.param[1] =
1243 	    (sdp_chan0->isp_req_ack_active_neg << 4) |
1244 	    (sdp_chan0->isp_data_line_active_neg << 5);
1245 	mbs.param[2] =
1246 	    (sdp_chan1->isp_req_ack_active_neg << 4) |
1247 	    (sdp_chan1->isp_data_line_active_neg << 5);
1248 	isp_mboxcmd(isp, &mbs);
1249 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1250 		isp_prt(isp, ISP_LOGERR,
1251 		    "failed to set active negation state (%d,%d), (%d,%d)",
1252 		    sdp_chan0->isp_req_ack_active_neg,
1253 		    sdp_chan0->isp_data_line_active_neg,
1254 		    sdp_chan1->isp_req_ack_active_neg,
1255 		    sdp_chan1->isp_data_line_active_neg);
1256 		/*
1257 		 * But don't return.
1258 		 */
1259 	}
1260 
1261 	/*
1262 	 * Set the Tag Aging limit
1263 	 */
1264 	MBSINIT(&mbs, MBOX_SET_TAG_AGE_LIMIT, MBLOGALL, 0);
1265 	mbs.param[1] = sdp_chan0->isp_tag_aging;
1266 	mbs.param[2] = sdp_chan1->isp_tag_aging;
1267 	isp_mboxcmd(isp, &mbs);
1268 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1269 		isp_prt(isp, ISP_LOGERR, "failed to set tag age limit (%d,%d)",
1270 		    sdp_chan0->isp_tag_aging, sdp_chan1->isp_tag_aging);
1271 		return;
1272 	}
1273 
1274 	/*
1275 	 * Set selection timeout.
1276 	 */
1277 	MBSINIT(&mbs, MBOX_SET_SELECT_TIMEOUT, MBLOGALL, 0);
1278 	mbs.param[1] = sdp_chan0->isp_selection_timeout;
1279 	mbs.param[2] = sdp_chan1->isp_selection_timeout;
1280 	isp_mboxcmd(isp, &mbs);
1281 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1282 		return;
1283 	}
1284 
1285 	/* now do per-channel settings */
1286 	isp_scsi_channel_init(isp, 0);
1287 	if (IS_DUALBUS(isp))
1288 		isp_scsi_channel_init(isp, 1);
1289 
1290 	/*
1291 	 * Now enable request/response queues
1292 	 */
1293 
1294 	if (IS_ULTRA2(isp) || IS_1240(isp)) {
1295 		MBSINIT(&mbs, MBOX_INIT_RES_QUEUE_A64, MBLOGALL, 0);
1296 		mbs.param[1] = RESULT_QUEUE_LEN(isp);
1297 		mbs.param[2] = DMA_WD1(isp->isp_result_dma);
1298 		mbs.param[3] = DMA_WD0(isp->isp_result_dma);
1299 		mbs.param[4] = 0;
1300 		mbs.param[6] = DMA_WD3(isp->isp_result_dma);
1301 		mbs.param[7] = DMA_WD2(isp->isp_result_dma);
1302 		isp_mboxcmd(isp, &mbs);
1303 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1304 			return;
1305 		}
1306 		isp->isp_residx = mbs.param[5];
1307 
1308 		MBSINIT(&mbs, MBOX_INIT_REQ_QUEUE_A64, MBLOGALL, 0);
1309 		mbs.param[1] = RQUEST_QUEUE_LEN(isp);
1310 		mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
1311 		mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
1312 		mbs.param[5] = 0;
1313 		mbs.param[6] = DMA_WD3(isp->isp_result_dma);
1314 		mbs.param[7] = DMA_WD2(isp->isp_result_dma);
1315 		isp_mboxcmd(isp, &mbs);
1316 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1317 			return;
1318 		}
1319 		isp->isp_reqidx = isp->isp_reqodx = mbs.param[4];
1320 	} else {
1321 		MBSINIT(&mbs, MBOX_INIT_RES_QUEUE, MBLOGALL, 0);
1322 		mbs.param[1] = RESULT_QUEUE_LEN(isp);
1323 		mbs.param[2] = DMA_WD1(isp->isp_result_dma);
1324 		mbs.param[3] = DMA_WD0(isp->isp_result_dma);
1325 		mbs.param[4] = 0;
1326 		isp_mboxcmd(isp, &mbs);
1327 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1328 			return;
1329 		}
1330 		isp->isp_residx = mbs.param[5];
1331 
1332 		MBSINIT(&mbs, MBOX_INIT_REQ_QUEUE, MBLOGALL, 0);
1333 		mbs.param[1] = RQUEST_QUEUE_LEN(isp);
1334 		mbs.param[2] = DMA_WD1(isp->isp_rquest_dma);
1335 		mbs.param[3] = DMA_WD0(isp->isp_rquest_dma);
1336 		mbs.param[5] = 0;
1337 		isp_mboxcmd(isp, &mbs);
1338 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1339 			return;
1340 		}
1341 		isp->isp_reqidx = isp->isp_reqodx = mbs.param[4];
1342 	}
1343 
1344 	/*
1345 	 * Turn on LVD transitions for ULTRA2 or better and other features
1346 	 *
1347 	 * Now that we have 32 bit handles, don't do any fast posting
1348 	 * any more. For Ultra2/Ultra3 cards, we can turn on 32 bit RIO
1349 	 * operation or use fast posting. To be conservative, we'll only
1350 	 * do this for Ultra3 cards now because the other cards are so
1351 	 * rare for this author to find and test with.
1352 	 */
1353 
1354 	MBSINIT(&mbs, MBOX_SET_FW_FEATURES, MBLOGALL, 0);
1355 	if (IS_ULTRA2(isp))
1356 		mbs.param[1] |= FW_FEATURE_LVD_NOTIFY;
1357 #ifdef	ISP_NO_RIO
1358 	if (IS_ULTRA3(isp))
1359 		mbs.param[1] |= FW_FEATURE_FAST_POST;
1360 #else
1361 	if (IS_ULTRA3(isp))
1362 		mbs.param[1] |= FW_FEATURE_RIO_32BIT;
1363 #endif
1364 	if (mbs.param[1] != 0) {
1365 		uint16_t sfeat = mbs.param[1];
1366 		isp_mboxcmd(isp, &mbs);
1367 		if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
1368 			isp_prt(isp, ISP_LOGINFO,
1369 			    "Enabled FW features (0x%x)", sfeat);
1370 		}
1371 	}
1372 
1373 	isp->isp_state = ISP_INITSTATE;
1374 }
1375 
1376 static void
1377 isp_scsi_channel_init(ispsoftc_t *isp, int chan)
1378 {
1379 	sdparam *sdp;
1380 	mbreg_t mbs;
1381 	int tgt;
1382 
1383 	sdp = SDPARAM(isp, chan);
1384 
1385 	/*
1386 	 * Set (possibly new) Initiator ID.
1387 	 */
1388 	MBSINIT(&mbs, MBOX_SET_INIT_SCSI_ID, MBLOGALL, 0);
1389 	mbs.param[1] = (chan << 7) | sdp->isp_initiator_id;
1390 	isp_mboxcmd(isp, &mbs);
1391 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1392 		return;
1393 	}
1394 	isp_prt(isp, ISP_LOGINFO, "Chan %d Initiator ID is %d",
1395 	    chan, sdp->isp_initiator_id);
1396 
1397 
1398 	/*
1399 	 * Set current per-target parameters to an initial safe minimum.
1400 	 */
1401 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
1402 		int lun;
1403 		uint16_t sdf;
1404 
1405 		if (sdp->isp_devparam[tgt].dev_enable == 0) {
1406 			continue;
1407 		}
1408 #ifndef	ISP_TARGET_MODE
1409 		sdf = sdp->isp_devparam[tgt].goal_flags;
1410 		sdf &= DPARM_SAFE_DFLT;
1411 		/*
1412 		 * It is not quite clear when this changed over so that
1413 		 * we could force narrow and async for 1000/1020 cards,
1414 		 * but assume that this is only the case for loaded
1415 		 * firmware.
1416 		 */
1417 		if (isp->isp_loaded_fw) {
1418 			sdf |= DPARM_NARROW | DPARM_ASYNC;
1419 		}
1420 #else
1421 		/*
1422 		 * The !$*!)$!$)* f/w uses the same index into some
1423 		 * internal table to decide how to respond to negotiations,
1424 		 * so if we've said "let's be safe" for ID X, and ID X
1425 		 * selects *us*, the negotiations will back to 'safe'
1426 		 * (as in narrow/async). What the f/w *should* do is
1427 		 * use the initiator id settings to decide how to respond.
1428 		 */
1429 		sdp->isp_devparam[tgt].goal_flags = sdf = DPARM_DEFAULT;
1430 #endif
1431 		MBSINIT(&mbs, MBOX_SET_TARGET_PARAMS, MBLOGNONE, 0);
1432 		mbs.param[1] = (chan << 15) | (tgt << 8);
1433 		mbs.param[2] = sdf;
1434 		if ((sdf & DPARM_SYNC) == 0) {
1435 			mbs.param[3] = 0;
1436 		} else {
1437 			mbs.param[3] =
1438 			    (sdp->isp_devparam[tgt].goal_offset << 8) |
1439 			    (sdp->isp_devparam[tgt].goal_period);
1440 		}
1441 		isp_prt(isp, ISP_LOGDEBUG0, "Initial Settings bus%d tgt%d flags 0x%x off 0x%x per 0x%x",
1442 		    chan, tgt, mbs.param[2], mbs.param[3] >> 8, mbs.param[3] & 0xff);
1443 		isp_mboxcmd(isp, &mbs);
1444 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1445 			sdf = DPARM_SAFE_DFLT;
1446 			MBSINIT(&mbs, MBOX_SET_TARGET_PARAMS, MBLOGALL, 0);
1447 			mbs.param[1] = (tgt << 8) | (chan << 15);
1448 			mbs.param[2] = sdf;
1449 			mbs.param[3] = 0;
1450 			isp_mboxcmd(isp, &mbs);
1451 			if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1452 				continue;
1453 			}
1454 		}
1455 
1456 		/*
1457 		 * We don't update any information directly from the f/w
1458 		 * because we need to run at least one command to cause a
1459 		 * new state to be latched up. So, we just assume that we
1460 		 * converge to the values we just had set.
1461 		 *
1462 		 * Ensure that we don't believe tagged queuing is enabled yet.
1463 		 * It turns out that sometimes the ISP just ignores our
1464 		 * attempts to set parameters for devices that it hasn't
1465 		 * seen yet.
1466 		 */
1467 		sdp->isp_devparam[tgt].actv_flags = sdf & ~DPARM_TQING;
1468 		for (lun = 0; lun < (int) isp->isp_maxluns; lun++) {
1469 			MBSINIT(&mbs, MBOX_SET_DEV_QUEUE_PARAMS, MBLOGALL, 0);
1470 			mbs.param[1] = (chan << 15) | (tgt << 8) | lun;
1471 			mbs.param[2] = sdp->isp_max_queue_depth;
1472 			mbs.param[3] = sdp->isp_devparam[tgt].exc_throttle;
1473 			isp_mboxcmd(isp, &mbs);
1474 			if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1475 				break;
1476 			}
1477 		}
1478 	}
1479 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
1480 		if (sdp->isp_devparam[tgt].dev_refresh) {
1481 			sdp->sendmarker = 1;
1482 			sdp->update = 1;
1483 			break;
1484 		}
1485 	}
1486 }
1487 
1488 /*
1489  * Fibre Channel specific initialization.
1490  */
1491 static void
1492 isp_fibre_init(ispsoftc_t *isp)
1493 {
1494 	fcparam *fcp;
1495 	isp_icb_t local, *icbp = &local;
1496 	mbreg_t mbs;
1497 	int ownloopid;
1498 
1499 	/*
1500 	 * We only support one channel on non-24XX cards
1501 	 */
1502 	fcp = FCPARAM(isp, 0);
1503 	if (fcp->role == ISP_ROLE_NONE) {
1504 		isp->isp_state = ISP_INITSTATE;
1505 		return;
1506 	}
1507 
1508 	ISP_MEMZERO(icbp, sizeof (*icbp));
1509 	icbp->icb_version = ICB_VERSION1;
1510 	icbp->icb_fwoptions = fcp->isp_fwoptions;
1511 
1512 	/*
1513 	 * Firmware Options are either retrieved from NVRAM or
1514 	 * are patched elsewhere. We check them for sanity here
1515 	 * and make changes based on board revision, but otherwise
1516 	 * let others decide policy.
1517 	 */
1518 
1519 	/*
1520 	 * If this is a 2100 < revision 5, we have to turn off FAIRNESS.
1521 	 */
1522 	if (IS_2100(isp) && isp->isp_revision < 5) {
1523 		icbp->icb_fwoptions &= ~ICBOPT_FAIRNESS;
1524 	}
1525 
1526 	/*
1527 	 * We have to use FULL LOGIN even though it resets the loop too much
1528 	 * because otherwise port database entries don't get updated after
1529 	 * a LIP- this is a known f/w bug for 2100 f/w less than 1.17.0.
1530 	 */
1531 	if (!ISP_FW_NEWER_THAN(isp, 1, 17, 0)) {
1532 		icbp->icb_fwoptions |= ICBOPT_FULL_LOGIN;
1533 	}
1534 
1535 	/*
1536 	 * Insist on Port Database Update Async notifications
1537 	 */
1538 	icbp->icb_fwoptions |= ICBOPT_PDBCHANGE_AE;
1539 
1540 	/*
1541 	 * Make sure that target role reflects into fwoptions.
1542 	 */
1543 	if (fcp->role & ISP_ROLE_TARGET) {
1544 		icbp->icb_fwoptions |= ICBOPT_TGT_ENABLE;
1545 	} else {
1546 		icbp->icb_fwoptions &= ~ICBOPT_TGT_ENABLE;
1547 	}
1548 
1549 	if (fcp->role & ISP_ROLE_INITIATOR) {
1550 		icbp->icb_fwoptions &= ~ICBOPT_INI_DISABLE;
1551 	} else {
1552 		icbp->icb_fwoptions |= ICBOPT_INI_DISABLE;
1553 	}
1554 
1555 	icbp->icb_maxfrmlen = DEFAULT_FRAMESIZE(isp);
1556 	if (icbp->icb_maxfrmlen < ICB_MIN_FRMLEN || icbp->icb_maxfrmlen > ICB_MAX_FRMLEN) {
1557 		isp_prt(isp, ISP_LOGERR, "bad frame length (%d) from NVRAM- using %d", DEFAULT_FRAMESIZE(isp), ICB_DFLT_FRMLEN);
1558 		icbp->icb_maxfrmlen = ICB_DFLT_FRMLEN;
1559 	}
1560 	icbp->icb_maxalloc = fcp->isp_maxalloc;
1561 	if (icbp->icb_maxalloc < 1) {
1562 		isp_prt(isp, ISP_LOGERR, "bad maximum allocation (%d)- using 16", fcp->isp_maxalloc);
1563 		icbp->icb_maxalloc = 16;
1564 	}
1565 	icbp->icb_execthrottle = DEFAULT_EXEC_THROTTLE(isp);
1566 	if (icbp->icb_execthrottle < 1) {
1567 		isp_prt(isp, ISP_LOGERR, "bad execution throttle of %d- using %d", DEFAULT_EXEC_THROTTLE(isp), ICB_DFLT_THROTTLE);
1568 		icbp->icb_execthrottle = ICB_DFLT_THROTTLE;
1569 	}
1570 	icbp->icb_retry_delay = fcp->isp_retry_delay;
1571 	icbp->icb_retry_count = fcp->isp_retry_count;
1572 	icbp->icb_hardaddr = fcp->isp_loopid;
1573 	ownloopid = (isp->isp_confopts & ISP_CFG_OWNLOOPID) != 0;
1574 	if (icbp->icb_hardaddr >= LOCAL_LOOP_LIM) {
1575 		icbp->icb_hardaddr = 0;
1576 		ownloopid = 0;
1577 	}
1578 
1579 	/*
1580 	 * Our life seems so much better with 2200s and later with
1581 	 * the latest f/w if we set Hard Address.
1582 	 */
1583 	if (ownloopid || ISP_FW_NEWER_THAN(isp, 2, 2, 5)) {
1584 		icbp->icb_fwoptions |= ICBOPT_HARD_ADDRESS;
1585 	}
1586 
1587 	/*
1588 	 * Right now we just set extended options to prefer point-to-point
1589 	 * over loop based upon some soft config options.
1590 	 *
1591 	 * NB: for the 2300, ICBOPT_EXTENDED is required.
1592 	 */
1593 	if (IS_2200(isp) || IS_23XX(isp)) {
1594 		icbp->icb_fwoptions |= ICBOPT_EXTENDED;
1595 		/*
1596 		 * Prefer or force Point-To-Point instead Loop?
1597 		 */
1598 		switch (isp->isp_confopts & ISP_CFG_PORT_PREF) {
1599 		case ISP_CFG_NPORT:
1600 			icbp->icb_xfwoptions |= ICBXOPT_PTP_2_LOOP;
1601 			break;
1602 		case ISP_CFG_NPORT_ONLY:
1603 			icbp->icb_xfwoptions |= ICBXOPT_PTP_ONLY;
1604 			break;
1605 		case ISP_CFG_LPORT_ONLY:
1606 			icbp->icb_xfwoptions |= ICBXOPT_LOOP_ONLY;
1607 			break;
1608 		default:
1609 			icbp->icb_xfwoptions |= ICBXOPT_LOOP_2_PTP;
1610 			break;
1611 		}
1612 		if (IS_2200(isp)) {
1613 			/*
1614 			 * We can't have Fast Posting any more- we now
1615 			 * have 32 bit handles.
1616 			 *
1617 			 * RIO seemed to have to much breakage.
1618 			 *
1619 			 * Just opt for safety.
1620 			 */
1621 			icbp->icb_xfwoptions &= ~ICBXOPT_RIO_16BIT;
1622 			icbp->icb_fwoptions &= ~ICBOPT_FAST_POST;
1623 		} else {
1624 			/*
1625 			 * QLogic recommends that FAST Posting be turned
1626 			 * off for 23XX cards and instead allow the HBA
1627 			 * to write response queue entries and interrupt
1628 			 * after a delay (ZIO).
1629 			 */
1630 			icbp->icb_fwoptions &= ~ICBOPT_FAST_POST;
1631 			if ((fcp->isp_xfwoptions & ICBXOPT_TIMER_MASK) == ICBXOPT_ZIO) {
1632 				icbp->icb_xfwoptions |= ICBXOPT_ZIO;
1633 				icbp->icb_idelaytimer = 10;
1634 			}
1635 			if (isp->isp_confopts & ISP_CFG_ONEGB) {
1636 				icbp->icb_zfwoptions |= ICBZOPT_RATE_ONEGB;
1637 			} else if (isp->isp_confopts & ISP_CFG_TWOGB) {
1638 				icbp->icb_zfwoptions |= ICBZOPT_RATE_TWOGB;
1639 			} else {
1640 				icbp->icb_zfwoptions |= ICBZOPT_RATE_AUTO;
1641 			}
1642 			if (fcp->isp_zfwoptions & ICBZOPT_50_OHM) {
1643 				icbp->icb_zfwoptions |= ICBZOPT_50_OHM;
1644 			}
1645 		}
1646 	}
1647 
1648 
1649 	/*
1650 	 * For 22XX > 2.1.26 && 23XX, set some options.
1651 	 */
1652 	if (ISP_FW_NEWER_THAN(isp, 2, 26, 0)) {
1653 		MBSINIT(&mbs, MBOX_SET_FIRMWARE_OPTIONS, MBLOGALL, 0);
1654 		mbs.param[1] = IFCOPT1_DISF7SWTCH|IFCOPT1_LIPASYNC|IFCOPT1_LIPF8;
1655 		mbs.param[2] = 0;
1656 		mbs.param[3] = 0;
1657 		if (ISP_FW_NEWER_THAN(isp, 3, 16, 0)) {
1658 			mbs.param[1] |= IFCOPT1_EQFQASYNC|IFCOPT1_CTIO_RETRY;
1659 			if (fcp->role & ISP_ROLE_TARGET) {
1660 				mbs.param[3] = IFCOPT3_NOPRLI;
1661 			}
1662 		}
1663 		isp_mboxcmd(isp, &mbs);
1664 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1665 			return;
1666 		}
1667 	}
1668 	icbp->icb_logintime = ICB_LOGIN_TOV;
1669 	icbp->icb_lunetimeout = ICB_LUN_ENABLE_TOV;
1670 
1671 	if (fcp->isp_wwnn && fcp->isp_wwpn && (fcp->isp_wwnn >> 60) != 2) {
1672 		icbp->icb_fwoptions |= ICBOPT_BOTH_WWNS;
1673 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_nodename, fcp->isp_wwnn);
1674 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_portname, fcp->isp_wwpn);
1675 		isp_prt(isp, ISP_LOGDEBUG1,
1676 		    "Setting ICB Node 0x%08x%08x Port 0x%08x%08x",
1677 		    ((uint32_t) (fcp->isp_wwnn >> 32)),
1678 		    ((uint32_t) (fcp->isp_wwnn)),
1679 		    ((uint32_t) (fcp->isp_wwpn >> 32)),
1680 		    ((uint32_t) (fcp->isp_wwpn)));
1681 	} else if (fcp->isp_wwpn) {
1682 		icbp->icb_fwoptions &= ~ICBOPT_BOTH_WWNS;
1683 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_portname, fcp->isp_wwpn);
1684 		isp_prt(isp, ISP_LOGDEBUG1,
1685 		    "Setting ICB Port 0x%08x%08x",
1686 		    ((uint32_t) (fcp->isp_wwpn >> 32)),
1687 		    ((uint32_t) (fcp->isp_wwpn)));
1688 	} else {
1689 		isp_prt(isp, ISP_LOGERR, "No valid WWNs to use");
1690 		return;
1691 	}
1692 	icbp->icb_rqstqlen = RQUEST_QUEUE_LEN(isp);
1693 	if (icbp->icb_rqstqlen < 1) {
1694 		isp_prt(isp, ISP_LOGERR, "bad request queue length");
1695 	}
1696 	icbp->icb_rsltqlen = RESULT_QUEUE_LEN(isp);
1697 	if (icbp->icb_rsltqlen < 1) {
1698 		isp_prt(isp, ISP_LOGERR, "bad result queue length");
1699 	}
1700 	icbp->icb_rqstaddr[RQRSP_ADDR0015] = DMA_WD0(isp->isp_rquest_dma);
1701 	icbp->icb_rqstaddr[RQRSP_ADDR1631] = DMA_WD1(isp->isp_rquest_dma);
1702 	icbp->icb_rqstaddr[RQRSP_ADDR3247] = DMA_WD2(isp->isp_rquest_dma);
1703 	icbp->icb_rqstaddr[RQRSP_ADDR4863] = DMA_WD3(isp->isp_rquest_dma);
1704 	icbp->icb_respaddr[RQRSP_ADDR0015] = DMA_WD0(isp->isp_result_dma);
1705 	icbp->icb_respaddr[RQRSP_ADDR1631] = DMA_WD1(isp->isp_result_dma);
1706 	icbp->icb_respaddr[RQRSP_ADDR3247] = DMA_WD2(isp->isp_result_dma);
1707 	icbp->icb_respaddr[RQRSP_ADDR4863] = DMA_WD3(isp->isp_result_dma);
1708 
1709 	if (FC_SCRATCH_ACQUIRE(isp, 0)) {
1710 		isp_prt(isp, ISP_LOGERR, sacq);
1711 		return;
1712 	}
1713 	isp_prt(isp, ISP_LOGDEBUG0, "isp_fibre_init: fwopt 0x%x xfwopt 0x%x zfwopt 0x%x",
1714 	    icbp->icb_fwoptions, icbp->icb_xfwoptions, icbp->icb_zfwoptions);
1715 
1716 	isp_put_icb(isp, icbp, (isp_icb_t *)fcp->isp_scratch);
1717 
1718 	/*
1719 	 * Init the firmware
1720 	 */
1721 	MBSINIT(&mbs, MBOX_INIT_FIRMWARE, MBLOGALL, 30000000);
1722 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
1723 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
1724 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
1725 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
1726 	mbs.logval = MBLOGALL;
1727 	isp_prt(isp, ISP_LOGDEBUG0, "INIT F/W from %p (%08x%08x)",
1728 	    fcp->isp_scratch, (uint32_t) ((uint64_t)fcp->isp_scdma >> 32),
1729 	    (uint32_t) fcp->isp_scdma);
1730 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, sizeof (*icbp), 0);
1731 	isp_mboxcmd(isp, &mbs);
1732 	FC_SCRATCH_RELEASE(isp, 0);
1733 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1734 		isp_print_bytes(isp, "isp_fibre_init", sizeof (*icbp), icbp);
1735 		return;
1736 	}
1737 	isp->isp_reqidx = 0;
1738 	isp->isp_reqodx = 0;
1739 	isp->isp_residx = 0;
1740 
1741 	/*
1742 	 * Whatever happens, we're now committed to being here.
1743 	 */
1744 	isp->isp_state = ISP_INITSTATE;
1745 }
1746 
1747 static void
1748 isp_fibre_init_2400(ispsoftc_t *isp)
1749 {
1750 	fcparam *fcp;
1751 	isp_icb_2400_t local, *icbp = &local;
1752 	mbreg_t mbs;
1753 	int chan;
1754 
1755 	/*
1756 	 * Check to see whether all channels have *some* kind of role
1757 	 */
1758 	for (chan = 0; chan < isp->isp_nchan; chan++) {
1759 		fcp = FCPARAM(isp, chan);
1760 		if (fcp->role != ISP_ROLE_NONE) {
1761 			break;
1762 		}
1763 	}
1764 	if (chan == isp->isp_nchan) {
1765 		isp_prt(isp, ISP_LOGDEBUG0, "all %d channels with role 'none'", chan);
1766 		isp->isp_state = ISP_INITSTATE;
1767 		return;
1768 	}
1769 
1770 	/*
1771 	 * Start with channel 0.
1772 	 */
1773 	fcp = FCPARAM(isp, 0);
1774 
1775 	/*
1776 	 * Turn on LIP F8 async event (1)
1777 	 */
1778 	MBSINIT(&mbs, MBOX_SET_FIRMWARE_OPTIONS, MBLOGALL, 0);
1779 	mbs.param[1] = 1;
1780 	isp_mboxcmd(isp, &mbs);
1781 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1782 		return;
1783 	}
1784 
1785 	ISP_MEMZERO(icbp, sizeof (*icbp));
1786 	icbp->icb_fwoptions1 = fcp->isp_fwoptions;
1787 	if (fcp->role & ISP_ROLE_TARGET) {
1788 		icbp->icb_fwoptions1 |= ICB2400_OPT1_TGT_ENABLE;
1789 	} else {
1790 		icbp->icb_fwoptions1 &= ~ICB2400_OPT1_TGT_ENABLE;
1791 	}
1792 
1793 	if (fcp->role & ISP_ROLE_INITIATOR) {
1794 		icbp->icb_fwoptions1 &= ~ICB2400_OPT1_INI_DISABLE;
1795 	} else {
1796 		icbp->icb_fwoptions1 |= ICB2400_OPT1_INI_DISABLE;
1797 	}
1798 
1799 	icbp->icb_version = ICB_VERSION1;
1800 	icbp->icb_maxfrmlen = DEFAULT_FRAMESIZE(isp);
1801 	if (icbp->icb_maxfrmlen < ICB_MIN_FRMLEN || icbp->icb_maxfrmlen > ICB_MAX_FRMLEN) {
1802 		isp_prt(isp, ISP_LOGERR, "bad frame length (%d) from NVRAM- using %d", DEFAULT_FRAMESIZE(isp), ICB_DFLT_FRMLEN);
1803 		icbp->icb_maxfrmlen = ICB_DFLT_FRMLEN;
1804 	}
1805 
1806 	icbp->icb_execthrottle = DEFAULT_EXEC_THROTTLE(isp);
1807 	if (icbp->icb_execthrottle < 1) {
1808 		isp_prt(isp, ISP_LOGERR, "bad execution throttle of %d- using %d", DEFAULT_EXEC_THROTTLE(isp), ICB_DFLT_THROTTLE);
1809 		icbp->icb_execthrottle = ICB_DFLT_THROTTLE;
1810 	}
1811 
1812 	if (icbp->icb_fwoptions1 & ICB2400_OPT1_TGT_ENABLE) {
1813 		/*
1814 		 * Get current resource count
1815 		 */
1816 		MBSINIT(&mbs, MBOX_GET_RESOURCE_COUNT, MBLOGALL, 0);
1817 		mbs.obits = 0x4cf;
1818 		isp_mboxcmd(isp, &mbs);
1819 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
1820 			return;
1821 		}
1822 		icbp->icb_xchgcnt = mbs.param[3];
1823 	}
1824 
1825 
1826 	icbp->icb_hardaddr = fcp->isp_loopid;
1827 	if (icbp->icb_hardaddr >= LOCAL_LOOP_LIM) {
1828 		icbp->icb_hardaddr = 0;
1829 	}
1830 
1831 	/*
1832 	 * Force this on.
1833 	 */
1834 	icbp->icb_fwoptions1 |= ICB2400_OPT1_HARD_ADDRESS;
1835 
1836 	icbp->icb_fwoptions2 = fcp->isp_xfwoptions;
1837 	switch (isp->isp_confopts & ISP_CFG_PORT_PREF) {
1838 #if	0
1839 	case ISP_CFG_NPORT:
1840 		/*
1841 		 * XXX: This causes the f/w to crash.
1842 		 */
1843 		icbp->icb_fwoptions2 &= ~ICB2400_OPT2_TOPO_MASK;
1844 		icbp->icb_fwoptions2 |= ICB2400_OPT2_PTP_2_LOOP;
1845 		break;
1846 #endif
1847 	case ISP_CFG_NPORT_ONLY:
1848 		icbp->icb_fwoptions2 &= ~ICB2400_OPT2_TOPO_MASK;
1849 		icbp->icb_fwoptions2 |= ICB2400_OPT2_PTP_ONLY;
1850 		break;
1851 	case ISP_CFG_LPORT_ONLY:
1852 		icbp->icb_fwoptions2 &= ~ICB2400_OPT2_TOPO_MASK;
1853 		icbp->icb_fwoptions2 |= ICB2400_OPT2_LOOP_ONLY;
1854 		break;
1855 	default:
1856 		icbp->icb_fwoptions2 &= ~ICB2400_OPT2_TOPO_MASK;
1857 		icbp->icb_fwoptions2 |= ICB2400_OPT2_LOOP_2_PTP;
1858 		break;
1859 	}
1860 
1861 	/* force this on for now */
1862 	icbp->icb_fwoptions2 |= ICB2400_OPT2_ZIO;
1863 
1864 	switch (icbp->icb_fwoptions2 & ICB2400_OPT2_TIMER_MASK) {
1865 	case ICB2400_OPT2_ZIO:
1866 	case ICB2400_OPT2_ZIO1:
1867 		icbp->icb_idelaytimer = 0;
1868 		break;
1869 	case 0:
1870 		break;
1871 	default:
1872 		isp_prt(isp, ISP_LOGWARN, "bad value %x in fwopt2 timer field", icbp->icb_fwoptions2 & ICB2400_OPT2_TIMER_MASK);
1873 		icbp->icb_fwoptions2 &= ~ICB2400_OPT2_TIMER_MASK;
1874 		break;
1875 	}
1876 
1877 	/*
1878 	 * We don't support FCTAPE, so clear it.
1879 	 */
1880 	icbp->icb_fwoptions2 &= ~ICB2400_OPT2_FCTAPE;
1881 
1882 	icbp->icb_fwoptions3 = fcp->isp_zfwoptions;
1883 	icbp->icb_fwoptions3 &= ~ICB2400_OPT3_RATE_AUTO;
1884 	if (isp->isp_confopts & ISP_CFG_ONEGB) {
1885 		icbp->icb_fwoptions3 |= ICB2400_OPT3_RATE_ONEGB;
1886 	} else if (isp->isp_confopts & ISP_CFG_TWOGB) {
1887 		icbp->icb_fwoptions3 |= ICB2400_OPT3_RATE_TWOGB;
1888 	} else if (isp->isp_confopts & ISP_CFG_FOURGB) {
1889 		icbp->icb_fwoptions3 |= ICB2400_OPT3_RATE_FOURGB;
1890 	} else {
1891 		icbp->icb_fwoptions3 |= ICB2400_OPT3_RATE_AUTO;
1892 	}
1893 
1894 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0) {
1895 		icbp->icb_fwoptions3 |= ICB2400_OPT3_SOFTID;
1896 	}
1897 	icbp->icb_logintime = ICB_LOGIN_TOV;
1898 
1899 	if (fcp->isp_wwnn && fcp->isp_wwpn && (fcp->isp_wwnn >> 60) != 2) {
1900 		icbp->icb_fwoptions1 |= ICB2400_OPT1_BOTH_WWNS;
1901 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_portname, fcp->isp_wwpn);
1902 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_nodename, fcp->isp_wwnn);
1903 		isp_prt(isp, ISP_LOGDEBUG1, "Setting ICB Node 0x%08x%08x Port 0x%08x%08x", ((uint32_t) (fcp->isp_wwnn >> 32)), ((uint32_t) (fcp->isp_wwnn)),
1904 		    ((uint32_t) (fcp->isp_wwpn >> 32)), ((uint32_t) (fcp->isp_wwpn)));
1905 	} else if (fcp->isp_wwpn) {
1906 		icbp->icb_fwoptions1 &= ~ICB2400_OPT1_BOTH_WWNS;
1907 		MAKE_NODE_NAME_FROM_WWN(icbp->icb_portname, fcp->isp_wwpn);
1908 		isp_prt(isp, ISP_LOGDEBUG1, "Setting ICB Node to be same as Port 0x%08x%08x", ((uint32_t) (fcp->isp_wwpn >> 32)), ((uint32_t) (fcp->isp_wwpn)));
1909 	} else {
1910 		isp_prt(isp, ISP_LOGERR, "No valid WWNs to use");
1911 		return;
1912 	}
1913 	icbp->icb_retry_count = fcp->isp_retry_count;
1914 
1915 	icbp->icb_rqstqlen = RQUEST_QUEUE_LEN(isp);
1916 	if (icbp->icb_rqstqlen < 8) {
1917 		isp_prt(isp, ISP_LOGERR, "bad request queue length %d", icbp->icb_rqstqlen);
1918 		return;
1919 	}
1920 	icbp->icb_rsltqlen = RESULT_QUEUE_LEN(isp);
1921 	if (icbp->icb_rsltqlen < 8) {
1922 		isp_prt(isp, ISP_LOGERR, "bad result queue length %d",
1923 		    icbp->icb_rsltqlen);
1924 		return;
1925 	}
1926 	icbp->icb_rqstaddr[RQRSP_ADDR0015] = DMA_WD0(isp->isp_rquest_dma);
1927 	icbp->icb_rqstaddr[RQRSP_ADDR1631] = DMA_WD1(isp->isp_rquest_dma);
1928 	icbp->icb_rqstaddr[RQRSP_ADDR3247] = DMA_WD2(isp->isp_rquest_dma);
1929 	icbp->icb_rqstaddr[RQRSP_ADDR4863] = DMA_WD3(isp->isp_rquest_dma);
1930 
1931 	icbp->icb_respaddr[RQRSP_ADDR0015] = DMA_WD0(isp->isp_result_dma);
1932 	icbp->icb_respaddr[RQRSP_ADDR1631] = DMA_WD1(isp->isp_result_dma);
1933 	icbp->icb_respaddr[RQRSP_ADDR3247] = DMA_WD2(isp->isp_result_dma);
1934 	icbp->icb_respaddr[RQRSP_ADDR4863] = DMA_WD3(isp->isp_result_dma);
1935 
1936 #ifdef	ISP_TARGET_MODE
1937 	/* unconditionally set up the ATIO queue if we support target mode */
1938 	icbp->icb_atioqlen = RESULT_QUEUE_LEN(isp);
1939 	if (icbp->icb_atioqlen < 8) {
1940 		isp_prt(isp, ISP_LOGERR, "bad ATIO queue length %d", icbp->icb_atioqlen);
1941 		return;
1942 	}
1943 	icbp->icb_atioqaddr[RQRSP_ADDR0015] = DMA_WD0(isp->isp_atioq_dma);
1944 	icbp->icb_atioqaddr[RQRSP_ADDR1631] = DMA_WD1(isp->isp_atioq_dma);
1945 	icbp->icb_atioqaddr[RQRSP_ADDR3247] = DMA_WD2(isp->isp_atioq_dma);
1946 	icbp->icb_atioqaddr[RQRSP_ADDR4863] = DMA_WD3(isp->isp_atioq_dma);
1947 	isp_prt(isp, ISP_LOGDEBUG0, "isp_fibre_init_2400: atioq %04x%04x%04x%04x", DMA_WD3(isp->isp_atioq_dma), DMA_WD2(isp->isp_atioq_dma),
1948 	    DMA_WD1(isp->isp_atioq_dma), DMA_WD0(isp->isp_atioq_dma));
1949 #endif
1950 
1951 	isp_prt(isp, ISP_LOGDEBUG0, "isp_fibre_init_2400: fwopt1 0x%x fwopt2 0x%x fwopt3 0x%x", icbp->icb_fwoptions1, icbp->icb_fwoptions2, icbp->icb_fwoptions3);
1952 
1953 	isp_prt(isp, ISP_LOGDEBUG0, "isp_fibre_init_2400: rqst %04x%04x%04x%04x rsp %04x%04x%04x%04x", DMA_WD3(isp->isp_rquest_dma), DMA_WD2(isp->isp_rquest_dma),
1954 	    DMA_WD1(isp->isp_rquest_dma), DMA_WD0(isp->isp_rquest_dma), DMA_WD3(isp->isp_result_dma), DMA_WD2(isp->isp_result_dma),
1955 	    DMA_WD1(isp->isp_result_dma), DMA_WD0(isp->isp_result_dma));
1956 
1957 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
1958 		isp_print_bytes(isp, "isp_fibre_init_2400", sizeof (*icbp), icbp);
1959 	}
1960 
1961 	if (FC_SCRATCH_ACQUIRE(isp, 0)) {
1962 		isp_prt(isp, ISP_LOGERR, sacq);
1963 		return;
1964 	}
1965 	ISP_MEMZERO(fcp->isp_scratch, ISP_FC_SCRLEN);
1966 	isp_put_icb_2400(isp, icbp, fcp->isp_scratch);
1967 
1968 	/*
1969 	 * Now fill in information about any additional channels
1970 	 */
1971 	if (isp->isp_nchan > 1) {
1972 		isp_icb_2400_vpinfo_t vpinfo, *vdst;
1973 		vp_port_info_t pi, *pdst;
1974 		size_t amt = 0;
1975 		uint8_t *off;
1976 
1977 		vpinfo.vp_count = isp->isp_nchan - 1;
1978 		vpinfo.vp_global_options = 0;
1979 		off = fcp->isp_scratch;
1980 		off += ICB2400_VPINFO_OFF;
1981 		vdst = (isp_icb_2400_vpinfo_t *) off;
1982 		isp_put_icb_2400_vpinfo(isp, &vpinfo, vdst);
1983 		amt = ICB2400_VPINFO_OFF + sizeof (isp_icb_2400_vpinfo_t);
1984 		for (chan = 1; chan < isp->isp_nchan; chan++) {
1985 			fcparam *fcp2;
1986 
1987 			ISP_MEMZERO(&pi, sizeof (pi));
1988 			fcp2 = FCPARAM(isp, chan);
1989 			if (fcp2->role != ISP_ROLE_NONE) {
1990 				pi.vp_port_options = ICB2400_VPOPT_ENABLED;
1991 				if (fcp2->role & ISP_ROLE_INITIATOR) {
1992 					pi.vp_port_options |= ICB2400_VPOPT_INI_ENABLE;
1993 				}
1994 				if ((fcp2->role & ISP_ROLE_TARGET) == 0) {
1995 					pi.vp_port_options |= ICB2400_VPOPT_TGT_DISABLE;
1996 				}
1997 				MAKE_NODE_NAME_FROM_WWN(pi.vp_port_portname, fcp2->isp_wwpn);
1998 				MAKE_NODE_NAME_FROM_WWN(pi.vp_port_nodename, fcp2->isp_wwnn);
1999 			}
2000 			off = fcp->isp_scratch;
2001 			off += ICB2400_VPINFO_PORT_OFF(chan);
2002 			pdst = (vp_port_info_t *) off;
2003 			isp_put_vp_port_info(isp, &pi, pdst);
2004 			amt += ICB2400_VPOPT_WRITE_SIZE;
2005 		}
2006 	}
2007 
2008 	/*
2009 	 * Init the firmware
2010 	 */
2011 	MBSINIT(&mbs, 0, MBLOGALL, 30000000);
2012 	if (isp->isp_nchan > 1) {
2013 		mbs.param[0] = MBOX_INIT_FIRMWARE_MULTI_ID;
2014 	} else {
2015 		mbs.param[0] = MBOX_INIT_FIRMWARE;
2016 	}
2017 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
2018 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
2019 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
2020 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
2021 	isp_prt(isp, ISP_LOGDEBUG0, "INIT F/W from %04x%04x%04x%04x", DMA_WD3(fcp->isp_scdma), DMA_WD2(fcp->isp_scdma), DMA_WD1(fcp->isp_scdma), DMA_WD0(fcp->isp_scdma));
2022 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, sizeof (*icbp), 0);
2023 	isp_mboxcmd(isp, &mbs);
2024 	FC_SCRATCH_RELEASE(isp, 0);
2025 
2026 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
2027 		return;
2028 	}
2029 	isp->isp_reqidx = 0;
2030 	isp->isp_reqodx = 0;
2031 	isp->isp_residx = 0;
2032 
2033 	/*
2034 	 * Whatever happens, we're now committed to being here.
2035 	 */
2036 	isp->isp_state = ISP_INITSTATE;
2037 }
2038 
2039 static void
2040 isp_mark_portdb(ispsoftc_t *isp, int chan, int disposition)
2041 {
2042 	fcparam *fcp = FCPARAM(isp, chan);
2043 	int i;
2044 
2045 	if (chan < 0 || chan >= isp->isp_nchan) {
2046 		isp_prt(isp, ISP_LOGWARN, "isp_mark_portdb: bad channel %d", chan);
2047 		return;
2048 	}
2049 	for (i = 0; i < MAX_FC_TARG; i++) {
2050 		if (fcp->portdb[i].target_mode) {
2051 			if (disposition < 0) {
2052 				isp_prt(isp, ISP_LOGTINFO, "isp_mark_portdb: Chan %d zeroing handle 0x" "%04x port 0x%06x", chan,
2053 				    fcp->portdb[i].handle, fcp->portdb[i].portid);
2054 				ISP_MEMZERO(&fcp->portdb[i], sizeof (fcportdb_t));
2055 			}
2056 			continue;
2057 		}
2058 		if (disposition == 0) {
2059 			ISP_MEMZERO(&fcp->portdb[i], sizeof (fcportdb_t));
2060 		} else {
2061 			switch (fcp->portdb[i].state) {
2062 			case FC_PORTDB_STATE_CHANGED:
2063 			case FC_PORTDB_STATE_PENDING_VALID:
2064 			case FC_PORTDB_STATE_VALID:
2065 			case FC_PORTDB_STATE_PROBATIONAL:
2066 				fcp->portdb[i].state = FC_PORTDB_STATE_PROBATIONAL;
2067 				break;
2068 			case FC_PORTDB_STATE_ZOMBIE:
2069 				break;
2070 			case FC_PORTDB_STATE_NIL:
2071 			default:
2072 				ISP_MEMZERO(&fcp->portdb[i], sizeof (fcportdb_t));
2073 				fcp->portdb[i].state = FC_PORTDB_STATE_NIL;
2074 				break;
2075 			}
2076 		}
2077 	}
2078 }
2079 
2080 /*
2081  * Perform an IOCB PLOGI or LOGO via EXECUTE IOCB A64 for 24XX cards
2082  * or via FABRIC LOGIN/FABRIC LOGOUT for other cards.
2083  */
2084 static int
2085 isp_plogx(ispsoftc_t *isp, int chan, uint16_t handle, uint32_t portid, int flags, int gs)
2086 {
2087 	mbreg_t mbs;
2088 	uint8_t q[QENTRY_LEN];
2089 	isp_plogx_t *plp;
2090 	fcparam *fcp;
2091 	uint8_t *scp;
2092 	uint32_t sst, parm1;
2093 	int rval;
2094 	const char *msg;
2095 	char buf[64];
2096 
2097 	if (!IS_24XX(isp)) {
2098 		int action = flags & PLOGX_FLG_CMD_MASK;
2099 		if (action == PLOGX_FLG_CMD_PLOGI) {
2100 			return (isp_port_login(isp, handle, portid));
2101 		} else if (action == PLOGX_FLG_CMD_LOGO) {
2102 			return (isp_port_logout(isp, handle, portid));
2103 		} else {
2104 			return (MBOX_INVALID_COMMAND);
2105 		}
2106 	}
2107 
2108 	ISP_MEMZERO(q, QENTRY_LEN);
2109 	plp = (isp_plogx_t *) q;
2110 	plp->plogx_header.rqs_entry_count = 1;
2111 	plp->plogx_header.rqs_entry_type = RQSTYPE_LOGIN;
2112 	plp->plogx_handle = 0xffffffff;
2113 	plp->plogx_nphdl = handle;
2114 	plp->plogx_vphdl = chan;
2115 	plp->plogx_portlo = portid;
2116 	plp->plogx_rspsz_porthi = (portid >> 16) & 0xff;
2117 	plp->plogx_flags = flags;
2118 
2119 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
2120 		isp_print_bytes(isp, "IOCB LOGX", QENTRY_LEN, plp);
2121 	}
2122 
2123 	if (gs == 0) {
2124 		if (FC_SCRATCH_ACQUIRE(isp, chan)) {
2125 			isp_prt(isp, ISP_LOGERR, sacq);
2126 			return (-1);
2127 		}
2128 	}
2129 	fcp = FCPARAM(isp, chan);
2130 	scp = fcp->isp_scratch;
2131 	isp_put_plogx(isp, plp, (isp_plogx_t *) scp);
2132 
2133 	MBSINIT(&mbs, MBOX_EXEC_COMMAND_IOCB_A64, MBLOGALL, 500000);
2134 	mbs.param[1] = QENTRY_LEN;
2135 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
2136 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
2137 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
2138 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
2139 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, QENTRY_LEN, chan);
2140 	isp_mboxcmd(isp, &mbs);
2141 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
2142 		rval = mbs.param[0];
2143 		goto out;
2144 	}
2145 	MEMORYBARRIER(isp, SYNC_SFORCPU, QENTRY_LEN, QENTRY_LEN, chan);
2146 	scp += QENTRY_LEN;
2147 	isp_get_plogx(isp, (isp_plogx_t *) scp, plp);
2148 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
2149 		isp_print_bytes(isp, "IOCB LOGX response", QENTRY_LEN, plp);
2150 	}
2151 
2152 	if (plp->plogx_status == PLOGX_STATUS_OK) {
2153 		rval = 0;
2154 		goto out;
2155 	} else if (plp->plogx_status != PLOGX_STATUS_IOCBERR) {
2156 		isp_prt(isp, ISP_LOGWARN,
2157 		    "status 0x%x on port login IOCB channel %d",
2158 		    plp->plogx_status, chan);
2159 		rval = -1;
2160 		goto out;
2161 	}
2162 
2163 	sst = plp->plogx_ioparm[0].lo16 | (plp->plogx_ioparm[0].hi16 << 16);
2164 	parm1 = plp->plogx_ioparm[1].lo16 | (plp->plogx_ioparm[1].hi16 << 16);
2165 
2166 	rval = -1;
2167 	msg = NULL;
2168 
2169 	switch (sst) {
2170 	case PLOGX_IOCBERR_NOLINK:
2171 		msg = "no link";
2172 		break;
2173 	case PLOGX_IOCBERR_NOIOCB:
2174 		msg = "no IOCB buffer";
2175 		break;
2176 	case PLOGX_IOCBERR_NOXGHG:
2177 		msg = "no Exchange Control Block";
2178 		break;
2179 	case PLOGX_IOCBERR_FAILED:
2180 		ISP_SNPRINTF(buf, sizeof (buf), "reason 0x%x (last LOGIN state 0x%x)", parm1 & 0xff, (parm1 >> 8) & 0xff);
2181 		msg = buf;
2182 		break;
2183 	case PLOGX_IOCBERR_NOFABRIC:
2184 		msg = "no fabric";
2185 		break;
2186 	case PLOGX_IOCBERR_NOTREADY:
2187 		msg = "firmware not ready";
2188 		break;
2189 	case PLOGX_IOCBERR_NOLOGIN:
2190 		ISP_SNPRINTF(buf, sizeof (buf), "not logged in (last state 0x%x)", parm1);
2191 		msg = buf;
2192 		rval = MBOX_NOT_LOGGED_IN;
2193 		break;
2194 	case PLOGX_IOCBERR_REJECT:
2195 		ISP_SNPRINTF(buf, sizeof (buf), "LS_RJT = 0x%x", parm1);
2196 		msg = buf;
2197 		break;
2198 	case PLOGX_IOCBERR_NOPCB:
2199 		msg = "no PCB allocated";
2200 		break;
2201 	case PLOGX_IOCBERR_EINVAL:
2202 		ISP_SNPRINTF(buf, sizeof (buf), "invalid parameter at offset 0x%x", parm1);
2203 		msg = buf;
2204 		break;
2205 	case PLOGX_IOCBERR_PORTUSED:
2206 		ISP_SNPRINTF(buf, sizeof (buf), "already logged in with N-Port handle 0x%x", parm1);
2207 		msg = buf;
2208 		rval = MBOX_PORT_ID_USED | (parm1 << 16);
2209 		break;
2210 	case PLOGX_IOCBERR_HNDLUSED:
2211 		ISP_SNPRINTF(buf, sizeof (buf), "handle already used for PortID 0x%06x", parm1);
2212 		msg = buf;
2213 		rval = MBOX_LOOP_ID_USED;
2214 		break;
2215 	case PLOGX_IOCBERR_NOHANDLE:
2216 		msg = "no handle allocated";
2217 		break;
2218 	case PLOGX_IOCBERR_NOFLOGI:
2219 		msg = "no FLOGI_ACC";
2220 		break;
2221 	default:
2222 		ISP_SNPRINTF(buf, sizeof (buf), "status %x from %x", plp->plogx_status, flags);
2223 		msg = buf;
2224 		break;
2225 	}
2226 	if (msg) {
2227 		isp_prt(isp, ISP_LOGERR, "Chan %d PLOGX PortID 0x%06x to N-Port handle 0x%x: %s", chan, portid, handle, msg);
2228 	}
2229 out:
2230 	if (gs == 0) {
2231 		FC_SCRATCH_RELEASE(isp, chan);
2232 	}
2233 	return (rval);
2234 }
2235 
2236 static int
2237 isp_port_login(ispsoftc_t *isp, uint16_t handle, uint32_t portid)
2238 {
2239 	mbreg_t mbs;
2240 
2241 	MBSINIT(&mbs, MBOX_FABRIC_LOGIN, MBLOGNONE, 500000);
2242 	if (ISP_CAP_2KLOGIN(isp)) {
2243 		mbs.param[1] = handle;
2244 		mbs.ibits = (1 << 10);
2245 	} else {
2246 		mbs.param[1] = handle << 8;
2247 	}
2248 	mbs.param[2] = portid >> 16;
2249 	mbs.param[3] = portid;
2250 	mbs.logval = MBLOGNONE;
2251 	mbs.timeout = 500000;
2252 	isp_mboxcmd(isp, &mbs);
2253 
2254 	switch (mbs.param[0]) {
2255 	case MBOX_PORT_ID_USED:
2256 		isp_prt(isp, ISP_LOGDEBUG0,
2257 		    "isp_port_login: portid 0x%06x already logged in as %u",
2258 		    portid, mbs.param[1]);
2259 		return (MBOX_PORT_ID_USED | (mbs.param[1] << 16));
2260 
2261 	case MBOX_LOOP_ID_USED:
2262 		isp_prt(isp, ISP_LOGDEBUG0,
2263 		    "isp_port_login: handle 0x%04x in use for port id 0x%02xXXXX",
2264 		    handle, mbs.param[1] & 0xff);
2265 		return (MBOX_LOOP_ID_USED);
2266 
2267 	case MBOX_COMMAND_COMPLETE:
2268 		return (0);
2269 
2270 	case MBOX_COMMAND_ERROR:
2271 		isp_prt(isp, ISP_LOGINFO,
2272 		    "isp_port_login: error 0x%x in PLOGI to port 0x%06x",
2273 		    mbs.param[1], portid);
2274 		return (MBOX_COMMAND_ERROR);
2275 
2276 	case MBOX_ALL_IDS_USED:
2277 		isp_prt(isp, ISP_LOGINFO,
2278 		    "isp_port_login: all IDs used for fabric login");
2279 		return (MBOX_ALL_IDS_USED);
2280 
2281 	default:
2282 		isp_prt(isp, ISP_LOGINFO,
2283 		    "isp_port_login: error 0x%x on port login of 0x%06x@0x%0x",
2284 		    mbs.param[0], portid, handle);
2285 		return (mbs.param[0]);
2286 	}
2287 }
2288 
2289 static int
2290 isp_port_logout(ispsoftc_t *isp, uint16_t handle, uint32_t portid)
2291 {
2292 	mbreg_t mbs;
2293 
2294 	MBSINIT(&mbs, MBOX_FABRIC_LOGOUT, MBLOGNONE, 500000);
2295 	if (ISP_CAP_2KLOGIN(isp)) {
2296 		mbs.param[1] = handle;
2297 		mbs.ibits = (1 << 10);
2298 	} else {
2299 		mbs.param[1] = handle << 8;
2300 	}
2301 	isp_mboxcmd(isp, &mbs);
2302 	return (mbs.param[0] == MBOX_COMMAND_COMPLETE? 0 : mbs.param[0]);
2303 }
2304 
2305 static int
2306 isp_getpdb(ispsoftc_t *isp, int chan, uint16_t id, isp_pdb_t *pdb, int dolock)
2307 {
2308 	fcparam *fcp = FCPARAM(isp, chan);
2309 	mbreg_t mbs;
2310 	union {
2311 		isp_pdb_21xx_t fred;
2312 		isp_pdb_24xx_t bill;
2313 	} un;
2314 
2315 	MBSINIT(&mbs, MBOX_GET_PORT_DB, MBLOGALL & ~MBOX_COMMAND_PARAM_ERROR, 250000);
2316 	if (IS_24XX(isp)) {
2317 		mbs.ibits = (1 << 9)|(1 << 10);
2318 		mbs.param[1] = id;
2319 		mbs.param[9] = chan;
2320 	} else if (ISP_CAP_2KLOGIN(isp)) {
2321 		mbs.param[1] = id;
2322 	} else {
2323 		mbs.param[1] = id << 8;
2324 	}
2325 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
2326 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
2327 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
2328 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
2329 	if (dolock) {
2330 		if (FC_SCRATCH_ACQUIRE(isp, chan)) {
2331 			isp_prt(isp, ISP_LOGERR, sacq);
2332 			return (-1);
2333 		}
2334 	}
2335 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, sizeof (un), chan);
2336 	isp_mboxcmd(isp, &mbs);
2337 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
2338 		if (dolock) {
2339 			FC_SCRATCH_RELEASE(isp, chan);
2340 		}
2341 		return (mbs.param[0]);
2342 	}
2343 	if (IS_24XX(isp)) {
2344 		isp_get_pdb_24xx(isp, fcp->isp_scratch, &un.bill);
2345 		pdb->handle = un.bill.pdb_handle;
2346 		pdb->s3_role = un.bill.pdb_prli_svc3;
2347 		pdb->portid = BITS2WORD_24XX(un.bill.pdb_portid_bits);
2348 		ISP_MEMCPY(pdb->portname, un.bill.pdb_portname, 8);
2349 		ISP_MEMCPY(pdb->nodename, un.bill.pdb_nodename, 8);
2350 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2351 		    "Chan %d Port 0x%06x flags 0x%x curstate %x",
2352 		    chan, pdb->portid, un.bill.pdb_flags,
2353 		    un.bill.pdb_curstate);
2354 		if (un.bill.pdb_curstate < PDB2400_STATE_PLOGI_DONE ||
2355 		    un.bill.pdb_curstate > PDB2400_STATE_LOGGED_IN) {
2356 			mbs.param[0] = MBOX_NOT_LOGGED_IN;
2357 			if (dolock) {
2358 				FC_SCRATCH_RELEASE(isp, chan);
2359 			}
2360 			return (mbs.param[0]);
2361 		}
2362 	} else {
2363 		isp_get_pdb_21xx(isp, fcp->isp_scratch, &un.fred);
2364 		pdb->handle = un.fred.pdb_loopid;
2365 		pdb->s3_role = un.fred.pdb_prli_svc3;
2366 		pdb->portid = BITS2WORD(un.fred.pdb_portid_bits);
2367 		ISP_MEMCPY(pdb->portname, un.fred.pdb_portname, 8);
2368 		ISP_MEMCPY(pdb->nodename, un.fred.pdb_nodename, 8);
2369 	}
2370 	if (dolock) {
2371 		FC_SCRATCH_RELEASE(isp, chan);
2372 	}
2373 	return (0);
2374 }
2375 
2376 static void
2377 isp_dump_chip_portdb(ispsoftc_t *isp, int chan, int dolock)
2378 {
2379 	isp_pdb_t pdb;
2380 	int lim, loopid;
2381 
2382 	if (ISP_CAP_2KLOGIN(isp)) {
2383 		lim = NPH_MAX_2K;
2384 	} else {
2385 		lim = NPH_MAX;
2386 	}
2387 	for (loopid = 0; loopid != lim; loopid++) {
2388 		if (isp_getpdb(isp, chan, loopid, &pdb, dolock)) {
2389 			continue;
2390 		}
2391 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGINFO, "Chan %d Loopid 0x%04x "
2392 		    "PortID 0x%06x WWPN 0x%02x%02x%02x%02x%02x%02x%02x%02x",
2393 		    chan, loopid, pdb.portid, pdb.portname[0], pdb.portname[1],
2394 		    pdb.portname[2], pdb.portname[3], pdb.portname[4],
2395 		    pdb.portname[5], pdb.portname[6], pdb.portname[7]);
2396 	}
2397 }
2398 
2399 static uint64_t
2400 isp_get_wwn(ispsoftc_t *isp, int chan, int loopid, int nodename)
2401 {
2402 	uint64_t wwn = INI_NONE;
2403 	fcparam *fcp = FCPARAM(isp, chan);
2404 	mbreg_t mbs;
2405 
2406 	if (fcp->isp_fwstate < FW_READY ||
2407 	    fcp->isp_loopstate < LOOP_PDB_RCVD) {
2408 		return (wwn);
2409 	}
2410 	MBSINIT(&mbs, MBOX_GET_PORT_NAME, MBLOGALL & ~MBOX_COMMAND_PARAM_ERROR, 500000);
2411 	if (ISP_CAP_2KLOGIN(isp)) {
2412 		mbs.param[1] = loopid;
2413 		mbs.ibits = (1 << 10);
2414 		if (nodename) {
2415 			mbs.param[10] = 1;
2416 		}
2417 		if (ISP_CAP_MULTI_ID(isp)) {
2418 			mbs.ibits |= (1 << 9);
2419 			mbs.param[9] = chan;
2420 		}
2421 	} else {
2422 		mbs.param[1] = loopid << 8;
2423 		if (nodename) {
2424 			mbs.param[1] |= 1;
2425 		}
2426 	}
2427 	isp_mboxcmd(isp, &mbs);
2428 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
2429 		return (wwn);
2430 	}
2431 	if (IS_24XX(isp)) {
2432 		wwn =
2433 		    (((uint64_t)(mbs.param[2] >> 8))	<< 56) |
2434 		    (((uint64_t)(mbs.param[2] & 0xff))	<< 48) |
2435 		    (((uint64_t)(mbs.param[3] >> 8))	<< 40) |
2436 		    (((uint64_t)(mbs.param[3] & 0xff))	<< 32) |
2437 		    (((uint64_t)(mbs.param[6] >> 8))	<< 24) |
2438 		    (((uint64_t)(mbs.param[6] & 0xff))	<< 16) |
2439 		    (((uint64_t)(mbs.param[7] >> 8))	<<  8) |
2440 		    (((uint64_t)(mbs.param[7] & 0xff)));
2441 	} else {
2442 		wwn =
2443 		    (((uint64_t)(mbs.param[2] & 0xff))  << 56) |
2444 		    (((uint64_t)(mbs.param[2] >> 8))	<< 48) |
2445 		    (((uint64_t)(mbs.param[3] & 0xff))	<< 40) |
2446 		    (((uint64_t)(mbs.param[3] >> 8))	<< 32) |
2447 		    (((uint64_t)(mbs.param[6] & 0xff))	<< 24) |
2448 		    (((uint64_t)(mbs.param[6] >> 8))	<< 16) |
2449 		    (((uint64_t)(mbs.param[7] & 0xff))	<<  8) |
2450 		    (((uint64_t)(mbs.param[7] >> 8)));
2451 	}
2452 	return (wwn);
2453 }
2454 
2455 /*
2456  * Make sure we have good FC link.
2457  */
2458 
2459 static int
2460 isp_fclink_test(ispsoftc_t *isp, int chan, int usdelay)
2461 {
2462 	mbreg_t mbs;
2463 	int count, check_for_fabric, r;
2464 	uint8_t lwfs;
2465 	int loopid;
2466 	fcparam *fcp;
2467 	fcportdb_t *lp;
2468 	isp_pdb_t pdb;
2469 
2470 	fcp = FCPARAM(isp, chan);
2471 
2472 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0, "Chan %d FC Link Test Entry", chan);
2473 	ISP_MARK_PORTDB(isp, chan, 1);
2474 
2475 	/*
2476 	 * Wait up to N microseconds for F/W to go to a ready state.
2477 	 */
2478 	lwfs = FW_CONFIG_WAIT;
2479 	count = 0;
2480 	while (count < usdelay) {
2481 		uint64_t enano;
2482 		uint32_t wrk;
2483 		NANOTIME_T hra, hrb;
2484 
2485 		GET_NANOTIME(&hra);
2486 		isp_fw_state(isp, chan);
2487 		if (lwfs != fcp->isp_fwstate) {
2488 			isp_prt(isp, ISP_LOGCONFIG|ISP_LOGSANCFG, "Chan %d Firmware State <%s->%s>", chan, isp_fc_fw_statename((int)lwfs), isp_fc_fw_statename((int)fcp->isp_fwstate));
2489 			lwfs = fcp->isp_fwstate;
2490 		}
2491 		if (fcp->isp_fwstate == FW_READY) {
2492 			break;
2493 		}
2494 		GET_NANOTIME(&hrb);
2495 
2496 		/*
2497 		 * Get the elapsed time in nanoseconds.
2498 		 * Always guaranteed to be non-zero.
2499 		 */
2500 		enano = NANOTIME_SUB(&hrb, &hra);
2501 
2502 		isp_prt(isp, ISP_LOGDEBUG1, "usec%d: 0x%lx->0x%lx enano 0x%x%08x", count, (long) GET_NANOSEC(&hra), (long) GET_NANOSEC(&hrb), (uint32_t)(enano >> 32), (uint32_t)(enano));
2503 
2504 		/*
2505 		 * If the elapsed time is less than 1 millisecond,
2506 		 * delay a period of time up to that millisecond of
2507 		 * waiting.
2508 		 *
2509 		 * This peculiar code is an attempt to try and avoid
2510 		 * invoking uint64_t math support functions for some
2511 		 * platforms where linkage is a problem.
2512 		 */
2513 		if (enano < (1000 * 1000)) {
2514 			count += 1000;
2515 			enano = (1000 * 1000) - enano;
2516 			while (enano > (uint64_t) 4000000000U) {
2517 				ISP_SLEEP(isp, 4000000);
2518 				enano -= (uint64_t) 4000000000U;
2519 			}
2520 			wrk = enano;
2521 			wrk /= 1000;
2522 			ISP_SLEEP(isp, wrk);
2523 		} else {
2524 			while (enano > (uint64_t) 4000000000U) {
2525 				count += 4000000;
2526 				enano -= (uint64_t) 4000000000U;
2527 			}
2528 			wrk = enano;
2529 			count += (wrk / 1000);
2530 		}
2531 	}
2532 
2533 
2534 
2535 	/*
2536 	 * If we haven't gone to 'ready' state, return.
2537 	 */
2538 	if (fcp->isp_fwstate != FW_READY) {
2539 		isp_prt(isp, ISP_LOGSANCFG, "%s: chan %d not at FW_READY state", __func__, chan);
2540 		return (-1);
2541 	}
2542 
2543 	/*
2544 	 * Get our Loop ID and Port ID.
2545 	 */
2546 	MBSINIT(&mbs, MBOX_GET_LOOP_ID, MBLOGALL, 0);
2547 	if (ISP_CAP_MULTI_ID(isp)) {
2548 		mbs.param[9] = chan;
2549 		mbs.ibits = (1 << 9);
2550 		mbs.obits = (1 << 7);
2551 	}
2552 	isp_mboxcmd(isp, &mbs);
2553 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
2554 		return (-1);
2555 	}
2556 
2557 	if (ISP_CAP_2KLOGIN(isp)) {
2558 		fcp->isp_loopid = mbs.param[1];
2559 	} else {
2560 		fcp->isp_loopid = mbs.param[1] & 0xff;
2561 	}
2562 
2563 	if (IS_2100(isp)) {
2564 		fcp->isp_topo = TOPO_NL_PORT;
2565 	} else {
2566 		int topo = (int) mbs.param[6];
2567 		if (topo < TOPO_NL_PORT || topo > TOPO_PTP_STUB) {
2568 			topo = TOPO_PTP_STUB;
2569 		}
2570 		fcp->isp_topo = topo;
2571 	}
2572 	fcp->isp_portid = mbs.param[2] | (mbs.param[3] << 16);
2573 
2574 	if (IS_2100(isp)) {
2575 		/*
2576 		 * Don't bother with fabric if we are using really old
2577 		 * 2100 firmware. It's just not worth it.
2578 		 */
2579 		if (ISP_FW_NEWER_THAN(isp, 1, 15, 37)) {
2580 			check_for_fabric = 1;
2581 		} else {
2582 			check_for_fabric = 0;
2583 		}
2584 	} else if (fcp->isp_topo == TOPO_FL_PORT || fcp->isp_topo == TOPO_F_PORT) {
2585 		check_for_fabric = 1;
2586 	} else {
2587 		check_for_fabric = 0;
2588 	}
2589 
2590 	/*
2591 	 * Check to make sure we got a valid loopid
2592 	 * The 24XX seems to mess this up for multiple channels.
2593 	 */
2594 	if (fcp->isp_topo == TOPO_FL_PORT || fcp->isp_topo == TOPO_NL_PORT) {
2595 		uint8_t alpa = fcp->isp_portid;
2596 
2597 		if (alpa == 0) {
2598 			/* "Cannot Happen" */
2599 			isp_prt(isp, ISP_LOGWARN, "Zero AL_PA for Loop Topology?");
2600 		} else {
2601 			int i;
2602 			for (i = 0; alpa_map[i]; i++) {
2603 				if (alpa_map[i] == alpa) {
2604 					break;
2605 				}
2606 			}
2607 			if (alpa_map[i] && fcp->isp_loopid != i) {
2608 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0, "Chan %d deriving loopid %d from AL_PA map  (AL_PA 0x%x) and ignoring returned value %d (AL_PA 0x%x)", chan, i, alpa_map[i], fcp->isp_loopid, alpa);
2609 				fcp->isp_loopid = i;
2610 			}
2611 		}
2612 	}
2613 
2614 
2615 	if (IS_24XX(isp)) { /* XXX SHOULDN'T THIS BE FOR 2K F/W? XXX */
2616 		loopid = NPH_FL_ID;
2617 	} else {
2618 		loopid = FL_ID;
2619 	}
2620 	if (check_for_fabric) {
2621 		r = isp_getpdb(isp, chan, loopid, &pdb, 1);
2622 		if (r && (fcp->isp_topo == TOPO_F_PORT || fcp->isp_topo == TOPO_FL_PORT)) {
2623 			isp_prt(isp, ISP_LOGWARN, "fabric topology but cannot get info about fabric controller (0x%x)", r);
2624 			fcp->isp_topo = TOPO_PTP_STUB;
2625 		}
2626 	} else {
2627 		r = -1;
2628 	}
2629 	if (r == 0) {
2630 		if (IS_2100(isp)) {
2631 			fcp->isp_topo = TOPO_FL_PORT;
2632 		}
2633 		if (pdb.portid == 0) {
2634 			/*
2635 			 * Crock.
2636 			 */
2637 			fcp->isp_topo = TOPO_NL_PORT;
2638 			goto not_on_fabric;
2639 		}
2640 
2641 		/*
2642 		 * Save the Fabric controller's port database entry.
2643 		 */
2644 		lp = &fcp->portdb[FL_ID];
2645 		lp->state = FC_PORTDB_STATE_PENDING_VALID;
2646 		MAKE_WWN_FROM_NODE_NAME(lp->node_wwn, pdb.nodename);
2647 		MAKE_WWN_FROM_NODE_NAME(lp->port_wwn, pdb.portname);
2648 		lp->roles = (pdb.s3_role & SVC3_ROLE_MASK) >> SVC3_ROLE_SHIFT;
2649 		lp->portid = pdb.portid;
2650 		lp->handle = pdb.handle;
2651 		lp->new_portid = lp->portid;
2652 		lp->new_roles = lp->roles;
2653 		if (IS_24XX(isp)) {
2654 			fcp->inorder = (mbs.param[7] & ISP24XX_INORDER) != 0;
2655 			if (ISP_FW_NEWER_THAN(isp, 4, 0, 27)) {
2656 				fcp->npiv_fabric = (mbs.param[7] & ISP24XX_NPIV_SAN) != 0;
2657 				if (fcp->npiv_fabric) {
2658 					isp_prt(isp, ISP_LOGCONFIG, "fabric supports NP-IV");
2659 				}
2660 			}
2661 			if (chan) {
2662 				fcp->isp_sns_hdl = NPH_SNS_HDLBASE + chan;
2663 				r = isp_plogx(isp, chan, fcp->isp_sns_hdl, SNS_PORT_ID, PLOGX_FLG_CMD_PLOGI | PLOGX_FLG_COND_PLOGI | PLOGX_FLG_SKIP_PRLI, 0);
2664 				if (r) {
2665 					isp_prt(isp, ISP_LOGWARN, "%s: Chan %d cannot log into SNS", __func__, chan);
2666 					return (-1);
2667 				}
2668 			} else {
2669 				fcp->isp_sns_hdl = NPH_SNS_ID;
2670 			}
2671 			r = isp_register_fc4_type_24xx(isp, chan);
2672 		} else {
2673 			fcp->isp_sns_hdl = SNS_ID;
2674 			r = isp_register_fc4_type(isp, chan);
2675 		}
2676 		if (r) {
2677 			isp_prt(isp, ISP_LOGWARN|ISP_LOGSANCFG, "%s: register fc4 type failed", __func__);
2678 			return (-1);
2679 		}
2680 	} else {
2681 not_on_fabric:
2682 		fcp->portdb[FL_ID].state = FC_PORTDB_STATE_NIL;
2683 	}
2684 
2685 	fcp->isp_gbspeed = 1;
2686 	if (IS_23XX(isp) || IS_24XX(isp)) {
2687 		MBSINIT(&mbs, MBOX_GET_SET_DATA_RATE, MBLOGALL, 3000000);
2688 		mbs.param[1] = MBGSD_GET_RATE;
2689 		/* mbs.param[2] undefined if we're just getting rate */
2690 		isp_mboxcmd(isp, &mbs);
2691 		if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
2692 			if (mbs.param[1] == MBGSD_EIGHTGB) {
2693 				isp_prt(isp, ISP_LOGINFO, "Chan %d 8Gb link speed", chan);
2694 				fcp->isp_gbspeed = 8;
2695 			} else if (mbs.param[1] == MBGSD_FOURGB) {
2696 				isp_prt(isp, ISP_LOGINFO, "Chan %d 4Gb link speed", chan);
2697 				fcp->isp_gbspeed = 4;
2698 			} else if (mbs.param[1] == MBGSD_TWOGB) {
2699 				isp_prt(isp, ISP_LOGINFO, "Chan %d 2Gb link speed", chan);
2700 				fcp->isp_gbspeed = 2;
2701 			} else if (mbs.param[1] == MBGSD_ONEGB) {
2702 				isp_prt(isp, ISP_LOGINFO, "Chan %d 1Gb link speed", chan);
2703 				fcp->isp_gbspeed = 1;
2704 			}
2705 		}
2706 	}
2707 
2708 	/*
2709 	 * Announce ourselves, too.
2710 	 */
2711 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGCONFIG, topology, chan, (uint32_t) (fcp->isp_wwpn >> 32), (uint32_t) fcp->isp_wwpn, fcp->isp_portid, fcp->isp_loopid, isp_fc_toponame(fcp));
2712 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0, "Chan %d FC Link Test Complete", chan);
2713 	return (0);
2714 }
2715 
2716 /*
2717  * Complete the synchronization of our Port Database.
2718  *
2719  * At this point, we've scanned the local loop (if any) and the fabric
2720  * and performed fabric logins on all new devices.
2721  *
2722  * Our task here is to go through our port database and remove any entities
2723  * that are still marked probational (issuing PLOGO for ones which we had
2724  * PLOGI'd into) or are dead.
2725  *
2726  * Our task here is to also check policy to decide whether devices which
2727  * have *changed* in some way should still be kept active. For example,
2728  * if a device has just changed PortID, we can either elect to treat it
2729  * as an old device or as a newly arrived device (and notify the outer
2730  * layer appropriately).
2731  *
2732  * We also do initiator map target id assignment here for new initiator
2733  * devices and refresh old ones ot make sure that they point to the corret
2734  * entities.
2735  */
2736 static int
2737 isp_pdb_sync(ispsoftc_t *isp, int chan)
2738 {
2739 	fcparam *fcp = FCPARAM(isp, chan);
2740 	fcportdb_t *lp;
2741 	uint16_t dbidx;
2742 
2743 	if (fcp->isp_loopstate == LOOP_READY) {
2744 		return (0);
2745 	}
2746 
2747 	/*
2748 	 * Make sure we're okay for doing this right now.
2749 	 */
2750 	if (fcp->isp_loopstate != LOOP_PDB_RCVD &&
2751 	    fcp->isp_loopstate != LOOP_FSCAN_DONE &&
2752 	    fcp->isp_loopstate != LOOP_LSCAN_DONE) {
2753 		isp_prt(isp, ISP_LOGWARN, "isp_pdb_sync: bad loopstate %d",
2754 		    fcp->isp_loopstate);
2755 		return (-1);
2756 	}
2757 
2758 	if (fcp->isp_topo == TOPO_FL_PORT ||
2759 	    fcp->isp_topo == TOPO_NL_PORT ||
2760 	    fcp->isp_topo == TOPO_N_PORT) {
2761 		if (fcp->isp_loopstate < LOOP_LSCAN_DONE) {
2762 			if (isp_scan_loop(isp, chan) != 0) {
2763 				isp_prt(isp, ISP_LOGWARN,
2764 				    "isp_pdb_sync: isp_scan_loop failed");
2765 				return (-1);
2766 			}
2767 		}
2768 	}
2769 
2770 	if (fcp->isp_topo == TOPO_F_PORT || fcp->isp_topo == TOPO_FL_PORT) {
2771 		if (fcp->isp_loopstate < LOOP_FSCAN_DONE) {
2772 			if (isp_scan_fabric(isp, chan) != 0) {
2773 				isp_prt(isp, ISP_LOGWARN,
2774 				    "isp_pdb_sync: isp_scan_fabric failed");
2775 				return (-1);
2776 			}
2777 		}
2778 	}
2779 
2780 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2781 	    "Chan %d Synchronizing PDBs", chan);
2782 
2783 	fcp->isp_loopstate = LOOP_SYNCING_PDB;
2784 
2785 	for (dbidx = 0; dbidx < MAX_FC_TARG; dbidx++) {
2786 		lp = &fcp->portdb[dbidx];
2787 
2788 		if (lp->state == FC_PORTDB_STATE_NIL || lp->target_mode) {
2789 			continue;
2790 		}
2791 
2792 		if (lp->state == FC_PORTDB_STATE_VALID) {
2793 			if (dbidx != FL_ID) {
2794 				isp_prt(isp,
2795 				    ISP_LOGERR, "portdb idx %d already valid",
2796 				    dbidx);
2797 			}
2798 			continue;
2799 		}
2800 
2801 		switch (lp->state) {
2802 		case FC_PORTDB_STATE_PROBATIONAL:
2803 		case FC_PORTDB_STATE_DEAD:
2804 			/*
2805 			 * It's up to the outer layers to clear isp_dev_map.
2806 			 */
2807 			lp->state = FC_PORTDB_STATE_NIL;
2808 			isp_async(isp, ISPASYNC_DEV_GONE, chan, lp);
2809 			if (lp->autologin == 0) {
2810 				(void) isp_plogx(isp, chan, lp->handle,
2811 				    lp->portid,
2812 				    PLOGX_FLG_CMD_LOGO |
2813 				    PLOGX_FLG_IMPLICIT |
2814 				    PLOGX_FLG_FREE_NPHDL, 0);
2815 			} else {
2816 				lp->autologin = 0;
2817 			}
2818 			lp->new_roles = 0;
2819 			lp->new_portid = 0;
2820 			/*
2821 			 * Note that we might come out of this with our state
2822 			 * set to FC_PORTDB_STATE_ZOMBIE.
2823 			 */
2824 			break;
2825 		case FC_PORTDB_STATE_NEW:
2826 			/*
2827 			 * It's up to the outer layers to assign a virtual
2828 			 * target id in isp_dev_map (if any).
2829 			 */
2830 			lp->portid = lp->new_portid;
2831 			lp->roles = lp->new_roles;
2832 			lp->state = FC_PORTDB_STATE_VALID;
2833 			isp_async(isp, ISPASYNC_DEV_ARRIVED, chan, lp);
2834 			lp->new_roles = 0;
2835 			lp->new_portid = 0;
2836 			lp->reserved = 0;
2837 			lp->new_reserved = 0;
2838 			break;
2839 		case FC_PORTDB_STATE_CHANGED:
2840 /*
2841  * XXXX FIX THIS
2842  */
2843 			lp->state = FC_PORTDB_STATE_VALID;
2844 			isp_async(isp, ISPASYNC_DEV_CHANGED, chan, lp);
2845 			lp->new_roles = 0;
2846 			lp->new_portid = 0;
2847 			lp->reserved = 0;
2848 			lp->new_reserved = 0;
2849 			break;
2850 		case FC_PORTDB_STATE_PENDING_VALID:
2851 			lp->portid = lp->new_portid;
2852 			lp->roles = lp->new_roles;
2853 			if (lp->dev_map_idx) {
2854 				int t = lp->dev_map_idx - 1;
2855 				fcp->isp_dev_map[t] = dbidx + 1;
2856 			}
2857 			lp->state = FC_PORTDB_STATE_VALID;
2858 			isp_async(isp, ISPASYNC_DEV_STAYED, chan, lp);
2859 			if (dbidx != FL_ID) {
2860 				lp->new_roles = 0;
2861 				lp->new_portid = 0;
2862 			}
2863 			lp->reserved = 0;
2864 			lp->new_reserved = 0;
2865 			break;
2866 		case FC_PORTDB_STATE_ZOMBIE:
2867 			break;
2868 		default:
2869 			isp_prt(isp, ISP_LOGWARN,
2870 			    "isp_scan_loop: state %d for idx %d",
2871 			    lp->state, dbidx);
2872 			isp_dump_portdb(isp, chan);
2873 		}
2874 	}
2875 
2876 	/*
2877 	 * If we get here, we've for sure seen not only a valid loop
2878 	 * but know what is or isn't on it, so mark this for usage
2879 	 * in isp_start.
2880 	 */
2881 	fcp->loop_seen_once = 1;
2882 	fcp->isp_loopstate = LOOP_READY;
2883 	return (0);
2884 }
2885 
2886 /*
2887  * Scan local loop for devices.
2888  */
2889 static int
2890 isp_scan_loop(ispsoftc_t *isp, int chan)
2891 {
2892 	fcportdb_t *lp, tmp;
2893 	fcparam *fcp = FCPARAM(isp, chan);
2894 	int i;
2895 	isp_pdb_t pdb;
2896 	uint16_t handle, lim = 0;
2897 
2898 	if (fcp->isp_fwstate < FW_READY ||
2899 	    fcp->isp_loopstate < LOOP_PDB_RCVD) {
2900 		return (-1);
2901 	}
2902 
2903 	if (fcp->isp_loopstate > LOOP_SCANNING_LOOP) {
2904 		return (0);
2905 	}
2906 
2907 	/*
2908 	 * Check our connection topology.
2909 	 *
2910 	 * If we're a public or private loop, we scan 0..125 as handle values.
2911 	 * The firmware has (typically) peformed a PLOGI for us. We skip this
2912 	 * step if we're a ISP_24XX in NP-IV mode.
2913 	 *
2914 	 * If we're a N-port connection, we treat this is a short loop (0..1).
2915 	 */
2916 	switch (fcp->isp_topo) {
2917 	case TOPO_NL_PORT:
2918 		lim = LOCAL_LOOP_LIM;
2919 		break;
2920 	case TOPO_FL_PORT:
2921 		if (IS_24XX(isp) && isp->isp_nchan > 1) {
2922 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2923 			    "Chan %d Skipping Local Loop Scan", chan);
2924 			fcp->isp_loopstate = LOOP_LSCAN_DONE;
2925 			return (0);
2926 		}
2927 		lim = LOCAL_LOOP_LIM;
2928 		break;
2929 	case TOPO_N_PORT:
2930 		lim = 2;
2931 		break;
2932 	default:
2933 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2934 		    "Chan %d no loop topology to scan", chan);
2935 		fcp->isp_loopstate = LOOP_LSCAN_DONE;
2936 		return (0);
2937 	}
2938 
2939 	fcp->isp_loopstate = LOOP_SCANNING_LOOP;
2940 
2941 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2942 	    "Chan %d FC scan loop 0..%d", chan, lim-1);
2943 
2944 
2945 	/*
2946 	 * Run through the list and get the port database info for each one.
2947 	 */
2948 	for (handle = 0; handle < lim; handle++) {
2949 		int r;
2950 		/*
2951 		 * Don't scan "special" ids.
2952 		 */
2953 		if (handle >= FL_ID && handle <= SNS_ID) {
2954 			continue;
2955 		}
2956 		if (ISP_CAP_2KLOGIN(isp)) {
2957 			if (handle >= NPH_RESERVED && handle <= NPH_FL_ID) {
2958 				continue;
2959 			}
2960 		}
2961 		/*
2962 		 * In older cards with older f/w GET_PORT_DATABASE has been
2963 		 * known to hang. This trick gets around that problem.
2964 		 */
2965 		if (IS_2100(isp) || IS_2200(isp)) {
2966 			uint64_t node_wwn = isp_get_wwn(isp, chan, handle, 1);
2967 			if (fcp->isp_loopstate < LOOP_SCANNING_LOOP) {
2968 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2969 				    "Chan %d FC scan loop DONE (bad)", chan);
2970 				return (-1);
2971 			}
2972 			if (node_wwn == INI_NONE) {
2973 				continue;
2974 			}
2975 		}
2976 
2977 		/*
2978 		 * Get the port database entity for this index.
2979 		 */
2980 		r = isp_getpdb(isp, chan, handle, &pdb, 1);
2981 		if (r != 0) {
2982 			isp_prt(isp, ISP_LOGDEBUG1,
2983 			    "Chan %d FC scan loop handle %d returned %x",
2984 			    chan, handle, r);
2985 			if (fcp->isp_loopstate < LOOP_SCANNING_LOOP) {
2986 				ISP_MARK_PORTDB(isp, chan, 1);
2987 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2988 				    "Chan %d FC scan loop DONE (bad)", chan);
2989 				return (-1);
2990 			}
2991 			continue;
2992 		}
2993 
2994 		if (fcp->isp_loopstate < LOOP_SCANNING_LOOP) {
2995 			ISP_MARK_PORTDB(isp, chan, 1);
2996 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
2997 			    "Chan %d FC scan loop DONE (bad)", chan);
2998 			return (-1);
2999 		}
3000 
3001 		/*
3002 		 * On *very* old 2100 firmware we would end up sometimes
3003 		 * with the firmware returning the port database entry
3004 		 * for something else. We used to restart this, but
3005 		 * now we just punt.
3006 		 */
3007 		if (IS_2100(isp) && pdb.handle != handle) {
3008 			isp_prt(isp, ISP_LOGWARN,
3009 			    "Chan %d cannot synchronize port database", chan);
3010 			ISP_MARK_PORTDB(isp, chan, 1);
3011 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3012 			    "Chan %d FC scan loop DONE (bad)", chan);
3013 			return (-1);
3014 		}
3015 
3016 		/*
3017 		 * Save the pertinent info locally.
3018 		 */
3019 		MAKE_WWN_FROM_NODE_NAME(tmp.node_wwn, pdb.nodename);
3020 		MAKE_WWN_FROM_NODE_NAME(tmp.port_wwn, pdb.portname);
3021 		tmp.roles = (pdb.s3_role & SVC3_ROLE_MASK) >> SVC3_ROLE_SHIFT;
3022 		tmp.portid = pdb.portid;
3023 		tmp.handle = pdb.handle;
3024 
3025 		/*
3026 		 * Check to make sure it's still a valid entry. The 24XX seems
3027 		 * to return a portid but not a WWPN/WWNN or role for devices
3028 		 * which shift on a loop.
3029 		 */
3030 		if (tmp.node_wwn == 0 || tmp.port_wwn == 0 || tmp.portid == 0) {
3031 			int a, b, c;
3032 			a = (tmp.node_wwn == 0);
3033 			b = (tmp.port_wwn == 0);
3034 			c = (tmp.portid == 0);
3035 			if (a == 0 && b == 0) {
3036 				tmp.node_wwn =
3037 				    isp_get_wwn(isp, chan, handle, 1);
3038 				tmp.port_wwn =
3039 				    isp_get_wwn(isp, chan, handle, 0);
3040 				if (tmp.node_wwn && tmp.port_wwn) {
3041 					isp_prt(isp, ISP_LOGINFO, "DODGED!");
3042 					goto cont;
3043 				}
3044 			}
3045 			isp_prt(isp, ISP_LOGWARN,
3046 			    "Chan %d bad pdb (%1d%1d%1d) @ handle 0x%x", chan,
3047 			    a, b, c, handle);
3048 			isp_dump_portdb(isp, chan);
3049 			continue;
3050 		}
3051   cont:
3052 
3053 		/*
3054 		 * Now search the entire port database
3055 		 * for the same Port and Node WWN.
3056 		 */
3057 		for (i = 0; i < MAX_FC_TARG; i++) {
3058 			lp = &fcp->portdb[i];
3059 
3060 			if (lp->state == FC_PORTDB_STATE_NIL ||
3061 			    lp->target_mode) {
3062 				continue;
3063 			}
3064 			if (lp->node_wwn != tmp.node_wwn) {
3065 				continue;
3066 			}
3067 			if (lp->port_wwn != tmp.port_wwn) {
3068 				continue;
3069 			}
3070 
3071 			/*
3072 			 * Okay- we've found a non-nil entry that matches.
3073 			 * Check to make sure it's probational or a zombie.
3074 			 */
3075 			if (lp->state != FC_PORTDB_STATE_PROBATIONAL &&
3076 			    lp->state != FC_PORTDB_STATE_ZOMBIE) {
3077 				isp_prt(isp, ISP_LOGERR,
3078 				    "Chan %d [%d] not probational/zombie (0x%x)",
3079 				    chan, i, lp->state);
3080 				isp_dump_portdb(isp, chan);
3081 				ISP_MARK_PORTDB(isp, chan, 1);
3082 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3083 				    "Chan %d FC scan loop DONE (bad)", chan);
3084 				return (-1);
3085 			}
3086 
3087 			/*
3088 			 * Mark the device as something the f/w logs into
3089 			 * automatically.
3090 			 */
3091 			lp->autologin = 1;
3092 
3093 			/*
3094 			 * Check to make see if really still the same
3095 			 * device. If it is, we mark it pending valid.
3096 			 */
3097 			if (lp->portid == tmp.portid &&
3098 			    lp->handle == tmp.handle &&
3099 			    lp->roles == tmp.roles) {
3100 				lp->new_portid = tmp.portid;
3101 				lp->new_roles = tmp.roles;
3102 				lp->state = FC_PORTDB_STATE_PENDING_VALID;
3103 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3104 				    "Chan %d Loop Port 0x%06x@0x%04x Pending "
3105 				    "Valid", chan, tmp.portid, tmp.handle);
3106 				break;
3107 			}
3108 
3109 			/*
3110 			 * We can wipe out the old handle value
3111 			 * here because it's no longer valid.
3112 			 */
3113 			lp->handle = tmp.handle;
3114 
3115 			/*
3116 			 * Claim that this has changed and let somebody else
3117 			 * decide what to do.
3118 			 */
3119 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3120 			    "Chan %d Loop Port 0x%06x@0x%04x changed",
3121 			    chan, tmp.portid, tmp.handle);
3122 			lp->state = FC_PORTDB_STATE_CHANGED;
3123 			lp->new_portid = tmp.portid;
3124 			lp->new_roles = tmp.roles;
3125 			break;
3126 		}
3127 
3128 		/*
3129 		 * Did we find and update an old entry?
3130 		 */
3131 		if (i < MAX_FC_TARG) {
3132 			continue;
3133 		}
3134 
3135 		/*
3136 		 * Ah. A new device entry. Find an empty slot
3137 		 * for it and save info for later disposition.
3138 		 */
3139 		for (i = 0; i < MAX_FC_TARG; i++) {
3140 			if (fcp->portdb[i].target_mode) {
3141 				continue;
3142 			}
3143 			if (fcp->portdb[i].state == FC_PORTDB_STATE_NIL) {
3144 				break;
3145 			}
3146 		}
3147 		if (i == MAX_FC_TARG) {
3148 			isp_prt(isp, ISP_LOGERR,
3149 			    "Chan %d out of portdb entries", chan);
3150 			continue;
3151 		}
3152 		lp = &fcp->portdb[i];
3153 
3154 		ISP_MEMZERO(lp, sizeof (fcportdb_t));
3155 		lp->autologin = 1;
3156 		lp->state = FC_PORTDB_STATE_NEW;
3157 		lp->new_portid = tmp.portid;
3158 		lp->new_roles = tmp.roles;
3159 		lp->handle = tmp.handle;
3160 		lp->port_wwn = tmp.port_wwn;
3161 		lp->node_wwn = tmp.node_wwn;
3162 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3163 		    "Chan %d Loop Port 0x%06x@0x%04x is New Entry",
3164 		    chan, tmp.portid, tmp.handle);
3165 	}
3166 	fcp->isp_loopstate = LOOP_LSCAN_DONE;
3167 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3168 	    "Chan %d FC scan loop DONE", chan);
3169 	return (0);
3170 }
3171 
3172 /*
3173  * Scan the fabric for devices and add them to our port database.
3174  *
3175  * Use the GID_FT command to get all Port IDs for FC4 SCSI devices it knows.
3176  *
3177  * For 2100-23XX cards, we can use the SNS mailbox command to pass simple
3178  * name server commands to the switch management server via the QLogic f/w.
3179  *
3180  * For the 24XX card, we have to use CT-Pass through run via the Execute IOCB
3181  * mailbox command.
3182  *
3183  * The net result is to leave the list of Port IDs setting untranslated in
3184  * offset IGPOFF of the FC scratch area, whereupon we'll canonicalize it to
3185  * host order at OGPOFF.
3186  */
3187 
3188 /*
3189  * Take less than half of our scratch area to store Port IDs
3190  */
3191 #define	GIDLEN	((ISP_FC_SCRLEN >> 1) - 16 - SNS_GID_FT_REQ_SIZE)
3192 #define	NGENT	((GIDLEN - 16) >> 2)
3193 
3194 #define	IGPOFF	(2 * QENTRY_LEN)
3195 #define	OGPOFF	(ISP_FC_SCRLEN >> 1)
3196 #define	ZTXOFF	(ISP_FC_SCRLEN - (1 * QENTRY_LEN))
3197 #define	CTXOFF	(ISP_FC_SCRLEN - (2 * QENTRY_LEN))
3198 #define	XTXOFF	(ISP_FC_SCRLEN - (3 * QENTRY_LEN))
3199 
3200 static int
3201 isp_gid_ft_sns(ispsoftc_t *isp, int chan)
3202 {
3203 	union {
3204 		sns_gid_ft_req_t _x;
3205 		uint8_t _y[SNS_GID_FT_REQ_SIZE];
3206 	} un;
3207 	fcparam *fcp = FCPARAM(isp, chan);
3208 	sns_gid_ft_req_t *rq = &un._x;
3209 	mbreg_t mbs;
3210 
3211 	isp_prt(isp, ISP_LOGDEBUG0,
3212 	    "Chan %d scanning fabric (GID_FT) via SNS", chan);
3213 
3214 	ISP_MEMZERO(rq, SNS_GID_FT_REQ_SIZE);
3215 	rq->snscb_rblen = GIDLEN >> 1;
3216 	rq->snscb_addr[RQRSP_ADDR0015] = DMA_WD0(fcp->isp_scdma + IGPOFF);
3217 	rq->snscb_addr[RQRSP_ADDR1631] = DMA_WD1(fcp->isp_scdma + IGPOFF);
3218 	rq->snscb_addr[RQRSP_ADDR3247] = DMA_WD2(fcp->isp_scdma + IGPOFF);
3219 	rq->snscb_addr[RQRSP_ADDR4863] = DMA_WD3(fcp->isp_scdma + IGPOFF);
3220 	rq->snscb_sblen = 6;
3221 	rq->snscb_cmd = SNS_GID_FT;
3222 	rq->snscb_mword_div_2 = NGENT;
3223 	rq->snscb_fc4_type = FC4_SCSI;
3224 
3225 	isp_put_gid_ft_request(isp, rq, fcp->isp_scratch);
3226 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, SNS_GID_FT_REQ_SIZE, chan);
3227 
3228 	MBSINIT(&mbs, MBOX_SEND_SNS, MBLOGALL, 10000000);
3229 	mbs.param[0] = MBOX_SEND_SNS;
3230 	mbs.param[1] = SNS_GID_FT_REQ_SIZE >> 1;
3231 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
3232 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
3233 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
3234 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
3235 	isp_mboxcmd(isp, &mbs);
3236 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
3237 		if (mbs.param[0] == MBOX_INVALID_COMMAND) {
3238 			return (1);
3239 		} else {
3240 			return (-1);
3241 		}
3242 	}
3243 	return (0);
3244 }
3245 
3246 static int
3247 isp_gid_ft_ct_passthru(ispsoftc_t *isp, int chan)
3248 {
3249 	mbreg_t mbs;
3250 	fcparam *fcp = FCPARAM(isp, chan);
3251 	union {
3252 		isp_ct_pt_t plocal;
3253 		ct_hdr_t clocal;
3254 		uint8_t q[QENTRY_LEN];
3255 	} un;
3256 	isp_ct_pt_t *pt;
3257 	ct_hdr_t *ct;
3258 	uint32_t *rp;
3259 	uint8_t *scp = fcp->isp_scratch;
3260 
3261 	isp_prt(isp, ISP_LOGDEBUG0,
3262 	    "Chan %d scanning fabric (GID_FT) via CT", chan);
3263 
3264 	if (!IS_24XX(isp)) {
3265 		return (1);
3266 	}
3267 
3268 	/*
3269 	 * Build a Passthrough IOCB in memory.
3270 	 */
3271 	pt = &un.plocal;
3272 	ISP_MEMZERO(un.q, QENTRY_LEN);
3273 	pt->ctp_header.rqs_entry_count = 1;
3274 	pt->ctp_header.rqs_entry_type = RQSTYPE_CT_PASSTHRU;
3275 	pt->ctp_handle = 0xffffffff;
3276 	pt->ctp_nphdl = fcp->isp_sns_hdl;
3277 	pt->ctp_cmd_cnt = 1;
3278 	pt->ctp_vpidx = ISP_GET_VPIDX(isp, chan);
3279 	pt->ctp_time = 30;
3280 	pt->ctp_rsp_cnt = 1;
3281 	pt->ctp_rsp_bcnt = GIDLEN;
3282 	pt->ctp_cmd_bcnt = sizeof (*ct) + sizeof (uint32_t);
3283 	pt->ctp_dataseg[0].ds_base = DMA_LO32(fcp->isp_scdma+XTXOFF);
3284 	pt->ctp_dataseg[0].ds_basehi = DMA_HI32(fcp->isp_scdma+XTXOFF);
3285 	pt->ctp_dataseg[0].ds_count = sizeof (*ct) + sizeof (uint32_t);
3286 	pt->ctp_dataseg[1].ds_base = DMA_LO32(fcp->isp_scdma+IGPOFF);
3287 	pt->ctp_dataseg[1].ds_basehi = DMA_HI32(fcp->isp_scdma+IGPOFF);
3288 	pt->ctp_dataseg[1].ds_count = GIDLEN;
3289 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
3290 		isp_print_bytes(isp, "ct IOCB", QENTRY_LEN, pt);
3291 	}
3292 	isp_put_ct_pt(isp, pt, (isp_ct_pt_t *) &scp[CTXOFF]);
3293 
3294 	/*
3295 	 * Build the CT header and command in memory.
3296 	 *
3297 	 * Note that the CT header has to end up as Big Endian format in memory.
3298 	 */
3299 	ct = &un.clocal;
3300 	ISP_MEMZERO(ct, sizeof (*ct));
3301 	ct->ct_revision = CT_REVISION;
3302 	ct->ct_fcs_type = CT_FC_TYPE_FC;
3303 	ct->ct_fcs_subtype = CT_FC_SUBTYPE_NS;
3304 	ct->ct_cmd_resp = SNS_GID_FT;
3305 	ct->ct_bcnt_resid = (GIDLEN - 16) >> 2;
3306 
3307 	isp_put_ct_hdr(isp, ct, (ct_hdr_t *) &scp[XTXOFF]);
3308 	rp = (uint32_t *) &scp[XTXOFF+sizeof (*ct)];
3309 	ISP_IOZPUT_32(isp, FC4_SCSI, rp);
3310 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
3311 		isp_print_bytes(isp, "CT HDR + payload after put",
3312 		    sizeof (*ct) + sizeof (uint32_t), &scp[XTXOFF]);
3313 	}
3314 	ISP_MEMZERO(&scp[ZTXOFF], QENTRY_LEN);
3315 	MBSINIT(&mbs, MBOX_EXEC_COMMAND_IOCB_A64, MBLOGALL, 500000);
3316 	mbs.param[1] = QENTRY_LEN;
3317 	mbs.param[2] = DMA_WD1(fcp->isp_scdma + CTXOFF);
3318 	mbs.param[3] = DMA_WD0(fcp->isp_scdma + CTXOFF);
3319 	mbs.param[6] = DMA_WD3(fcp->isp_scdma + CTXOFF);
3320 	mbs.param[7] = DMA_WD2(fcp->isp_scdma + CTXOFF);
3321 	MEMORYBARRIER(isp, SYNC_SFORDEV, XTXOFF, 2 * QENTRY_LEN, chan);
3322 	isp_mboxcmd(isp, &mbs);
3323 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
3324 		return (-1);
3325 	}
3326 	MEMORYBARRIER(isp, SYNC_SFORCPU, ZTXOFF, QENTRY_LEN, chan);
3327 	pt = &un.plocal;
3328 	isp_get_ct_pt(isp, (isp_ct_pt_t *) &scp[ZTXOFF], pt);
3329 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
3330 		isp_print_bytes(isp, "IOCB response", QENTRY_LEN, pt);
3331 	}
3332 
3333 	if (pt->ctp_status && pt->ctp_status != RQCS_DATA_UNDERRUN) {
3334 		isp_prt(isp, ISP_LOGWARN,
3335 		    "Chan %d ISP GID FT CT Passthrough returned 0x%x",
3336 		    chan, pt->ctp_status);
3337 		return (-1);
3338 	}
3339 	MEMORYBARRIER(isp, SYNC_SFORCPU, IGPOFF, GIDLEN + 16, chan);
3340 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
3341 		isp_print_bytes(isp, "CT response", GIDLEN+16, &scp[IGPOFF]);
3342 	}
3343 	return (0);
3344 }
3345 
3346 static int
3347 isp_scan_fabric(ispsoftc_t *isp, int chan)
3348 {
3349 	fcparam *fcp = FCPARAM(isp, chan);
3350 	uint32_t portid;
3351 	uint16_t handle, oldhandle, loopid;
3352 	isp_pdb_t pdb;
3353 	int portidx, portlim, r;
3354 	sns_gid_ft_rsp_t *rs0, *rs1;
3355 
3356 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3357 	    "Chan %d FC Scan Fabric", chan);
3358 	if (fcp->isp_fwstate != FW_READY ||
3359 	    fcp->isp_loopstate < LOOP_LSCAN_DONE) {
3360 		return (-1);
3361 	}
3362 	if (fcp->isp_loopstate > LOOP_SCANNING_FABRIC) {
3363 		return (0);
3364 	}
3365 	if (fcp->isp_topo != TOPO_FL_PORT && fcp->isp_topo != TOPO_F_PORT) {
3366 		fcp->isp_loopstate = LOOP_FSCAN_DONE;
3367 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3368 		    "Chan %d FC Scan Fabric Done (no fabric)", chan);
3369 		return (0);
3370 	}
3371 
3372 	fcp->isp_loopstate = LOOP_SCANNING_FABRIC;
3373 	if (FC_SCRATCH_ACQUIRE(isp, chan)) {
3374 		isp_prt(isp, ISP_LOGERR, sacq);
3375 		ISP_MARK_PORTDB(isp, chan, 1);
3376 		return (-1);
3377 	}
3378 	if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
3379 		FC_SCRATCH_RELEASE(isp, chan);
3380 		ISP_MARK_PORTDB(isp, chan, 1);
3381 		return (-1);
3382 	}
3383 
3384 	/*
3385 	 * Make sure we still are logged into the fabric controller.
3386 	 */
3387 	if (IS_24XX(isp)) {	/* XXX SHOULDN'T THIS BE TRUE FOR 2K F/W? XXX */
3388 		loopid = NPH_FL_ID;
3389 	} else {
3390 		loopid = FL_ID;
3391 	}
3392 	r = isp_getpdb(isp, chan, loopid, &pdb, 0);
3393 	if (r == MBOX_NOT_LOGGED_IN) {
3394 		isp_dump_chip_portdb(isp, chan, 0);
3395 	}
3396 	if (r) {
3397 		fcp->isp_loopstate = LOOP_PDB_RCVD;
3398 		FC_SCRATCH_RELEASE(isp, chan);
3399 		ISP_MARK_PORTDB(isp, chan, 1);
3400 		return (-1);
3401 	}
3402 
3403 	if (IS_24XX(isp)) {
3404 		r = isp_gid_ft_ct_passthru(isp, chan);
3405 	} else {
3406 		r = isp_gid_ft_sns(isp, chan);
3407 	}
3408 
3409 	if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
3410 		FC_SCRATCH_RELEASE(isp, chan);
3411 		ISP_MARK_PORTDB(isp, chan, 1);
3412 		return (-1);
3413 	}
3414 
3415 	if (r > 0) {
3416 		fcp->isp_loopstate = LOOP_FSCAN_DONE;
3417 		FC_SCRATCH_RELEASE(isp, chan);
3418 		return (0);
3419 	} else if (r < 0) {
3420 		fcp->isp_loopstate = LOOP_PDB_RCVD;	/* try again */
3421 		FC_SCRATCH_RELEASE(isp, chan);
3422 		return (0);
3423 	}
3424 
3425 	MEMORYBARRIER(isp, SYNC_SFORCPU, IGPOFF, GIDLEN, chan);
3426 	rs0 = (sns_gid_ft_rsp_t *) ((uint8_t *)fcp->isp_scratch+IGPOFF);
3427 	rs1 = (sns_gid_ft_rsp_t *) ((uint8_t *)fcp->isp_scratch+OGPOFF);
3428 	isp_get_gid_ft_response(isp, rs0, rs1, NGENT);
3429 	if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
3430 		FC_SCRATCH_RELEASE(isp, chan);
3431 		ISP_MARK_PORTDB(isp, chan, 1);
3432 		return (-1);
3433 	}
3434 	if (rs1->snscb_cthdr.ct_cmd_resp != LS_ACC) {
3435 		int level;
3436 		if (rs1->snscb_cthdr.ct_reason == 9 &&
3437 		    rs1->snscb_cthdr.ct_explanation == 7) {
3438 			level = ISP_LOGSANCFG|ISP_LOGDEBUG0;
3439 		} else {
3440 			level = ISP_LOGWARN;
3441 		}
3442 		isp_prt(isp, level, "Chan %d Fabric Nameserver rejected GID_FT"
3443 		    " (Reason=0x%x Expl=0x%x)", chan,
3444 		    rs1->snscb_cthdr.ct_reason,
3445 		    rs1->snscb_cthdr.ct_explanation);
3446 		FC_SCRATCH_RELEASE(isp, chan);
3447 		fcp->isp_loopstate = LOOP_FSCAN_DONE;
3448 		return (0);
3449 	}
3450 
3451 
3452 	/*
3453 	 * If we get this far, we certainly still have the fabric controller.
3454 	 */
3455 	fcp->portdb[FL_ID].state = FC_PORTDB_STATE_PENDING_VALID;
3456 
3457 	/*
3458 	 * Prime the handle we will start using.
3459 	 */
3460 	oldhandle = FCPARAM(isp, 0)->isp_lasthdl;
3461 
3462 	/*
3463 	 * Go through the list and remove duplicate port ids.
3464 	 */
3465 
3466 	portlim = 0;
3467 	portidx = 0;
3468 	for (portidx = 0; portidx < NGENT-1; portidx++) {
3469 		if (rs1->snscb_ports[portidx].control & 0x80) {
3470 			break;
3471 		}
3472 	}
3473 
3474 	/*
3475 	 * If we're not at the last entry, our list wasn't big enough.
3476 	 */
3477 	if ((rs1->snscb_ports[portidx].control & 0x80) == 0) {
3478 		isp_prt(isp, ISP_LOGWARN,
3479 		    "fabric too big for scratch area: increase ISP_FC_SCRLEN");
3480 	}
3481 	portlim = portidx + 1;
3482 	isp_prt(isp, ISP_LOGSANCFG,
3483 	    "Chan %d got %d ports back from name server", chan, portlim);
3484 
3485 	for (portidx = 0; portidx < portlim; portidx++) {
3486 		int npidx;
3487 
3488 		portid =
3489 		    ((rs1->snscb_ports[portidx].portid[0]) << 16) |
3490 		    ((rs1->snscb_ports[portidx].portid[1]) << 8) |
3491 		    ((rs1->snscb_ports[portidx].portid[2]));
3492 
3493 		for (npidx = portidx + 1; npidx < portlim; npidx++) {
3494 			uint32_t new_portid =
3495 			    ((rs1->snscb_ports[npidx].portid[0]) << 16) |
3496 			    ((rs1->snscb_ports[npidx].portid[1]) << 8) |
3497 			    ((rs1->snscb_ports[npidx].portid[2]));
3498 			if (new_portid == portid) {
3499 				break;
3500 			}
3501 		}
3502 
3503 		if (npidx < portlim) {
3504 			rs1->snscb_ports[npidx].portid[0] = 0;
3505 			rs1->snscb_ports[npidx].portid[1] = 0;
3506 			rs1->snscb_ports[npidx].portid[2] = 0;
3507 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3508 			    "Chan %d removing duplicate PortID 0x%06x"
3509 			    " entry from list", chan, portid);
3510 		}
3511 	}
3512 
3513 	/*
3514 	 * We now have a list of Port IDs for all FC4 SCSI devices
3515 	 * that the Fabric Name server knows about.
3516 	 *
3517 	 * For each entry on this list go through our port database looking
3518 	 * for probational entries- if we find one, then an old entry is
3519 	 * maybe still this one. We get some information to find out.
3520 	 *
3521 	 * Otherwise, it's a new fabric device, and we log into it
3522 	 * (unconditionally). After searching the entire database
3523 	 * again to make sure that we never ever ever ever have more
3524 	 * than one entry that has the same PortID or the same
3525 	 * WWNN/WWPN duple, we enter the device into our database.
3526 	 */
3527 
3528 	for (portidx = 0; portidx < portlim; portidx++) {
3529 		fcportdb_t *lp;
3530 		uint64_t wwnn, wwpn;
3531 		int dbidx, nr;
3532 
3533 		portid =
3534 		    ((rs1->snscb_ports[portidx].portid[0]) << 16) |
3535 		    ((rs1->snscb_ports[portidx].portid[1]) << 8) |
3536 		    ((rs1->snscb_ports[portidx].portid[2]));
3537 
3538 		if (portid == 0) {
3539 			isp_prt(isp, ISP_LOGSANCFG,
3540 			    "Chan %d skipping null PortID at idx %d",
3541 			    chan, portidx);
3542 			continue;
3543 		}
3544 
3545 		/*
3546 		 * Skip ourselves here and on other channels. If we're
3547 		 * multi-id, we can't check the portids in other FCPARAM
3548 		 * arenas because the resolutions here aren't synchronized.
3549 		 * The best way to do this is to exclude looking at portids
3550 		 * that have the same domain and area code as our own
3551 		 * portid.
3552 		 */
3553 		if (ISP_CAP_MULTI_ID(isp)) {
3554 			if ((portid >> 8) == (fcp->isp_portid >> 8)) {
3555 				isp_prt(isp, ISP_LOGSANCFG,
3556 				    "Chan %d skip PortID 0x%06x",
3557 				    chan, portid);
3558 				continue;
3559 			}
3560 		} else if (portid == fcp->isp_portid) {
3561 			isp_prt(isp, ISP_LOGSANCFG,
3562 			    "Chan %d skip ourselves on @ PortID 0x%06x",
3563 			    chan, portid);
3564 			continue;
3565 		}
3566 
3567 		isp_prt(isp, ISP_LOGSANCFG,
3568 		    "Chan %d Checking Fabric Port 0x%06x", chan, portid);
3569 
3570 		/*
3571 		 * We now search our Port Database for any
3572 		 * probational entries with this PortID. We don't
3573 		 * look for zombies here- only probational
3574 		 * entries (we've already logged out of zombies).
3575 		 */
3576 		for (dbidx = 0; dbidx < MAX_FC_TARG; dbidx++) {
3577 			lp = &fcp->portdb[dbidx];
3578 
3579 			if (lp->state != FC_PORTDB_STATE_PROBATIONAL ||
3580 			    lp->target_mode) {
3581 				continue;
3582 			}
3583 			if (lp->portid == portid) {
3584 				break;
3585 			}
3586 		}
3587 
3588 		/*
3589 		 * We found a probational entry with this Port ID.
3590 		 */
3591 		if (dbidx < MAX_FC_TARG) {
3592 			int handle_changed = 0;
3593 
3594 			lp = &fcp->portdb[dbidx];
3595 
3596 			/*
3597 			 * See if we're still logged into it.
3598 			 *
3599 			 * If we aren't, mark it as a dead device and
3600 			 * leave the new portid in the database entry
3601 			 * for somebody further along to decide what to
3602 			 * do (policy choice).
3603 			 *
3604 			 * If we are, check to see if it's the same
3605 			 * device still (it should be). If for some
3606 			 * reason it isn't, mark it as a changed device
3607 			 * and leave the new portid and role in the
3608 			 * database entry for somebody further along to
3609 			 * decide what to do (policy choice).
3610 			 *
3611 			 */
3612 
3613 			r = isp_getpdb(isp, chan, lp->handle, &pdb, 0);
3614 			if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
3615 				FC_SCRATCH_RELEASE(isp, chan);
3616 				ISP_MARK_PORTDB(isp, chan, 1);
3617 				return (-1);
3618 			}
3619 			if (r != 0) {
3620 				lp->new_portid = portid;
3621 				lp->state = FC_PORTDB_STATE_DEAD;
3622 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3623 				    "Chan %d Fabric Port 0x%06x is dead",
3624 				    chan, portid);
3625 				continue;
3626 			}
3627 
3628 
3629 			/*
3630 			 * Check to make sure that handle, portid, WWPN and
3631 			 * WWNN agree. If they don't, then the association
3632 			 * between this PortID and the stated handle has been
3633 			 * broken by the firmware.
3634 			 */
3635 			MAKE_WWN_FROM_NODE_NAME(wwnn, pdb.nodename);
3636 			MAKE_WWN_FROM_NODE_NAME(wwpn, pdb.portname);
3637 			if (pdb.handle != lp->handle ||
3638 			    pdb.portid != portid ||
3639 			    wwpn != lp->port_wwn ||
3640 			    wwnn != lp->node_wwn) {
3641 				isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3642 				    fconf, chan, dbidx, pdb.handle, pdb.portid,
3643 				    (uint32_t) (wwnn >> 32), (uint32_t) wwnn,
3644 				    (uint32_t) (wwpn >> 32), (uint32_t) wwpn,
3645 				    lp->handle, portid,
3646 				    (uint32_t) (lp->node_wwn >> 32),
3647 				    (uint32_t) lp->node_wwn,
3648 				    (uint32_t) (lp->port_wwn >> 32),
3649 				    (uint32_t) lp->port_wwn);
3650 				/*
3651 				 * Try to re-login to this device using a
3652 				 * new handle. If that fails, mark it dead.
3653 				 *
3654 				 * isp_login_device will check for handle and
3655 				 * portid consistency after re-login.
3656 				 *
3657 				 */
3658 				if (isp_login_device(isp, chan, portid, &pdb,
3659 				    &oldhandle)) {
3660 					lp->new_portid = portid;
3661 					lp->state = FC_PORTDB_STATE_DEAD;
3662 					if (fcp->isp_loopstate !=
3663 					    LOOP_SCANNING_FABRIC) {
3664 						FC_SCRATCH_RELEASE(isp, chan);
3665 						ISP_MARK_PORTDB(isp, chan, 1);
3666 						return (-1);
3667 					}
3668 					continue;
3669 				}
3670 				if (fcp->isp_loopstate !=
3671 				    LOOP_SCANNING_FABRIC) {
3672 					FC_SCRATCH_RELEASE(isp, chan);
3673 					ISP_MARK_PORTDB(isp, chan, 1);
3674 					return (-1);
3675 				}
3676 				FCPARAM(isp, 0)->isp_lasthdl = oldhandle;
3677 				MAKE_WWN_FROM_NODE_NAME(wwnn, pdb.nodename);
3678 				MAKE_WWN_FROM_NODE_NAME(wwpn, pdb.portname);
3679 				if (wwpn != lp->port_wwn ||
3680 				    wwnn != lp->node_wwn) {
3681 					isp_prt(isp, ISP_LOGWARN, "changed WWN"
3682 					    " after relogin");
3683 					lp->new_portid = portid;
3684 					lp->state = FC_PORTDB_STATE_DEAD;
3685 					continue;
3686 				}
3687 
3688 				lp->handle = pdb.handle;
3689 				handle_changed++;
3690 			}
3691 
3692 			nr = (pdb.s3_role & SVC3_ROLE_MASK) >> SVC3_ROLE_SHIFT;
3693 
3694 			/*
3695 			 * Check to see whether the portid and roles have
3696 			 * stayed the same. If they have stayed the same,
3697 			 * we believe that this is the same device and it
3698 			 * hasn't become disconnected and reconnected, so
3699 			 * mark it as pending valid.
3700 			 *
3701 			 * If they aren't the same, mark the device as a
3702 			 * changed device and save the new port id and role
3703 			 * and let somebody else decide.
3704 			 */
3705 
3706 			lp->new_portid = portid;
3707 			lp->new_roles = nr;
3708 			if (pdb.portid != lp->portid || nr != lp->roles ||
3709 			    handle_changed) {
3710 				isp_prt(isp, ISP_LOGSANCFG,
3711 				    "Chan %d Fabric Port 0x%06x changed",
3712 				    chan, portid);
3713 				lp->state = FC_PORTDB_STATE_CHANGED;
3714 			} else {
3715 				isp_prt(isp, ISP_LOGSANCFG,
3716 				    "Chan %d Fabric Port 0x%06x "
3717 				    "Now Pending Valid", chan, portid);
3718 				lp->state = FC_PORTDB_STATE_PENDING_VALID;
3719 			}
3720 			continue;
3721 		}
3722 
3723 		/*
3724 		 * Ah- a new entry. Search the database again for all non-NIL
3725 		 * entries to make sure we never ever make a new database entry
3726 		 * with the same port id. While we're at it, mark where the
3727 		 * last free entry was.
3728 		 */
3729 
3730 		dbidx = MAX_FC_TARG;
3731 		for (lp = fcp->portdb; lp < &fcp->portdb[MAX_FC_TARG]; lp++) {
3732 			if (lp >= &fcp->portdb[FL_ID] &&
3733 			    lp <= &fcp->portdb[SNS_ID]) {
3734 				continue;
3735 			}
3736 			/*
3737 			 * Skip any target mode entries.
3738 			 */
3739 			if (lp->target_mode) {
3740 				continue;
3741 			}
3742 			if (lp->state == FC_PORTDB_STATE_NIL) {
3743 				if (dbidx == MAX_FC_TARG) {
3744 					dbidx = lp - fcp->portdb;
3745 				}
3746 				continue;
3747 			}
3748 			if (lp->state == FC_PORTDB_STATE_ZOMBIE) {
3749 				continue;
3750 			}
3751 			if (lp->portid == portid) {
3752 				break;
3753 			}
3754 		}
3755 
3756 		if (lp < &fcp->portdb[MAX_FC_TARG]) {
3757 			isp_prt(isp, ISP_LOGWARN, "Chan %d PortID 0x%06x "
3758 			    "already at %d handle %d state %d",
3759 			    chan, portid, dbidx, lp->handle, lp->state);
3760 			continue;
3761 		}
3762 
3763 		/*
3764 		 * We should have the index of the first free entry seen.
3765 		 */
3766 		if (dbidx == MAX_FC_TARG) {
3767 			isp_prt(isp, ISP_LOGERR,
3768 			    "port database too small to login PortID 0x%06x"
3769 			    "- increase MAX_FC_TARG", portid);
3770 			continue;
3771 		}
3772 
3773 		/*
3774 		 * Otherwise, point to our new home.
3775 		 */
3776 		lp = &fcp->portdb[dbidx];
3777 
3778 		/*
3779 		 * Try to see if we are logged into this device,
3780 		 * and maybe log into it.
3781 		 *
3782 		 * isp_login_device will check for handle and
3783 		 * portid consistency after login.
3784 		 */
3785 		if (isp_login_device(isp, chan, portid, &pdb, &oldhandle)) {
3786 			if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
3787 				FC_SCRATCH_RELEASE(isp, chan);
3788 				ISP_MARK_PORTDB(isp, chan, 1);
3789 				return (-1);
3790 			}
3791 			continue;
3792 		}
3793 		if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
3794 			FC_SCRATCH_RELEASE(isp, chan);
3795 			ISP_MARK_PORTDB(isp, chan, 1);
3796 			return (-1);
3797 		}
3798 		FCPARAM(isp, 0)->isp_lasthdl = oldhandle;
3799 
3800 		handle = pdb.handle;
3801 		MAKE_WWN_FROM_NODE_NAME(wwnn, pdb.nodename);
3802 		MAKE_WWN_FROM_NODE_NAME(wwpn, pdb.portname);
3803 		nr = (pdb.s3_role & SVC3_ROLE_MASK) >> SVC3_ROLE_SHIFT;
3804 
3805 		/*
3806 		 * And go through the database *one* more time to make sure
3807 		 * that we do not make more than one entry that has the same
3808 		 * WWNN/WWPN duple
3809 		 */
3810 		for (dbidx = 0; dbidx < MAX_FC_TARG; dbidx++) {
3811 			if (dbidx >= FL_ID && dbidx <= SNS_ID) {
3812 				continue;
3813 			}
3814 			if (fcp->portdb[dbidx].target_mode) {
3815 				continue;
3816 			}
3817 			if (fcp->portdb[dbidx].node_wwn == wwnn &&
3818 			    fcp->portdb[dbidx].port_wwn == wwpn) {
3819 				break;
3820 			}
3821 		}
3822 
3823 		if (dbidx == MAX_FC_TARG) {
3824 			ISP_MEMZERO(lp, sizeof (fcportdb_t));
3825 			lp->handle = handle;
3826 			lp->node_wwn = wwnn;
3827 			lp->port_wwn = wwpn;
3828 			lp->new_portid = portid;
3829 			lp->new_roles = nr;
3830 			lp->state = FC_PORTDB_STATE_NEW;
3831 			isp_prt(isp, ISP_LOGSANCFG,
3832 			    "Chan %d Fabric Port 0x%06x is a New Entry",
3833 			    chan, portid);
3834 			continue;
3835 		}
3836 
3837 		if (fcp->portdb[dbidx].state != FC_PORTDB_STATE_ZOMBIE) {
3838 			isp_prt(isp, ISP_LOGWARN,
3839 			    "Chan %d PortID 0x%x 0x%08x%08x/0x%08x%08x %ld "
3840 			    "already at idx %d, state 0x%x", chan, portid,
3841 			    (uint32_t) (wwnn >> 32), (uint32_t) wwnn,
3842 			    (uint32_t) (wwpn >> 32), (uint32_t) wwpn,
3843 			    (long) (lp - fcp->portdb), dbidx,
3844 			    fcp->portdb[dbidx].state);
3845 			continue;
3846 		}
3847 
3848 		/*
3849 		 * We found a zombie entry that matches us.
3850 		 * Revive it. We know that WWN and WWPN
3851 		 * are the same. For fabric devices, we
3852 		 * don't care that handle is different
3853 		 * as we assign that. If role or portid
3854 		 * are different, it maybe a changed device.
3855 		 */
3856 		lp = &fcp->portdb[dbidx];
3857 		lp->handle = handle;
3858 		lp->new_portid = portid;
3859 		lp->new_roles = nr;
3860 		if (lp->portid != portid || lp->roles != nr) {
3861 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3862 			    "Chan %d Zombie Fabric Port 0x%06x Now Changed",
3863 			    chan, portid);
3864 			lp->state = FC_PORTDB_STATE_CHANGED;
3865 		} else {
3866 			isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3867 			    "Chan %d Zombie Fabric Port 0x%06x "
3868 			    "Now Pending Valid", chan, portid);
3869 			lp->state = FC_PORTDB_STATE_PENDING_VALID;
3870 		}
3871 	}
3872 
3873 	FC_SCRATCH_RELEASE(isp, chan);
3874 	if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
3875 		ISP_MARK_PORTDB(isp, chan, 1);
3876 		return (-1);
3877 	}
3878 	fcp->isp_loopstate = LOOP_FSCAN_DONE;
3879 	isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
3880 	    "Chan %d FC Scan Fabric Done", chan);
3881 	return (0);
3882 }
3883 
3884 /*
3885  * Find an unused handle and try and use to login to a port.
3886  */
3887 static int
3888 isp_login_device(ispsoftc_t *isp, int chan, uint32_t portid, isp_pdb_t *p, uint16_t *ohp)
3889 {
3890 	int lim, i, r;
3891 	uint16_t handle;
3892 
3893 	if (ISP_CAP_2KLOGIN(isp)) {
3894 		lim = NPH_MAX_2K;
3895 	} else {
3896 		lim = NPH_MAX;
3897 	}
3898 
3899 	handle = isp_nxt_handle(isp, chan, *ohp);
3900 	for (i = 0; i < lim; i++) {
3901 		/*
3902 		 * See if we're still logged into something with
3903 		 * this handle and that something agrees with this
3904 		 * port id.
3905 		 */
3906 		r = isp_getpdb(isp, chan, handle, p, 0);
3907 		if (r == 0 && p->portid != portid) {
3908 			(void) isp_plogx(isp, chan, handle, portid, PLOGX_FLG_CMD_LOGO | PLOGX_FLG_IMPLICIT | PLOGX_FLG_FREE_NPHDL, 1);
3909 		} else if (r == 0) {
3910 			break;
3911 		}
3912 		if (FCPARAM(isp, chan)->isp_loopstate != LOOP_SCANNING_FABRIC) {
3913 			return (-1);
3914 		}
3915 		/*
3916 		 * Now try and log into the device
3917 		 */
3918 		r = isp_plogx(isp, chan, handle, portid, PLOGX_FLG_CMD_PLOGI, 1);
3919 		if (FCPARAM(isp, chan)->isp_loopstate != LOOP_SCANNING_FABRIC) {
3920 			return (-1);
3921 		}
3922 		if (r == 0) {
3923 			*ohp = handle;
3924 			break;
3925 		} else if ((r & 0xffff) == MBOX_PORT_ID_USED) {
3926 			/*
3927 			 * If we get here, then the firmwware still thinks we're logged into this device, but with a different
3928 			 * handle. We need to break that association. We used to try and just substitute the handle, but then
3929 			 * failed to get any data via isp_getpdb (below).
3930 			 */
3931 			if (isp_plogx(isp, chan, r >> 16, portid, PLOGX_FLG_CMD_LOGO | PLOGX_FLG_IMPLICIT | PLOGX_FLG_FREE_NPHDL, 1)) {
3932 				isp_prt(isp, ISP_LOGERR, "baw... logout of %x failed", r >> 16);
3933 			}
3934 			if (FCPARAM(isp, chan)->isp_loopstate != LOOP_SCANNING_FABRIC) {
3935 				return (-1);
3936 			}
3937 			r = isp_plogx(isp, chan, handle, portid, PLOGX_FLG_CMD_PLOGI, 1);
3938 			if (FCPARAM(isp, chan)->isp_loopstate != LOOP_SCANNING_FABRIC) {
3939 				return (-1);
3940 			}
3941 			if (r == 0) {
3942 				*ohp = handle;
3943 			} else {
3944 				i = lim;
3945 			}
3946 			break;
3947 		} else if ((r & 0xffff) == MBOX_LOOP_ID_USED) {
3948 			/*
3949 			 * Try the next loop id.
3950 			 */
3951 			*ohp = handle;
3952 			handle = isp_nxt_handle(isp, chan, handle);
3953 		} else {
3954 			/*
3955 			 * Give up.
3956 			 */
3957 			i = lim;
3958 			break;
3959 		}
3960 	}
3961 
3962 	if (i == lim) {
3963 		isp_prt(isp, ISP_LOGWARN, "Chan %d PLOGI 0x%06x failed", chan, portid);
3964 		return (-1);
3965 	}
3966 
3967 	/*
3968 	 * If we successfully logged into it, get the PDB for it
3969 	 * so we can crosscheck that it is still what we think it
3970 	 * is and that we also have the role it plays
3971 	 */
3972 	r = isp_getpdb(isp, chan, handle, p, 0);
3973 	if (FCPARAM(isp, chan)->isp_loopstate != LOOP_SCANNING_FABRIC) {
3974 		return (-1);
3975 	}
3976 	if (r != 0) {
3977 		isp_prt(isp, ISP_LOGERR, "Chan %d new device 0x%06x@0x%x disappeared", chan, portid, handle);
3978 		return (-1);
3979 	}
3980 
3981 	if (p->handle != handle || p->portid != portid) {
3982 		isp_prt(isp, ISP_LOGERR, "Chan %d new device 0x%06x@0x%x changed (0x%06x@0x%0x)",
3983 		    chan, portid, handle, p->portid, p->handle);
3984 		return (-1);
3985 	}
3986 	return (0);
3987 }
3988 
3989 static int
3990 isp_register_fc4_type(ispsoftc_t *isp, int chan)
3991 {
3992 	fcparam *fcp = FCPARAM(isp, chan);
3993 	uint8_t local[SNS_RFT_ID_REQ_SIZE];
3994 	sns_screq_t *reqp = (sns_screq_t *) local;
3995 	mbreg_t mbs;
3996 
3997 	ISP_MEMZERO((void *) reqp, SNS_RFT_ID_REQ_SIZE);
3998 	reqp->snscb_rblen = SNS_RFT_ID_RESP_SIZE >> 1;
3999 	reqp->snscb_addr[RQRSP_ADDR0015] = DMA_WD0(fcp->isp_scdma + 0x100);
4000 	reqp->snscb_addr[RQRSP_ADDR1631] = DMA_WD1(fcp->isp_scdma + 0x100);
4001 	reqp->snscb_addr[RQRSP_ADDR3247] = DMA_WD2(fcp->isp_scdma + 0x100);
4002 	reqp->snscb_addr[RQRSP_ADDR4863] = DMA_WD3(fcp->isp_scdma + 0x100);
4003 	reqp->snscb_sblen = 22;
4004 	reqp->snscb_data[0] = SNS_RFT_ID;
4005 	reqp->snscb_data[4] = fcp->isp_portid & 0xffff;
4006 	reqp->snscb_data[5] = (fcp->isp_portid >> 16) & 0xff;
4007 	reqp->snscb_data[6] = (1 << FC4_SCSI);
4008 	if (FC_SCRATCH_ACQUIRE(isp, chan)) {
4009 		isp_prt(isp, ISP_LOGERR, sacq);
4010 		return (-1);
4011 	}
4012 	isp_put_sns_request(isp, reqp, (sns_screq_t *) fcp->isp_scratch);
4013 	MBSINIT(&mbs, MBOX_SEND_SNS, MBLOGALL, 1000000);
4014 	mbs.param[1] = SNS_RFT_ID_REQ_SIZE >> 1;
4015 	mbs.param[2] = DMA_WD1(fcp->isp_scdma);
4016 	mbs.param[3] = DMA_WD0(fcp->isp_scdma);
4017 	mbs.param[6] = DMA_WD3(fcp->isp_scdma);
4018 	mbs.param[7] = DMA_WD2(fcp->isp_scdma);
4019 	MEMORYBARRIER(isp, SYNC_SFORDEV, 0, SNS_RFT_ID_REQ_SIZE, chan);
4020 	isp_mboxcmd(isp, &mbs);
4021 	FC_SCRATCH_RELEASE(isp, chan);
4022 	if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
4023 		return (0);
4024 	} else {
4025 		return (-1);
4026 	}
4027 }
4028 
4029 static int
4030 isp_register_fc4_type_24xx(ispsoftc_t *isp, int chan)
4031 {
4032 	mbreg_t mbs;
4033 	fcparam *fcp = FCPARAM(isp, chan);
4034 	union {
4035 		isp_ct_pt_t plocal;
4036 		rft_id_t clocal;
4037 		uint8_t q[QENTRY_LEN];
4038 	} un;
4039 	isp_ct_pt_t *pt;
4040 	ct_hdr_t *ct;
4041 	rft_id_t *rp;
4042 	uint8_t *scp = fcp->isp_scratch;
4043 
4044 	if (FC_SCRATCH_ACQUIRE(isp, chan)) {
4045 		isp_prt(isp, ISP_LOGERR, sacq);
4046 		return (-1);
4047 	}
4048 
4049 	/*
4050 	 * Build a Passthrough IOCB in memory.
4051 	 */
4052 	ISP_MEMZERO(un.q, QENTRY_LEN);
4053 	pt = &un.plocal;
4054 	pt->ctp_header.rqs_entry_count = 1;
4055 	pt->ctp_header.rqs_entry_type = RQSTYPE_CT_PASSTHRU;
4056 	pt->ctp_handle = 0xffffffff;
4057 	pt->ctp_nphdl = fcp->isp_sns_hdl;
4058 	pt->ctp_cmd_cnt = 1;
4059 	pt->ctp_vpidx = ISP_GET_VPIDX(isp, chan);
4060 	pt->ctp_time = 1;
4061 	pt->ctp_rsp_cnt = 1;
4062 	pt->ctp_rsp_bcnt = sizeof (ct_hdr_t);
4063 	pt->ctp_cmd_bcnt = sizeof (rft_id_t);
4064 	pt->ctp_dataseg[0].ds_base = DMA_LO32(fcp->isp_scdma+XTXOFF);
4065 	pt->ctp_dataseg[0].ds_basehi = DMA_HI32(fcp->isp_scdma+XTXOFF);
4066 	pt->ctp_dataseg[0].ds_count = sizeof (rft_id_t);
4067 	pt->ctp_dataseg[1].ds_base = DMA_LO32(fcp->isp_scdma+IGPOFF);
4068 	pt->ctp_dataseg[1].ds_basehi = DMA_HI32(fcp->isp_scdma+IGPOFF);
4069 	pt->ctp_dataseg[1].ds_count = sizeof (ct_hdr_t);
4070 	isp_put_ct_pt(isp, pt, (isp_ct_pt_t *) &scp[CTXOFF]);
4071 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
4072 		isp_print_bytes(isp, "IOCB CT Request", QENTRY_LEN, pt);
4073 	}
4074 
4075 	/*
4076 	 * Build the CT header and command in memory.
4077 	 *
4078 	 * Note that the CT header has to end up as Big Endian format in memory.
4079 	 */
4080 	ISP_MEMZERO(&un.clocal, sizeof (un.clocal));
4081 	ct = &un.clocal.rftid_hdr;
4082 	ct->ct_revision = CT_REVISION;
4083 	ct->ct_fcs_type = CT_FC_TYPE_FC;
4084 	ct->ct_fcs_subtype = CT_FC_SUBTYPE_NS;
4085 	ct->ct_cmd_resp = SNS_RFT_ID;
4086 	ct->ct_bcnt_resid = (sizeof (rft_id_t) - sizeof (ct_hdr_t)) >> 2;
4087 	rp = &un.clocal;
4088 	rp->rftid_portid[0] = fcp->isp_portid >> 16;
4089 	rp->rftid_portid[1] = fcp->isp_portid >> 8;
4090 	rp->rftid_portid[2] = fcp->isp_portid;
4091 	rp->rftid_fc4types[FC4_SCSI >> 5] = 1 << (FC4_SCSI & 0x1f);
4092 	isp_put_rft_id(isp, rp, (rft_id_t *) &scp[XTXOFF]);
4093 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
4094 		isp_print_bytes(isp, "CT Header", QENTRY_LEN, &scp[XTXOFF]);
4095 	}
4096 
4097 	ISP_MEMZERO(&scp[ZTXOFF], sizeof (ct_hdr_t));
4098 
4099 	MBSINIT(&mbs, MBOX_EXEC_COMMAND_IOCB_A64, MBLOGALL, 1000000);
4100 	mbs.param[1] = QENTRY_LEN;
4101 	mbs.param[2] = DMA_WD1(fcp->isp_scdma + CTXOFF);
4102 	mbs.param[3] = DMA_WD0(fcp->isp_scdma + CTXOFF);
4103 	mbs.param[6] = DMA_WD3(fcp->isp_scdma + CTXOFF);
4104 	mbs.param[7] = DMA_WD2(fcp->isp_scdma + CTXOFF);
4105 	MEMORYBARRIER(isp, SYNC_SFORDEV, XTXOFF, 2 * QENTRY_LEN, chan);
4106 	isp_mboxcmd(isp, &mbs);
4107 	if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4108 		FC_SCRATCH_RELEASE(isp, chan);
4109 		return (-1);
4110 	}
4111 	MEMORYBARRIER(isp, SYNC_SFORCPU, ZTXOFF, QENTRY_LEN, chan);
4112 	pt = &un.plocal;
4113 	isp_get_ct_pt(isp, (isp_ct_pt_t *) &scp[ZTXOFF], pt);
4114 	if (isp->isp_dblev & ISP_LOGDEBUG1) {
4115 		isp_print_bytes(isp, "IOCB response", QENTRY_LEN, pt);
4116 	}
4117 	if (pt->ctp_status) {
4118 		FC_SCRATCH_RELEASE(isp, chan);
4119 		isp_prt(isp, ISP_LOGWARN,
4120 		    "Chan %d Register FC4 Type CT Passthrough returned 0x%x",
4121 		    chan, pt->ctp_status);
4122 		return (1);
4123 	}
4124 
4125 	isp_get_ct_hdr(isp, (ct_hdr_t *) &scp[IGPOFF], ct);
4126 	FC_SCRATCH_RELEASE(isp, chan);
4127 
4128 	if (ct->ct_cmd_resp == LS_RJT) {
4129 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
4130 		    "Chan %d Register FC4 Type rejected", chan);
4131 		return (-1);
4132 	} else if (ct->ct_cmd_resp == LS_ACC) {
4133 		isp_prt(isp, ISP_LOGSANCFG|ISP_LOGDEBUG0,
4134 		    "Chan %d Register FC4 Type accepted", chan);
4135 		return (0);
4136 	} else {
4137 		isp_prt(isp, ISP_LOGWARN,
4138 		    "Chan %d Register FC4 Type: 0x%x",
4139 		    chan, ct->ct_cmd_resp);
4140 		return (-1);
4141 	}
4142 }
4143 
4144 static uint16_t
4145 isp_nxt_handle(ispsoftc_t *isp, int chan, uint16_t handle)
4146 {
4147 	int i;
4148 	if (handle == NIL_HANDLE) {
4149 		if (FCPARAM(isp, chan)->isp_topo == TOPO_F_PORT) {
4150 			handle = 0;
4151 		} else {
4152 			handle = SNS_ID+1;
4153 		}
4154 	} else {
4155 		handle += 1;
4156 		if (handle >= FL_ID && handle <= SNS_ID) {
4157 			handle = SNS_ID+1;
4158 		}
4159 		if (handle >= NPH_RESERVED && handle <= NPH_FL_ID) {
4160 			handle = NPH_FL_ID+1;
4161 		}
4162 		if (ISP_CAP_2KLOGIN(isp)) {
4163 			if (handle == NPH_MAX_2K) {
4164 				handle = 0;
4165 			}
4166 		} else {
4167 			if (handle == NPH_MAX) {
4168 				handle = 0;
4169 			}
4170 		}
4171 	}
4172 	if (handle == FCPARAM(isp, chan)->isp_loopid) {
4173 		return (isp_nxt_handle(isp, chan, handle));
4174 	}
4175 	for (i = 0; i < MAX_FC_TARG; i++) {
4176 		if (FCPARAM(isp, chan)->portdb[i].state ==
4177 		    FC_PORTDB_STATE_NIL) {
4178 			continue;
4179 		}
4180 		if (FCPARAM(isp, chan)->portdb[i].handle == handle) {
4181 			return (isp_nxt_handle(isp, chan, handle));
4182 		}
4183 	}
4184 	return (handle);
4185 }
4186 
4187 /*
4188  * Start a command. Locking is assumed done in the caller.
4189  */
4190 
4191 int
4192 isp_start(XS_T *xs)
4193 {
4194 	ispsoftc_t *isp;
4195 	uint32_t handle, cdblen;
4196 	uint8_t local[QENTRY_LEN];
4197 	ispreq_t *reqp;
4198 	void *cdbp, *qep;
4199 	uint16_t *tptr;
4200 	int target, dmaresult, hdlidx = 0;
4201 
4202 	XS_INITERR(xs);
4203 	isp = XS_ISP(xs);
4204 
4205 	/*
4206 	 * Now make sure we're running.
4207 	 */
4208 
4209 	if (isp->isp_state != ISP_RUNSTATE) {
4210 		isp_prt(isp, ISP_LOGERR, "Adapter not at RUNSTATE");
4211 		XS_SETERR(xs, HBA_BOTCH);
4212 		return (CMD_COMPLETE);
4213 	}
4214 
4215 	/*
4216 	 * Check command CDB length, etc.. We really are limited to 16 bytes
4217 	 * for Fibre Channel, but can do up to 44 bytes in parallel SCSI,
4218 	 * but probably only if we're running fairly new firmware (we'll
4219 	 * let the old f/w choke on an extended command queue entry).
4220 	 */
4221 
4222 	if (XS_CDBLEN(xs) > (IS_FC(isp)? 16 : 44) || XS_CDBLEN(xs) == 0) {
4223 		isp_prt(isp, ISP_LOGERR, "unsupported cdb length (%d, CDB[0]=0x%x)", XS_CDBLEN(xs), XS_CDBP(xs)[0] & 0xff);
4224 		XS_SETERR(xs, HBA_BOTCH);
4225 		return (CMD_COMPLETE);
4226 	}
4227 
4228 	/*
4229 	 * Translate the target to device handle as appropriate, checking
4230 	 * for correct device state as well.
4231 	 */
4232 	target = XS_TGT(xs);
4233 	if (IS_FC(isp)) {
4234 		fcparam *fcp = FCPARAM(isp, XS_CHANNEL(xs));
4235 
4236 		if ((fcp->role & ISP_ROLE_INITIATOR) == 0) {
4237 			XS_SETERR(xs, HBA_SELTIMEOUT);
4238 			return (CMD_COMPLETE);
4239 		}
4240 
4241 		/*
4242 		 * Try again later.
4243 		 */
4244 		if (fcp->isp_fwstate != FW_READY || fcp->isp_loopstate != LOOP_READY) {
4245 			return (CMD_RQLATER);
4246 		}
4247 
4248 		if (XS_TGT(xs) >= MAX_FC_TARG) {
4249 			XS_SETERR(xs, HBA_SELTIMEOUT);
4250 			return (CMD_COMPLETE);
4251 		}
4252 
4253 		hdlidx = fcp->isp_dev_map[XS_TGT(xs)] - 1;
4254 		isp_prt(isp, ISP_LOGDEBUG2, "XS_TGT(xs)=%d- hdlidx value %d", XS_TGT(xs), hdlidx);
4255 		if (hdlidx < 0 || hdlidx >= MAX_FC_TARG) {
4256 			XS_SETERR(xs, HBA_SELTIMEOUT);
4257 			return (CMD_COMPLETE);
4258 		}
4259 		if (fcp->portdb[hdlidx].state == FC_PORTDB_STATE_ZOMBIE) {
4260 			return (CMD_RQLATER);
4261 		}
4262 		if (fcp->portdb[hdlidx].state != FC_PORTDB_STATE_VALID) {
4263 			XS_SETERR(xs, HBA_SELTIMEOUT);
4264 			return (CMD_COMPLETE);
4265 		}
4266 		target = fcp->portdb[hdlidx].handle;
4267 		fcp->portdb[hdlidx].dirty = 1;
4268 	} else {
4269 		sdparam *sdp = SDPARAM(isp, XS_CHANNEL(xs));
4270 		if ((sdp->role & ISP_ROLE_INITIATOR) == 0) {
4271 			XS_SETERR(xs, HBA_SELTIMEOUT);
4272 			return (CMD_COMPLETE);
4273 		}
4274 		if (sdp->update) {
4275 			isp_spi_update(isp, XS_CHANNEL(xs));
4276 		}
4277 	}
4278 
4279  start_again:
4280 
4281 	qep = isp_getrqentry(isp);
4282 	if (qep == NULL) {
4283 		isp_prt(isp, ISP_LOGDEBUG0, "Request Queue Overflow");
4284 		XS_SETERR(xs, HBA_BOTCH);
4285 		return (CMD_EAGAIN);
4286 	}
4287 	XS_SETERR(xs, HBA_NOERROR);
4288 
4289 	/*
4290 	 * Now see if we need to synchronize the ISP with respect to anything.
4291 	 * We do dual duty here (cough) for synchronizing for busses other
4292 	 * than which we got here to send a command to.
4293 	 */
4294 	reqp = (ispreq_t *) local;
4295 	ISP_MEMZERO(local, QENTRY_LEN);
4296 	if (ISP_TST_SENDMARKER(isp, XS_CHANNEL(xs))) {
4297 		if (IS_24XX(isp)) {
4298 			isp_marker_24xx_t *m = (isp_marker_24xx_t *) reqp;
4299 			m->mrk_header.rqs_entry_count = 1;
4300 			m->mrk_header.rqs_entry_type = RQSTYPE_MARKER;
4301 			m->mrk_modifier = SYNC_ALL;
4302 			isp_put_marker_24xx(isp, m, qep);
4303 		} else {
4304 			isp_marker_t *m = (isp_marker_t *) reqp;
4305 			m->mrk_header.rqs_entry_count = 1;
4306 			m->mrk_header.rqs_entry_type = RQSTYPE_MARKER;
4307 			m->mrk_target = (XS_CHANNEL(xs) << 7);	/* bus # */
4308 			m->mrk_modifier = SYNC_ALL;
4309 			isp_put_marker(isp, m, qep);
4310 		}
4311 		ISP_SYNC_REQUEST(isp);
4312 		ISP_SET_SENDMARKER(isp, XS_CHANNEL(xs), 0);
4313 		goto start_again;
4314 	}
4315 
4316 	reqp->req_header.rqs_entry_count = 1;
4317 	if (IS_24XX(isp)) {
4318 		reqp->req_header.rqs_entry_type = RQSTYPE_T7RQS;
4319 	} else if (IS_FC(isp)) {
4320 		reqp->req_header.rqs_entry_type = RQSTYPE_T2RQS;
4321 	} else {
4322 		if (XS_CDBLEN(xs) > 12) {
4323 			reqp->req_header.rqs_entry_type = RQSTYPE_CMDONLY;
4324 		} else {
4325 			reqp->req_header.rqs_entry_type = RQSTYPE_REQUEST;
4326 		}
4327 	}
4328 
4329 	if (IS_24XX(isp)) {
4330 		int ttype;
4331 		if (XS_TAG_P(xs)) {
4332 			ttype = XS_TAG_TYPE(xs);
4333 		} else {
4334 			if (XS_CDBP(xs)[0] == 0x3) {
4335 				ttype = REQFLAG_HTAG;
4336 			} else {
4337 				ttype = REQFLAG_STAG;
4338 			}
4339 		}
4340 		if (ttype == REQFLAG_OTAG) {
4341 			ttype = FCP_CMND_TASK_ATTR_ORDERED;
4342 		} else if (ttype == REQFLAG_HTAG) {
4343 			ttype = FCP_CMND_TASK_ATTR_HEAD;
4344 		} else {
4345 			ttype = FCP_CMND_TASK_ATTR_SIMPLE;
4346 		}
4347 		((ispreqt7_t *)reqp)->req_task_attribute = ttype;
4348 	} else if (IS_FC(isp)) {
4349 		/*
4350 		 * See comment in isp_intr
4351 		 */
4352 		/* XS_SET_RESID(xs, 0); */
4353 
4354 		/*
4355 		 * Fibre Channel always requires some kind of tag.
4356 		 * The Qlogic drivers seem be happy not to use a tag,
4357 		 * but this breaks for some devices (IBM drives).
4358 		 */
4359 		if (XS_TAG_P(xs)) {
4360 			((ispreqt2_t *)reqp)->req_flags = XS_TAG_TYPE(xs);
4361 		} else {
4362 			/*
4363 			 * If we don't know what tag to use, use HEAD OF QUEUE
4364 			 * for Request Sense or Simple.
4365 			 */
4366 			if (XS_CDBP(xs)[0] == 0x3)	/* REQUEST SENSE */
4367 				((ispreqt2_t *)reqp)->req_flags = REQFLAG_HTAG;
4368 			else
4369 				((ispreqt2_t *)reqp)->req_flags = REQFLAG_STAG;
4370 		}
4371 	} else {
4372 		sdparam *sdp = SDPARAM(isp, XS_CHANNEL(xs));
4373 		if ((sdp->isp_devparam[target].actv_flags & DPARM_TQING) && XS_TAG_P(xs)) {
4374 			reqp->req_flags = XS_TAG_TYPE(xs);
4375 		}
4376 	}
4377 
4378 	tptr = &reqp->req_time;
4379 
4380 	/*
4381 	 * NB: we do not support long CDBs
4382 	 */
4383 	cdblen = XS_CDBLEN(xs);
4384 
4385 	if (IS_SCSI(isp)) {
4386 		reqp->req_target = target | (XS_CHANNEL(xs) << 7);
4387 		reqp->req_lun_trn = XS_LUN(xs);
4388 		cdblen = ISP_MIN(cdblen, sizeof (reqp->req_cdb));
4389 		cdbp = reqp->req_cdb;
4390 		reqp->req_cdblen = cdblen;
4391 	} else if (IS_24XX(isp)) {
4392 		ispreqt7_t *t7 = (ispreqt7_t *)local;
4393 		fcportdb_t *lp;
4394 
4395 		lp = &FCPARAM(isp, XS_CHANNEL(xs))->portdb[hdlidx];
4396 		t7->req_nphdl = target;
4397 		t7->req_tidlo = lp->portid;
4398 		t7->req_tidhi = lp->portid >> 16;
4399 		t7->req_vpidx = ISP_GET_VPIDX(isp, XS_CHANNEL(xs));
4400 		if (XS_LUN(xs) > 256) {
4401 			t7->req_lun[0] = XS_LUN(xs) >> 8;
4402 			t7->req_lun[0] |= 0x40;
4403 		}
4404 		t7->req_lun[1] = XS_LUN(xs);
4405 		tptr = &t7->req_time;
4406 		cdbp = t7->req_cdb;
4407 		cdblen = ISP_MIN(cdblen, sizeof (t7->req_cdb));
4408 	} else if (ISP_CAP_2KLOGIN(isp)) {
4409 		ispreqt2e_t *t2e = (ispreqt2e_t *)local;
4410 		t2e->req_target = target;
4411 		t2e->req_scclun = XS_LUN(xs);
4412 		cdbp = t2e->req_cdb;
4413 		cdblen = ISP_MIN(cdblen, sizeof (t2e->req_cdb));
4414 	} else if (ISP_CAP_SCCFW(isp)) {
4415 		ispreqt2_t *t2 = (ispreqt2_t *)local;
4416 		t2->req_target = target;
4417 		t2->req_scclun = XS_LUN(xs);
4418 		cdbp = t2->req_cdb;
4419 		cdblen = ISP_MIN(cdblen, sizeof (t2->req_cdb));
4420 	} else {
4421 		ispreqt2_t *t2 = (ispreqt2_t *)local;
4422 		t2->req_target = target;
4423 		t2->req_lun_trn = XS_LUN(xs);
4424 		cdbp = t2->req_cdb;
4425 		cdblen = ISP_MIN(cdblen, sizeof (t2->req_cdb));
4426 	}
4427 	ISP_MEMCPY(cdbp, XS_CDBP(xs), cdblen);
4428 
4429 	*tptr = XS_TIME(xs) / 1000;
4430 	if (*tptr == 0 && XS_TIME(xs)) {
4431 		*tptr = 1;
4432 	}
4433 	if (IS_24XX(isp) && *tptr > 0x1999) {
4434 		*tptr = 0x1999;
4435 	}
4436 
4437 	if (isp_allocate_xs(isp, xs, &handle)) {
4438 		isp_prt(isp, ISP_LOGDEBUG0, "out of xflist pointers");
4439 		XS_SETERR(xs, HBA_BOTCH);
4440 		return (CMD_EAGAIN);
4441 	}
4442 	/* Whew. Thankfully the same for type 7 requests */
4443 	reqp->req_handle = handle;
4444 
4445 	/*
4446 	 * Set up DMA and/or do any platform dependent swizzling of the request entry
4447 	 * so that the Qlogic F/W understands what is being asked of it.
4448 	 *
4449 	 * The callee is responsible for adding all requests at this point.
4450 	 */
4451 	dmaresult = ISP_DMASETUP(isp, xs, reqp);
4452 	if (dmaresult != CMD_QUEUED) {
4453 		isp_destroy_handle(isp, handle);
4454 		/*
4455 		 * dmasetup sets actual error in packet, and
4456 		 * return what we were given to return.
4457 		 */
4458 		return (dmaresult);
4459 	}
4460 	isp_xs_prt(isp, xs, ISP_LOGDEBUG0, "START cmd cdb[0]=0x%x datalen %ld", XS_CDBP(xs)[0], (long) XS_XFRLEN(xs));
4461 	isp->isp_nactive++;
4462 	return (CMD_QUEUED);
4463 }
4464 
4465 /*
4466  * isp control
4467  * Locks (ints blocked) assumed held.
4468  */
4469 
4470 int
4471 isp_control(ispsoftc_t *isp, ispctl_t ctl, ...)
4472 {
4473 	XS_T *xs;
4474 	mbreg_t *mbr, mbs;
4475 	int chan, tgt;
4476 	uint32_t handle;
4477 	__va_list ap;
4478 
4479 	switch (ctl) {
4480 	case ISPCTL_RESET_BUS:
4481 		/*
4482 		 * Issue a bus reset.
4483 		 */
4484 		if (IS_24XX(isp)) {
4485 			isp_prt(isp, ISP_LOGWARN, "RESET BUS NOT IMPLEMENTED");
4486 			break;
4487 		} else if (IS_FC(isp)) {
4488 			mbs.param[1] = 10;
4489 			chan = 0;
4490 		} else {
4491 			__va_start(ap, ctl);
4492 			chan = __va_arg(ap, int);
4493 			__va_end(ap);
4494 			mbs.param[1] = SDPARAM(isp, chan)->isp_bus_reset_delay;
4495 			if (mbs.param[1] < 2) {
4496 				mbs.param[1] = 2;
4497 			}
4498 			mbs.param[2] = chan;
4499 		}
4500 		MBSINIT(&mbs, MBOX_BUS_RESET, MBLOGALL, 0);
4501 		ISP_SET_SENDMARKER(isp, chan, 1);
4502 		isp_mboxcmd(isp, &mbs);
4503 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4504 			break;
4505 		}
4506 		isp_prt(isp, ISP_LOGINFO,
4507 		    "driver initiated bus reset of bus %d", chan);
4508 		return (0);
4509 
4510 	case ISPCTL_RESET_DEV:
4511 		__va_start(ap, ctl);
4512 		chan = __va_arg(ap, int);
4513 		tgt = __va_arg(ap, int);
4514 		__va_end(ap);
4515 		if (IS_24XX(isp)) {
4516 			uint8_t local[QENTRY_LEN];
4517 			isp24xx_tmf_t *tmf;
4518 			isp24xx_statusreq_t *sp;
4519 			fcparam *fcp = FCPARAM(isp, chan);
4520 			fcportdb_t *lp;
4521 			int hdlidx;
4522 
4523 			hdlidx = fcp->isp_dev_map[tgt] - 1;
4524 			if (hdlidx < 0 || hdlidx >= MAX_FC_TARG) {
4525 				isp_prt(isp, ISP_LOGWARN,
4526 				    "Chan %d bad handle %d trying to reset"
4527 				    "target %d", chan, hdlidx, tgt);
4528 				break;
4529 			}
4530 			lp = &fcp->portdb[hdlidx];
4531 			if (lp->state != FC_PORTDB_STATE_VALID) {
4532 				isp_prt(isp, ISP_LOGWARN,
4533 				    "Chan %d handle %d for abort of target %d "
4534 				    "no longer valid", chan,
4535 				    hdlidx, tgt);
4536 				break;
4537 			}
4538 
4539 			tmf = (isp24xx_tmf_t *) local;
4540 			ISP_MEMZERO(tmf, QENTRY_LEN);
4541 			tmf->tmf_header.rqs_entry_type = RQSTYPE_TSK_MGMT;
4542 			tmf->tmf_header.rqs_entry_count = 1;
4543 			tmf->tmf_nphdl = lp->handle;
4544 			tmf->tmf_delay = 2;
4545 			tmf->tmf_timeout = 2;
4546 			tmf->tmf_flags = ISP24XX_TMF_TARGET_RESET;
4547 			tmf->tmf_tidlo = lp->portid;
4548 			tmf->tmf_tidhi = lp->portid >> 16;
4549 			tmf->tmf_vpidx = ISP_GET_VPIDX(isp, chan);
4550 			isp_prt(isp, ISP_LOGALL, "Chan %d Reset N-Port Handle 0x%04x @ Port 0x%06x", chan, lp->handle, lp->portid);
4551 			MBSINIT(&mbs, MBOX_EXEC_COMMAND_IOCB_A64, MBLOGALL, 5000000);
4552 			mbs.param[1] = QENTRY_LEN;
4553 			mbs.param[2] = DMA_WD1(fcp->isp_scdma);
4554 			mbs.param[3] = DMA_WD0(fcp->isp_scdma);
4555 			mbs.param[6] = DMA_WD3(fcp->isp_scdma);
4556 			mbs.param[7] = DMA_WD2(fcp->isp_scdma);
4557 
4558 			if (FC_SCRATCH_ACQUIRE(isp, chan)) {
4559 				isp_prt(isp, ISP_LOGERR, sacq);
4560 				break;
4561 			}
4562 			isp_put_24xx_tmf(isp, tmf, fcp->isp_scratch);
4563 			MEMORYBARRIER(isp, SYNC_SFORDEV, 0, QENTRY_LEN, chan);
4564 			fcp->sendmarker = 1;
4565 			isp_mboxcmd(isp, &mbs);
4566 			if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4567 				FC_SCRATCH_RELEASE(isp, chan);
4568 				break;
4569 			}
4570 			MEMORYBARRIER(isp, SYNC_SFORCPU, QENTRY_LEN,
4571 			    QENTRY_LEN, chan);
4572 			sp = (isp24xx_statusreq_t *) local;
4573 			isp_get_24xx_response(isp,
4574 			    &((isp24xx_statusreq_t *)fcp->isp_scratch)[1], sp);
4575 			FC_SCRATCH_RELEASE(isp, chan);
4576 			if (sp->req_completion_status == 0) {
4577 				return (0);
4578 			}
4579 			isp_prt(isp, ISP_LOGWARN,
4580 			    "Chan %d reset of target %d returned 0x%x",
4581 			    chan, tgt, sp->req_completion_status);
4582 			break;
4583 		} else if (IS_FC(isp)) {
4584 			if (ISP_CAP_2KLOGIN(isp)) {
4585 				mbs.param[1] = tgt;
4586 				mbs.ibits = (1 << 10);
4587 			} else {
4588 				mbs.param[1] = (tgt << 8);
4589 			}
4590 		} else {
4591 			mbs.param[1] = (chan << 15) | (tgt << 8);
4592 		}
4593 		MBSINIT(&mbs, MBOX_ABORT_TARGET, MBLOGALL, 0);
4594 		mbs.param[2] = 3;	/* 'delay', in seconds */
4595 		isp_mboxcmd(isp, &mbs);
4596 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4597 			break;
4598 		}
4599 		isp_prt(isp, ISP_LOGINFO,
4600 		    "Target %d on Bus %d Reset Succeeded", tgt, chan);
4601 		ISP_SET_SENDMARKER(isp, chan, 1);
4602 		return (0);
4603 
4604 	case ISPCTL_ABORT_CMD:
4605 		__va_start(ap, ctl);
4606 		xs = __va_arg(ap, XS_T *);
4607 		__va_end(ap);
4608 
4609 		tgt = XS_TGT(xs);
4610 		chan = XS_CHANNEL(xs);
4611 
4612 		handle = isp_find_handle(isp, xs);
4613 		if (handle == 0) {
4614 			isp_prt(isp, ISP_LOGWARN,
4615 			    "cannot find handle for command to abort");
4616 			break;
4617 		}
4618 		if (IS_24XX(isp)) {
4619 			isp24xx_abrt_t local, *ab = &local, *ab2;
4620 			fcparam *fcp;
4621 			fcportdb_t *lp;
4622 			int hdlidx;
4623 
4624 			fcp = FCPARAM(isp, chan);
4625 			hdlidx = fcp->isp_dev_map[tgt] - 1;
4626 			if (hdlidx < 0 || hdlidx >= MAX_FC_TARG) {
4627 				isp_prt(isp, ISP_LOGWARN,
4628 				    "Chan %d bad handle %d trying to abort"
4629 				    "target %d", chan, hdlidx, tgt);
4630 				break;
4631 			}
4632 			lp = &fcp->portdb[hdlidx];
4633 			if (lp->state != FC_PORTDB_STATE_VALID) {
4634 				isp_prt(isp, ISP_LOGWARN,
4635 				    "Chan %d handle %d for abort of target %d "
4636 				    "no longer valid", chan, hdlidx, tgt);
4637 				break;
4638 			}
4639 			isp_prt(isp, ISP_LOGALL,
4640 			    "Chan %d Abort Cmd for N-Port 0x%04x @ Port "
4641 			    "0x%06x %p", chan, lp->handle, lp->portid, xs);
4642 			ISP_MEMZERO(ab, QENTRY_LEN);
4643 			ab->abrt_header.rqs_entry_type = RQSTYPE_ABORT_IO;
4644 			ab->abrt_header.rqs_entry_count = 1;
4645 			ab->abrt_handle = lp->handle;
4646 			ab->abrt_cmd_handle = handle;
4647 			ab->abrt_tidlo = lp->portid;
4648 			ab->abrt_tidhi = lp->portid >> 16;
4649 			ab->abrt_vpidx = ISP_GET_VPIDX(isp, chan);
4650 
4651 			ISP_MEMZERO(&mbs, sizeof (mbs));
4652 			MBSINIT(&mbs, MBOX_EXEC_COMMAND_IOCB_A64, MBLOGALL, 5000000);
4653 			mbs.param[1] = QENTRY_LEN;
4654 			mbs.param[2] = DMA_WD1(fcp->isp_scdma);
4655 			mbs.param[3] = DMA_WD0(fcp->isp_scdma);
4656 			mbs.param[6] = DMA_WD3(fcp->isp_scdma);
4657 			mbs.param[7] = DMA_WD2(fcp->isp_scdma);
4658 
4659 			if (FC_SCRATCH_ACQUIRE(isp, chan)) {
4660 				isp_prt(isp, ISP_LOGERR, sacq);
4661 				break;
4662 			}
4663 			isp_put_24xx_abrt(isp, ab, fcp->isp_scratch);
4664 			ab2 = (isp24xx_abrt_t *)
4665 			    &((uint8_t *)fcp->isp_scratch)[QENTRY_LEN];
4666 			ab2->abrt_nphdl = 0xdeaf;
4667 			MEMORYBARRIER(isp, SYNC_SFORDEV, 0, 2 * QENTRY_LEN, chan);
4668 			isp_mboxcmd(isp, &mbs);
4669 			if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4670 				FC_SCRATCH_RELEASE(isp, chan);
4671 				break;
4672 			}
4673 			MEMORYBARRIER(isp, SYNC_SFORCPU, QENTRY_LEN,
4674 			    QENTRY_LEN, chan);
4675 			isp_get_24xx_abrt(isp, ab2, ab);
4676 			FC_SCRATCH_RELEASE(isp, chan);
4677 			if (ab->abrt_nphdl == ISP24XX_ABRT_OKAY) {
4678 				return (0);
4679 			}
4680 			isp_prt(isp, ISP_LOGWARN,
4681 			    "Chan %d handle %d abort returned 0x%x", chan,
4682 			    hdlidx, ab->abrt_nphdl);
4683 			break;
4684 		} else if (IS_FC(isp)) {
4685 			if (ISP_CAP_SCCFW(isp)) {
4686 				if (ISP_CAP_2KLOGIN(isp)) {
4687 					mbs.param[1] = tgt;
4688 				} else {
4689 					mbs.param[1] = tgt << 8;
4690 				}
4691 				mbs.param[6] = XS_LUN(xs);
4692 			} else {
4693 				mbs.param[1] = tgt << 8 | XS_LUN(xs);
4694 			}
4695 		} else {
4696 			mbs.param[1] = (chan << 15) | (tgt << 8) | XS_LUN(xs);
4697 		}
4698 		MBSINIT(&mbs, MBOX_ABORT, MBLOGALL & ~MBOX_COMMAND_ERROR, 0);
4699 		mbs.param[2] = handle;
4700 		isp_mboxcmd(isp, &mbs);
4701 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
4702 			break;
4703 		}
4704 		return (0);
4705 
4706 	case ISPCTL_UPDATE_PARAMS:
4707 
4708 		__va_start(ap, ctl);
4709 		chan = __va_arg(ap, int);
4710 		__va_end(ap);
4711 		isp_spi_update(isp, chan);
4712 		return (0);
4713 
4714 	case ISPCTL_FCLINK_TEST:
4715 
4716 		if (IS_FC(isp)) {
4717 			int usdelay;
4718 			__va_start(ap, ctl);
4719 			chan = __va_arg(ap, int);
4720 			usdelay = __va_arg(ap, int);
4721 			__va_end(ap);
4722 			if (usdelay == 0) {
4723 				usdelay =  250000;
4724 			}
4725 			return (isp_fclink_test(isp, chan, usdelay));
4726 		}
4727 		break;
4728 
4729 	case ISPCTL_SCAN_FABRIC:
4730 
4731 		if (IS_FC(isp)) {
4732 			__va_start(ap, ctl);
4733 			chan = __va_arg(ap, int);
4734 			__va_end(ap);
4735 			return (isp_scan_fabric(isp, chan));
4736 		}
4737 		break;
4738 
4739 	case ISPCTL_SCAN_LOOP:
4740 
4741 		if (IS_FC(isp)) {
4742 			__va_start(ap, ctl);
4743 			chan = __va_arg(ap, int);
4744 			__va_end(ap);
4745 			return (isp_scan_loop(isp, chan));
4746 		}
4747 		break;
4748 
4749 	case ISPCTL_PDB_SYNC:
4750 
4751 		if (IS_FC(isp)) {
4752 			__va_start(ap, ctl);
4753 			chan = __va_arg(ap, int);
4754 			__va_end(ap);
4755 			return (isp_pdb_sync(isp, chan));
4756 		}
4757 		break;
4758 
4759 	case ISPCTL_SEND_LIP:
4760 
4761 		if (IS_FC(isp) && !IS_24XX(isp)) {
4762 			MBSINIT(&mbs, MBOX_INIT_LIP, MBLOGALL, 0);
4763 			if (ISP_CAP_2KLOGIN(isp)) {
4764 				mbs.ibits = (1 << 10);
4765 			}
4766 			isp_mboxcmd(isp, &mbs);
4767 			if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
4768 				return (0);
4769 			}
4770 		}
4771 		break;
4772 
4773 	case ISPCTL_GET_PDB:
4774 		if (IS_FC(isp)) {
4775 			isp_pdb_t *pdb;
4776 			__va_start(ap, ctl);
4777 			chan = __va_arg(ap, int);
4778 			tgt = __va_arg(ap, int);
4779 			pdb = __va_arg(ap, isp_pdb_t *);
4780 			__va_end(ap);
4781 			return (isp_getpdb(isp, chan, tgt, pdb, 1));
4782 		}
4783 		break;
4784 
4785 	case ISPCTL_GET_NAMES:
4786 	{
4787 		uint64_t *wwnn, *wwnp;
4788 		__va_start(ap, ctl);
4789 		chan = __va_arg(ap, int);
4790 		tgt = __va_arg(ap, int);
4791 		wwnn = __va_arg(ap, uint64_t *);
4792 		wwnp = __va_arg(ap, uint64_t *);
4793 		__va_end(ap);
4794 		if (wwnn == NULL && wwnp == NULL) {
4795 			break;
4796 		}
4797 		if (wwnn) {
4798 			*wwnn = isp_get_wwn(isp, chan, tgt, 1);
4799 			if (*wwnn == INI_NONE) {
4800 				break;
4801 			}
4802 		}
4803 		if (wwnp) {
4804 			*wwnp = isp_get_wwn(isp, chan, tgt, 0);
4805 			if (*wwnp == INI_NONE) {
4806 				break;
4807 			}
4808 		}
4809 		return (0);
4810 	}
4811 	case ISPCTL_RUN_MBOXCMD:
4812 	{
4813 		__va_start(ap, ctl);
4814 		mbr = __va_arg(ap, mbreg_t *);
4815 		__va_end(ap);
4816 		isp_mboxcmd(isp, mbr);
4817 		return (0);
4818 	}
4819 	case ISPCTL_PLOGX:
4820 	{
4821 		isp_plcmd_t *p;
4822 		int r;
4823 
4824 		__va_start(ap, ctl);
4825 		p = __va_arg(ap, isp_plcmd_t *);
4826 		__va_end(ap);
4827 
4828 		if ((p->flags & PLOGX_FLG_CMD_MASK) != PLOGX_FLG_CMD_PLOGI || (p->handle != NIL_HANDLE)) {
4829 			return (isp_plogx(isp, p->channel, p->handle, p->portid, p->flags, 0));
4830 		}
4831 		do {
4832 			p->handle = isp_nxt_handle(isp, p->channel, p->handle);
4833 			r = isp_plogx(isp, p->channel, p->handle, p->portid, p->flags, 0);
4834 			if ((r & 0xffff) == MBOX_PORT_ID_USED) {
4835 				p->handle = r >> 16;
4836 				r = 0;
4837 				break;
4838 			}
4839 		} while ((r & 0xffff) == MBOX_LOOP_ID_USED);
4840 		return (r);
4841 	}
4842 	default:
4843 		isp_prt(isp, ISP_LOGERR, "Unknown Control Opcode 0x%x", ctl);
4844 		break;
4845 
4846 	}
4847 	return (-1);
4848 }
4849 
4850 /*
4851  * Interrupt Service Routine(s).
4852  *
4853  * External (OS) framework has done the appropriate locking,
4854  * and the locking will be held throughout this function.
4855  */
4856 
4857 /*
4858  * Limit our stack depth by sticking with the max likely number
4859  * of completions on a request queue at any one time.
4860  */
4861 #ifndef	MAX_REQUESTQ_COMPLETIONS
4862 #define	MAX_REQUESTQ_COMPLETIONS	32
4863 #endif
4864 
4865 void
4866 isp_intr(ispsoftc_t *isp, uint32_t isr, uint16_t sema, uint16_t mbox)
4867 {
4868 	XS_T *complist[MAX_REQUESTQ_COMPLETIONS], *xs;
4869 	uint32_t iptr, optr, junk;
4870 	int i, nlooked = 0, ndone = 0;
4871 
4872 again:
4873 	optr = isp->isp_residx;
4874 	/*
4875 	 * Is this a mailbox related interrupt?
4876 	 * The mailbox semaphore will be nonzero if so.
4877 	 */
4878 	if (sema) {
4879  fmbox:
4880 		if (mbox & MBOX_COMMAND_COMPLETE) {
4881 			isp->isp_intmboxc++;
4882 			if (isp->isp_mboxbsy) {
4883 				int obits = isp->isp_obits;
4884 				isp->isp_mboxtmp[0] = mbox;
4885 				for (i = 1; i < MAX_MAILBOX(isp); i++) {
4886 					if ((obits & (1 << i)) == 0) {
4887 						continue;
4888 					}
4889 					isp->isp_mboxtmp[i] = ISP_READ(isp, MBOX_OFF(i));
4890 				}
4891 				if (isp->isp_mbxwrk0) {
4892 					if (isp_mbox_continue(isp) == 0) {
4893 						return;
4894 					}
4895 				}
4896 				MBOX_NOTIFY_COMPLETE(isp);
4897 			} else {
4898 				isp_prt(isp, ISP_LOGWARN, "mailbox cmd (0x%x) with no waiters", mbox);
4899 			}
4900 		} else {
4901 			i = IS_FC(isp)? isp_parse_async_fc(isp, mbox) : isp_parse_async(isp, mbox);
4902 			if (i < 0) {
4903 				return;
4904 			}
4905 		}
4906 		if ((IS_FC(isp) && mbox != ASYNC_RIOZIO_STALL) || isp->isp_state != ISP_RUNSTATE) {
4907 			goto out;
4908 		}
4909 	}
4910 
4911 	/*
4912 	 * We can't be getting this now.
4913 	 */
4914 	if (isp->isp_state != ISP_RUNSTATE) {
4915 		/*
4916 		 * This seems to happen to 23XX and 24XX cards- don't know why.
4917 		 */
4918 		 if (isp->isp_mboxbsy && isp->isp_lastmbxcmd == MBOX_ABOUT_FIRMWARE) {
4919 			goto fmbox;
4920 		}
4921 		isp_prt(isp, ISP_LOGINFO, "interrupt (ISR=%x SEMA=%x) when not ready", isr, sema);
4922 		/*
4923 		 * Thank you very much!  *Burrrp*!
4924 		 */
4925 		ISP_WRITE(isp, isp->isp_respoutrp, ISP_READ(isp, isp->isp_respinrp));
4926 		if (IS_24XX(isp)) {
4927 			ISP_DISABLE_INTS(isp);
4928 		}
4929 		goto out;
4930 	}
4931 
4932 #ifdef	ISP_TARGET_MODE
4933 	/*
4934 	 * Check for ATIO Queue entries.
4935 	 */
4936 	if (IS_24XX(isp)) {
4937 		iptr = ISP_READ(isp, BIU2400_ATIO_RSPINP);
4938 		optr = ISP_READ(isp, BIU2400_ATIO_RSPOUTP);
4939 
4940 		while (optr != iptr) {
4941 			uint8_t qe[QENTRY_LEN];
4942 			isphdr_t *hp;
4943 			uint32_t oop;
4944 			void *addr;
4945 
4946 			oop = optr;
4947 			MEMORYBARRIER(isp, SYNC_ATIOQ, oop, QENTRY_LEN, -1);
4948 			addr = ISP_QUEUE_ENTRY(isp->isp_atioq, oop);
4949 			isp_get_hdr(isp, addr, (isphdr_t *)qe);
4950 			hp = (isphdr_t *)qe;
4951 			switch (hp->rqs_entry_type) {
4952 			case RQSTYPE_NOTIFY:
4953 			case RQSTYPE_ATIO:
4954 				(void) isp_target_notify(isp, addr, &oop);
4955 				break;
4956 			default:
4957 				isp_print_qentry(isp, "?ATIOQ entry?", oop, addr);
4958 				break;
4959 			}
4960 			optr = ISP_NXT_QENTRY(oop, RESULT_QUEUE_LEN(isp));
4961 			ISP_WRITE(isp, BIU2400_ATIO_RSPOUTP, optr);
4962 		}
4963 		optr = isp->isp_residx;
4964 	}
4965 #endif
4966 
4967 	/*
4968 	 * Get the current Response Queue Out Pointer.
4969 	 *
4970 	 * If we're a 2300 or 2400, we can ask what hardware what it thinks.
4971 	 */
4972 	if (IS_23XX(isp) || IS_24XX(isp)) {
4973 		optr = ISP_READ(isp, isp->isp_respoutrp);
4974 		/*
4975 		 * Debug: to be taken out eventually
4976 		 */
4977 		if (isp->isp_residx != optr) {
4978 			isp_prt(isp, ISP_LOGINFO, "isp_intr: hard optr=%x, soft optr %x", optr, isp->isp_residx);
4979 			isp->isp_residx = optr;
4980 		}
4981 	} else {
4982 		optr = isp->isp_residx;
4983 	}
4984 
4985 	/*
4986 	 * You *must* read the Response Queue In Pointer
4987 	 * prior to clearing the RISC interrupt.
4988 	 *
4989 	 * Debounce the 2300 if revision less than 2.
4990 	 */
4991 	if (IS_2100(isp) || (IS_2300(isp) && isp->isp_revision < 2)) {
4992 		i = 0;
4993 		do {
4994 			iptr = ISP_READ(isp, isp->isp_respinrp);
4995 			junk = ISP_READ(isp, isp->isp_respinrp);
4996 		} while (junk != iptr && ++i < 1000);
4997 
4998 		if (iptr != junk) {
4999 			isp_prt(isp, ISP_LOGWARN, "Response Queue Out Pointer Unstable (%x, %x)", iptr, junk);
5000 			goto out;
5001 		}
5002 	} else {
5003 		iptr = ISP_READ(isp, isp->isp_respinrp);
5004 	}
5005 	isp->isp_resodx = iptr;
5006 
5007 
5008 	if (optr == iptr && sema == 0) {
5009 		/*
5010 		 * There are a lot of these- reasons unknown- mostly on
5011 		 * faster Alpha machines.
5012 		 *
5013 		 * I tried delaying after writing HCCR_CMD_CLEAR_RISC_INT to
5014 		 * make sure the old interrupt went away (to avoid 'ringing'
5015 		 * effects), but that didn't stop this from occurring.
5016 		 */
5017 		if (IS_24XX(isp)) {
5018 			junk = 0;
5019 		} else if (IS_23XX(isp)) {
5020 			ISP_DELAY(100);
5021 			iptr = ISP_READ(isp, isp->isp_respinrp);
5022 			junk = ISP_READ(isp, BIU_R2HSTSLO);
5023 		} else {
5024 			junk = ISP_READ(isp, BIU_ISR);
5025 		}
5026 		if (optr == iptr) {
5027 			if (IS_23XX(isp) || IS_24XX(isp)) {
5028 				;
5029 			} else {
5030 				sema = ISP_READ(isp, BIU_SEMA);
5031 				mbox = ISP_READ(isp, OUTMAILBOX0);
5032 				if ((sema & 0x3) && (mbox & 0x8000)) {
5033 					goto again;
5034 				}
5035 			}
5036 			isp->isp_intbogus++;
5037 			isp_prt(isp, ISP_LOGDEBUG1, "bogus intr- isr %x (%x) iptr %x optr %x", isr, junk, iptr, optr);
5038 		}
5039 	}
5040 	isp->isp_resodx = iptr;
5041 
5042 	while (optr != iptr) {
5043 		uint8_t qe[QENTRY_LEN];
5044 		ispstatusreq_t *sp = (ispstatusreq_t *) qe;
5045 		isphdr_t *hp;
5046 		int buddaboom, etype, scsi_status, completion_status;
5047 		int req_status_flags, req_state_flags;
5048 		uint8_t *snsp, *resp;
5049 		uint32_t rlen, slen;
5050 		long resid;
5051 		uint16_t oop;
5052 
5053 		hp = (isphdr_t *) ISP_QUEUE_ENTRY(isp->isp_result, optr);
5054 		oop = optr;
5055 		optr = ISP_NXT_QENTRY(optr, RESULT_QUEUE_LEN(isp));
5056 		nlooked++;
5057  read_again:
5058 		buddaboom = req_status_flags = req_state_flags = 0;
5059 		resid = 0L;
5060 
5061 		/*
5062 		 * Synchronize our view of this response queue entry.
5063 		 */
5064 		MEMORYBARRIER(isp, SYNC_RESULT, oop, QENTRY_LEN, -1);
5065 		isp_get_hdr(isp, hp, &sp->req_header);
5066 		etype = sp->req_header.rqs_entry_type;
5067 
5068 		if (IS_24XX(isp) && etype == RQSTYPE_RESPONSE) {
5069 			isp24xx_statusreq_t *sp2 = (isp24xx_statusreq_t *)qe;
5070 			isp_get_24xx_response(isp, (isp24xx_statusreq_t *)hp, sp2);
5071 			if (isp->isp_dblev & ISP_LOGDEBUG1) {
5072 				isp_print_bytes(isp, "Response Queue Entry", QENTRY_LEN, sp2);
5073 			}
5074 			scsi_status = sp2->req_scsi_status;
5075 			completion_status = sp2->req_completion_status;
5076 			req_state_flags = 0;
5077 			resid = sp2->req_resid;
5078 		} else if (etype == RQSTYPE_RESPONSE) {
5079 			isp_get_response(isp, (ispstatusreq_t *) hp, sp);
5080 			if (isp->isp_dblev & ISP_LOGDEBUG1) {
5081 				isp_print_bytes(isp, "Response Queue Entry", QENTRY_LEN, sp);
5082 			}
5083 			scsi_status = sp->req_scsi_status;
5084 			completion_status = sp->req_completion_status;
5085 			req_status_flags = sp->req_status_flags;
5086 			req_state_flags = sp->req_state_flags;
5087 			resid = sp->req_resid;
5088 		} else if (etype == RQSTYPE_RIO1) {
5089 			isp_rio1_t *rio = (isp_rio1_t *) qe;
5090 			isp_get_rio1(isp, (isp_rio1_t *) hp, rio);
5091 			if (isp->isp_dblev & ISP_LOGDEBUG1) {
5092 				isp_print_bytes(isp, "Response Queue Entry", QENTRY_LEN, rio);
5093 			}
5094 			for (i = 0; i < rio->req_header.rqs_seqno; i++) {
5095 				isp_fastpost_complete(isp, rio->req_handles[i]);
5096 			}
5097 			if (isp->isp_fpcchiwater < rio->req_header.rqs_seqno) {
5098 				isp->isp_fpcchiwater = rio->req_header.rqs_seqno;
5099 			}
5100 			ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5101 			continue;
5102 		} else if (etype == RQSTYPE_RIO2) {
5103 			isp_prt(isp, ISP_LOGERR, "dropping RIO2 response\n");
5104 			ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5105 			continue;
5106 		} else {
5107 			/*
5108 			 * Somebody reachable via isp_handle_other_response
5109 			 * may have updated the response queue pointers for
5110 			 * us, so we reload our goal index.
5111 			 */
5112 			int r;
5113 			uint32_t tsto = oop;
5114 			r = isp_handle_other_response(isp, etype, hp, &tsto);
5115 			if (r < 0) {
5116 				goto read_again;
5117 			}
5118 			/*
5119 			 * If somebody updated the output pointer, then reset
5120 			 * optr to be one more than the updated amount.
5121 			 */
5122 			while (tsto != oop) {
5123 				optr = ISP_NXT_QENTRY(tsto,
5124 				    RESULT_QUEUE_LEN(isp));
5125 			}
5126 			if (r > 0) {
5127 				ISP_WRITE(isp, isp->isp_respoutrp, optr);
5128 				ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5129 				continue;
5130 			}
5131 
5132 			/*
5133 			 * After this point, we'll just look at the header as
5134 			 * we don't know how to deal with the rest of the
5135 			 * response.
5136 			 */
5137 
5138 			/*
5139 			 * It really has to be a bounced request just copied
5140 			 * from the request queue to the response queue. If
5141 			 * not, something bad has happened.
5142 			 */
5143 			if (etype != RQSTYPE_REQUEST) {
5144 				isp_prt(isp, ISP_LOGERR, notresp,
5145 				    etype, oop, optr, nlooked);
5146 				isp_print_bytes(isp,
5147 				    "Request Queue Entry", QENTRY_LEN, sp);
5148 				ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5149 				continue;
5150 			}
5151 			buddaboom = 1;
5152 			scsi_status = sp->req_scsi_status;
5153 			completion_status = sp->req_completion_status;
5154 			req_status_flags = sp->req_status_flags;
5155 			req_state_flags = sp->req_state_flags;
5156 			resid = sp->req_resid;
5157 		}
5158 
5159 		if (sp->req_header.rqs_flags & RQSFLAG_MASK) {
5160 			if (sp->req_header.rqs_flags & RQSFLAG_CONTINUATION) {
5161 				isp_print_bytes(isp, "unexpected continuation segment", QENTRY_LEN, sp);
5162 				ISP_WRITE(isp, isp->isp_respoutrp, optr);
5163 				continue;
5164 			}
5165 			if (sp->req_header.rqs_flags & RQSFLAG_FULL) {
5166 				isp_prt(isp, ISP_LOGDEBUG0, "internal queues full");
5167 				/*
5168 				 * We'll synthesize a QUEUE FULL message below.
5169 				 */
5170 			}
5171 			if (sp->req_header.rqs_flags & RQSFLAG_BADHEADER) {
5172 				isp_print_bytes(isp, "bad header flag", QENTRY_LEN, sp);
5173 				buddaboom++;
5174 			}
5175 			if (sp->req_header.rqs_flags & RQSFLAG_BADPACKET) {
5176 				isp_print_bytes(isp, "bad request packet", QENTRY_LEN, sp);
5177 				buddaboom++;
5178 			}
5179 			if (sp->req_header.rqs_flags & RQSFLAG_BADCOUNT) {
5180 				isp_print_bytes(isp, "invalid entry count", QENTRY_LEN, sp);
5181 				buddaboom++;
5182 			}
5183 			if (sp->req_header.rqs_flags & RQSFLAG_BADORDER) {
5184 				isp_print_bytes(isp, "invalid IOCB ordering", QENTRY_LEN, sp);
5185 				ISP_WRITE(isp, isp->isp_respoutrp, optr);
5186 				continue;
5187 			}
5188 		}
5189 
5190 		if (!ISP_VALID_HANDLE(isp, sp->req_handle)) {
5191 			isp_prt(isp, ISP_LOGERR, "bad request handle 0x%x (iocb type 0x%x)", sp->req_handle, etype);
5192 			ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5193 			ISP_WRITE(isp, isp->isp_respoutrp, optr);
5194 			continue;
5195 		}
5196 		xs = isp_find_xs(isp, sp->req_handle);
5197 		if (xs == NULL) {
5198 			uint8_t ts = completion_status & 0xff;
5199 			/*
5200 			 * Only whine if this isn't the expected fallout of
5201 			 * aborting the command or resetting the target.
5202 			 */
5203 			if (etype != RQSTYPE_RESPONSE) {
5204 				isp_prt(isp, ISP_LOGERR, "cannot find handle 0x%x (type 0x%x)", sp->req_handle, etype);
5205 			} else if (ts != RQCS_ABORTED && ts != RQCS_RESET_OCCURRED) {
5206 				isp_prt(isp, ISP_LOGERR, "cannot find handle 0x%x (status 0x%x)", sp->req_handle, ts);
5207 			}
5208 			ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5209 			ISP_WRITE(isp, isp->isp_respoutrp, optr);
5210 			continue;
5211 		}
5212 		if (req_status_flags & RQSTF_BUS_RESET) {
5213 			XS_SETERR(xs, HBA_BUSRESET);
5214 			ISP_SET_SENDMARKER(isp, XS_CHANNEL(xs), 1);
5215 		}
5216 		if (buddaboom) {
5217 			XS_SETERR(xs, HBA_BOTCH);
5218 		}
5219 
5220 		resp = NULL;
5221 		rlen = 0;
5222 		snsp = NULL;
5223 		slen = 0;
5224 		if (IS_24XX(isp) && (scsi_status & (RQCS_RV|RQCS_SV)) != 0) {
5225 			resp = ((isp24xx_statusreq_t *)sp)->req_rsp_sense;
5226 			rlen = ((isp24xx_statusreq_t *)sp)->req_response_len;
5227 		} else if (IS_FC(isp) && (scsi_status & RQCS_RV) != 0) {
5228 			resp = sp->req_response;
5229 			rlen = sp->req_response_len;
5230 		}
5231 		if (IS_FC(isp) && (scsi_status & RQCS_SV) != 0) {
5232 			/*
5233 			 * Fibre Channel F/W doesn't say we got status
5234 			 * if there's Sense Data instead. I guess they
5235 			 * think it goes w/o saying.
5236 			 */
5237 			req_state_flags |= RQSF_GOT_STATUS|RQSF_GOT_SENSE;
5238 			if (IS_24XX(isp)) {
5239 				snsp = ((isp24xx_statusreq_t *)sp)->req_rsp_sense;
5240 				snsp += rlen;
5241 				slen = ((isp24xx_statusreq_t *)sp)->req_sense_len;
5242 			} else {
5243 				snsp = sp->req_sense_data;
5244 				slen = sp->req_sense_len;
5245 			}
5246 		} else if (IS_SCSI(isp) && (req_state_flags & RQSF_GOT_SENSE)) {
5247 			snsp = sp->req_sense_data;
5248 			slen = sp->req_sense_len;
5249 		}
5250 		if (req_state_flags & RQSF_GOT_STATUS) {
5251 			*XS_STSP(xs) = scsi_status & 0xff;
5252 		}
5253 
5254 		switch (etype) {
5255 		case RQSTYPE_RESPONSE:
5256 			if (resp && rlen >= 4 && resp[FCP_RSPNS_CODE_OFFSET] != 0) {
5257 				const char *ptr;
5258 				char lb[64];
5259 				const char *rnames[6] = {
5260 					"Task Management Function Done",
5261 					"Data Length Differs From Burst Length",
5262 					"Invalid FCP Cmnd",
5263 					"FCP DATA RO mismatch with FCP DATA_XFR_RDY RO",
5264 					"Task Management Function Rejected",
5265 					"Task Management Function Failed",
5266 				};
5267 				if (resp[FCP_RSPNS_CODE_OFFSET] > 5) {
5268 					ISP_SNPRINTF(lb, sizeof lb, "Unknown FCP Response Code 0x%x", resp[FCP_RSPNS_CODE_OFFSET]);
5269 					ptr = lb;
5270 				} else {
5271 					ptr = rnames[resp[FCP_RSPNS_CODE_OFFSET]];
5272 				}
5273 				isp_xs_prt(isp, xs, ISP_LOGWARN, "FCP RESPONSE, LENGTH %u: %s CDB0=0x%02x", rlen, ptr, XS_CDBP(xs)[0] & 0xff);
5274 				if (resp[FCP_RSPNS_CODE_OFFSET] != 0) {
5275 					XS_SETERR(xs, HBA_BOTCH);
5276 				}
5277 			}
5278 			if (IS_24XX(isp)) {
5279 				isp_parse_status_24xx(isp, (isp24xx_statusreq_t *)sp, xs, &resid);
5280 			} else {
5281 				isp_parse_status(isp, (void *)sp, xs, &resid);
5282 			}
5283 			if ((XS_NOERR(xs) || XS_ERR(xs) == HBA_NOERROR) && (*XS_STSP(xs) == SCSI_BUSY)) {
5284 				XS_SETERR(xs, HBA_TGTBSY);
5285 			}
5286 			if (IS_SCSI(isp)) {
5287 				XS_SET_RESID(xs, resid);
5288 				/*
5289 				 * A new synchronous rate was negotiated for
5290 				 * this target. Mark state such that we'll go
5291 				 * look up that which has changed later.
5292 				 */
5293 				if (req_status_flags & RQSTF_NEGOTIATION) {
5294 					int t = XS_TGT(xs);
5295 					sdparam *sdp = SDPARAM(isp, XS_CHANNEL(xs));
5296 					sdp->isp_devparam[t].dev_refresh = 1;
5297 					sdp->update = 1;
5298 				}
5299 			} else {
5300 				if (req_status_flags & RQSF_XFER_COMPLETE) {
5301 					XS_SET_RESID(xs, 0);
5302 				} else if (scsi_status & RQCS_RESID) {
5303 					XS_SET_RESID(xs, resid);
5304 				} else {
5305 					XS_SET_RESID(xs, 0);
5306 				}
5307 			}
5308 			if (snsp && slen) {
5309 				XS_SAVE_SENSE(xs, snsp, slen);
5310 			} else if ((req_status_flags & RQSF_GOT_STATUS) && (scsi_status & 0xff) == SCSI_CHECK && IS_FC(isp)) {
5311 				isp_prt(isp, ISP_LOGWARN, "CHECK CONDITION w/o sense data for CDB=0x%x", XS_CDBP(xs)[0] & 0xff);
5312 				isp_print_bytes(isp, "CC with no Sense", QENTRY_LEN, qe);
5313 			}
5314 			isp_prt(isp, ISP_LOGDEBUG2, "asked for %ld got raw resid %ld settled for %ld", (long) XS_XFRLEN(xs), resid, (long) XS_GET_RESID(xs));
5315 			break;
5316 		case RQSTYPE_REQUEST:
5317 		case RQSTYPE_A64:
5318 		case RQSTYPE_T2RQS:
5319 		case RQSTYPE_T3RQS:
5320 		case RQSTYPE_T7RQS:
5321 			if (!IS_24XX(isp) && (sp->req_header.rqs_flags & RQSFLAG_FULL)) {
5322 				/*
5323 				 * Force Queue Full status.
5324 				 */
5325 				*XS_STSP(xs) = SCSI_QFULL;
5326 				XS_SETERR(xs, HBA_NOERROR);
5327 			} else if (XS_NOERR(xs)) {
5328 				XS_SETERR(xs, HBA_BOTCH);
5329 			}
5330 			XS_SET_RESID(xs, XS_XFRLEN(xs));
5331 			break;
5332 		default:
5333 			isp_print_bytes(isp, "Unhandled Response Type", QENTRY_LEN, qe);
5334 			if (XS_NOERR(xs)) {
5335 				XS_SETERR(xs, HBA_BOTCH);
5336 			}
5337 			break;
5338 		}
5339 
5340 		/*
5341 		 * Free any DMA resources. As a side effect, this may
5342 		 * also do any cache flushing necessary for data coherence.
5343 		 */
5344 		if (XS_XFRLEN(xs)) {
5345 			ISP_DMAFREE(isp, xs, sp->req_handle);
5346 		}
5347 		isp_destroy_handle(isp, sp->req_handle);
5348 
5349 		if (((isp->isp_dblev & (ISP_LOGDEBUG1|ISP_LOGDEBUG2|ISP_LOGDEBUG3))) ||
5350 		    ((isp->isp_dblev & (ISP_LOGDEBUG0|ISP_LOG_CWARN) && ((!XS_NOERR(xs)) || (*XS_STSP(xs) != SCSI_GOOD))))) {
5351 			isp_prt_endcmd(isp, xs);
5352 		}
5353 		if (isp->isp_nactive > 0) {
5354 		    isp->isp_nactive--;
5355 		}
5356 		complist[ndone++] = xs;	/* defer completion call until later */
5357 		ISP_MEMZERO(hp, QENTRY_LEN);	/* PERF */
5358 		if (ndone == MAX_REQUESTQ_COMPLETIONS) {
5359 			break;
5360 		}
5361 	}
5362 
5363 	/*
5364 	 * If we looked at any commands, then it's valid to find out
5365 	 * what the outpointer is. It also is a trigger to update the
5366 	 * ISP's notion of what we've seen so far.
5367 	 */
5368 	if (nlooked) {
5369 		ISP_WRITE(isp, isp->isp_respoutrp, optr);
5370 		/*
5371 		 * While we're at it, read the requst queue out pointer.
5372 		 */
5373 		isp->isp_reqodx = ISP_READ(isp, isp->isp_rqstoutrp);
5374 		if (isp->isp_rscchiwater < ndone) {
5375 			isp->isp_rscchiwater = ndone;
5376 		}
5377 	}
5378 
5379 out:
5380 
5381 	if (IS_24XX(isp)) {
5382 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_CLEAR_RISC_INT);
5383 	} else {
5384 		ISP_WRITE(isp, HCCR, HCCR_CMD_CLEAR_RISC_INT);
5385 		ISP_WRITE(isp, BIU_SEMA, 0);
5386 	}
5387 
5388 	isp->isp_residx = optr;
5389 	for (i = 0; i < ndone; i++) {
5390 		xs = complist[i];
5391 		if (xs) {
5392 			isp->isp_rsltccmplt++;
5393 			isp_done(xs);
5394 		}
5395 	}
5396 }
5397 
5398 /*
5399  * Support routines.
5400  */
5401 
5402 void
5403 isp_prt_endcmd(ispsoftc_t *isp, XS_T *xs)
5404 {
5405 	char cdbstr[16 * 5 + 1];
5406 	int i, lim;
5407 
5408 	lim = XS_CDBLEN(xs) > 16? 16 : XS_CDBLEN(xs);
5409 	ISP_SNPRINTF(cdbstr, sizeof (cdbstr), "0x%02x ", XS_CDBP(xs)[0]);
5410 	for (i = 1; i < lim; i++) {
5411 		ISP_SNPRINTF(cdbstr, sizeof (cdbstr), "%s0x%02x ", cdbstr, XS_CDBP(xs)[i]);
5412 	}
5413 	if (XS_SENSE_VALID(xs)) {
5414 		isp_xs_prt(isp, xs, ISP_LOGALL, "FIN dl%d resid %ld CDB=%s KEY/ASC/ASCQ=XXX/XXX/XXX",
5415 		    XS_XFRLEN(xs), (long) XS_GET_RESID(xs), cdbstr /* XXX swildner , XS_SNSKEY(xs), XS_SNSASC(xs), XS_SNSASCQ(xs) */);
5416 	} else {
5417 		isp_xs_prt(isp, xs, ISP_LOGALL, "FIN dl%d resid %ld CDB=%s STS 0x%x XS_ERR=0x%x", XS_XFRLEN(xs), (long) XS_GET_RESID(xs), cdbstr, *XS_STSP(xs), XS_ERR(xs));
5418 	}
5419 }
5420 
5421 /*
5422  * Parse an ASYNC mailbox complete
5423  *
5424  * Return non-zero if the event has been acknowledged.
5425  */
5426 static int
5427 isp_parse_async(ispsoftc_t *isp, uint16_t mbox)
5428 {
5429 	int acked = 0;
5430 	uint32_t h1 = 0, h2 = 0;
5431 	uint16_t chan = 0;
5432 
5433 	/*
5434 	 * Pick up the channel, but not if this is a ASYNC_RIO32_2,
5435 	 * where Mailboxes 6/7 have the second handle.
5436 	 */
5437 	if (mbox != ASYNC_RIO32_2) {
5438 		if (IS_DUALBUS(isp)) {
5439 			chan = ISP_READ(isp, OUTMAILBOX6);
5440 		}
5441 	}
5442 	isp_prt(isp, ISP_LOGDEBUG2, "Async Mbox 0x%x", mbox);
5443 
5444 	switch (mbox) {
5445 	case ASYNC_BUS_RESET:
5446 		ISP_SET_SENDMARKER(isp, chan, 1);
5447 #ifdef	ISP_TARGET_MODE
5448 		if (isp_target_async(isp, chan, mbox)) {
5449 			acked = 1;
5450 		}
5451 #endif
5452 		isp_async(isp, ISPASYNC_BUS_RESET, chan);
5453 		break;
5454 	case ASYNC_SYSTEM_ERROR:
5455 		isp->isp_dead = 1;
5456 		isp->isp_state = ISP_CRASHED;
5457 		/*
5458 		 * Were we waiting for a mailbox command to complete?
5459 		 * If so, it's dead, so wake up the waiter.
5460 		 */
5461 		if (isp->isp_mboxbsy) {
5462 			isp->isp_obits = 1;
5463 			isp->isp_mboxtmp[0] = MBOX_HOST_INTERFACE_ERROR;
5464 			MBOX_NOTIFY_COMPLETE(isp);
5465 		}
5466 		/*
5467 		 * It's up to the handler for isp_async to reinit stuff and
5468 		 * restart the firmware
5469 		 */
5470 		isp_async(isp, ISPASYNC_FW_CRASH);
5471 		acked = 1;
5472 		break;
5473 
5474 	case ASYNC_RQS_XFER_ERR:
5475 		isp_prt(isp, ISP_LOGERR, "Request Queue Transfer Error");
5476 		break;
5477 
5478 	case ASYNC_RSP_XFER_ERR:
5479 		isp_prt(isp, ISP_LOGERR, "Response Queue Transfer Error");
5480 		break;
5481 
5482 	case ASYNC_QWAKEUP:
5483 		/*
5484 		 * We've just been notified that the Queue has woken up.
5485 		 * We don't need to be chatty about this- just unlatch things
5486 		 * and move on.
5487 		 */
5488 		mbox = ISP_READ(isp, isp->isp_rqstoutrp);
5489 		break;
5490 
5491 	case ASYNC_TIMEOUT_RESET:
5492 		isp_prt(isp, ISP_LOGWARN, "timeout initiated SCSI bus reset of chan %d", chan);
5493 		ISP_SET_SENDMARKER(isp, chan, 1);
5494 #ifdef	ISP_TARGET_MODE
5495 		if (isp_target_async(isp, chan, mbox)) {
5496 			acked = 1;
5497 		}
5498 #endif
5499 		break;
5500 
5501 	case ASYNC_DEVICE_RESET:
5502 		isp_prt(isp, ISP_LOGINFO, "device reset on chan %d", chan);
5503 		ISP_SET_SENDMARKER(isp, chan, 1);
5504 #ifdef	ISP_TARGET_MODE
5505 		if (isp_target_async(isp, chan, mbox)) {
5506 			acked = 1;
5507 		}
5508 #endif
5509 		break;
5510 
5511 	case ASYNC_EXTMSG_UNDERRUN:
5512 		isp_prt(isp, ISP_LOGWARN, "extended message underrun");
5513 		break;
5514 
5515 	case ASYNC_SCAM_INT:
5516 		isp_prt(isp, ISP_LOGINFO, "SCAM interrupt");
5517 		break;
5518 
5519 	case ASYNC_HUNG_SCSI:
5520 		isp_prt(isp, ISP_LOGERR, "stalled SCSI Bus after DATA Overrun");
5521 		/* XXX: Need to issue SCSI reset at this point */
5522 		break;
5523 
5524 	case ASYNC_KILLED_BUS:
5525 		isp_prt(isp, ISP_LOGERR, "SCSI Bus reset after DATA Overrun");
5526 		break;
5527 
5528 	case ASYNC_BUS_TRANSIT:
5529 		mbox = ISP_READ(isp, OUTMAILBOX2);
5530 		switch (mbox & SXP_PINS_MODE_MASK) {
5531 		case SXP_PINS_LVD_MODE:
5532 			isp_prt(isp, ISP_LOGINFO, "Transition to LVD mode");
5533 			SDPARAM(isp, chan)->isp_diffmode = 0;
5534 			SDPARAM(isp, chan)->isp_ultramode = 0;
5535 			SDPARAM(isp, chan)->isp_lvdmode = 1;
5536 			break;
5537 		case SXP_PINS_HVD_MODE:
5538 			isp_prt(isp, ISP_LOGINFO,
5539 			    "Transition to Differential mode");
5540 			SDPARAM(isp, chan)->isp_diffmode = 1;
5541 			SDPARAM(isp, chan)->isp_ultramode = 0;
5542 			SDPARAM(isp, chan)->isp_lvdmode = 0;
5543 			break;
5544 		case SXP_PINS_SE_MODE:
5545 			isp_prt(isp, ISP_LOGINFO,
5546 			    "Transition to Single Ended mode");
5547 			SDPARAM(isp, chan)->isp_diffmode = 0;
5548 			SDPARAM(isp, chan)->isp_ultramode = 1;
5549 			SDPARAM(isp, chan)->isp_lvdmode = 0;
5550 			break;
5551 		default:
5552 			isp_prt(isp, ISP_LOGWARN,
5553 			    "Transition to Unknown Mode 0x%x", mbox);
5554 			break;
5555 		}
5556 		/*
5557 		 * XXX: Set up to renegotiate again!
5558 		 */
5559 		/* Can only be for a 1080... */
5560 		ISP_SET_SENDMARKER(isp, chan, 1);
5561 		break;
5562 
5563 	case ASYNC_CMD_CMPLT:
5564 	case ASYNC_RIO32_1:
5565 		if (!IS_ULTRA3(isp)) {
5566 			isp_prt(isp, ISP_LOGERR, "unexpected fast posting completion");
5567 			break;
5568 		}
5569 		/* FALLTHROUGH */
5570 		h1 = (ISP_READ(isp, OUTMAILBOX2) << 16) | ISP_READ(isp, OUTMAILBOX1);
5571 		break;
5572 
5573 	case ASYNC_RIO32_2:
5574 		h1 = (ISP_READ(isp, OUTMAILBOX2) << 16) | ISP_READ(isp, OUTMAILBOX1);
5575 		h2 = (ISP_READ(isp, OUTMAILBOX7) << 16) | ISP_READ(isp, OUTMAILBOX6);
5576 		break;
5577 
5578 	case ASYNC_RIO16_5:
5579 	case ASYNC_RIO16_4:
5580 	case ASYNC_RIO16_3:
5581 	case ASYNC_RIO16_2:
5582 	case ASYNC_RIO16_1:
5583 		isp_prt(isp, ISP_LOGERR, "unexpected 16 bit RIO handle");
5584 		break;
5585 	default:
5586 		isp_prt(isp, ISP_LOGWARN, "%s: unhandled async code 0x%x", __func__, mbox);
5587 		break;
5588 	}
5589 
5590 	if (h1 || h2) {
5591 		isp_prt(isp, ISP_LOGDEBUG3, "fast post/rio completion of 0x%08x", h1);
5592 		isp_fastpost_complete(isp, h1);
5593 		if (h2) {
5594 			isp_prt(isp, ISP_LOGDEBUG3, "fast post/rio completion of 0x%08x", h2);
5595 			isp_fastpost_complete(isp, h2);
5596 			if (isp->isp_fpcchiwater < 2) {
5597 				isp->isp_fpcchiwater = 2;
5598 			}
5599 		} else {
5600 			if (isp->isp_fpcchiwater < 1) {
5601 				isp->isp_fpcchiwater = 1;
5602 			}
5603 		}
5604 	} else {
5605 		isp->isp_intoasync++;
5606 	}
5607 	return (acked);
5608 }
5609 
5610 #define	GET_24XX_BUS(isp, chan, msg)										\
5611 	if (IS_24XX(isp)) {											\
5612 		chan = ISP_READ(isp, OUTMAILBOX3) & 0xff;							\
5613 		if (chan >= isp->isp_nchan) {									\
5614 			isp_prt(isp, ISP_LOGERR, "bogus channel %u for %s at line %d",	chan, msg, __LINE__);	\
5615 			break;											\
5616 		}												\
5617 	}
5618 
5619 
5620 static int
5621 isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
5622 {
5623 	int acked = 0;
5624 	uint16_t chan;
5625 
5626 	if (IS_DUALBUS(isp)) {
5627 		chan = ISP_READ(isp, OUTMAILBOX6);
5628 	} else {
5629 		chan = 0;
5630 	}
5631 	isp_prt(isp, ISP_LOGDEBUG2, "Async Mbox 0x%x", mbox);
5632 
5633 	switch (mbox) {
5634 	case ASYNC_SYSTEM_ERROR:
5635 		isp->isp_dead = 1;
5636 		isp->isp_state = ISP_CRASHED;
5637 		FCPARAM(isp, chan)->isp_loopstate = LOOP_NIL;
5638 		FCPARAM(isp, chan)->isp_fwstate = FW_CONFIG_WAIT;
5639 		/*
5640 		 * Were we waiting for a mailbox command to complete?
5641 		 * If so, it's dead, so wake up the waiter.
5642 		 */
5643 		if (isp->isp_mboxbsy) {
5644 			isp->isp_obits = 1;
5645 			isp->isp_mboxtmp[0] = MBOX_HOST_INTERFACE_ERROR;
5646 			MBOX_NOTIFY_COMPLETE(isp);
5647 		}
5648 		/*
5649 		 * It's up to the handler for isp_async to reinit stuff and
5650 		 * restart the firmware
5651 		 */
5652 		isp_async(isp, ISPASYNC_FW_CRASH);
5653 		acked = 1;
5654 		break;
5655 
5656 	case ASYNC_RQS_XFER_ERR:
5657 		isp_prt(isp, ISP_LOGERR, "Request Queue Transfer Error");
5658 		break;
5659 
5660 	case ASYNC_RSP_XFER_ERR:
5661 		isp_prt(isp, ISP_LOGERR, "Response Queue Transfer Error");
5662 		break;
5663 
5664 	case ASYNC_QWAKEUP:
5665 #ifdef	ISP_TARGET_MODE
5666 		if (IS_24XX(isp)) {
5667 			isp_prt(isp, ISP_LOGERR, "ATIO Queue Transfer Error");
5668 			break;
5669 		}
5670 #endif
5671 		isp_prt(isp, ISP_LOGERR, "%s: unexpected ASYNC_QWAKEUP code", __func__);
5672 		break;
5673 
5674 	case ASYNC_CMD_CMPLT:
5675 		isp_fastpost_complete(isp, (ISP_READ(isp, OUTMAILBOX2) << 16) | ISP_READ(isp, OUTMAILBOX1));
5676 		if (isp->isp_fpcchiwater < 1) {
5677 			isp->isp_fpcchiwater = 1;
5678 		}
5679 		break;
5680 
5681 	case ASYNC_RIOZIO_STALL:
5682 		break;
5683 
5684 	case ASYNC_CTIO_DONE:
5685 #ifdef	ISP_TARGET_MODE
5686 		if (isp_target_async(isp, (ISP_READ(isp, OUTMAILBOX2) << 16) | ISP_READ(isp, OUTMAILBOX1), mbox)) {
5687 			acked = 1;
5688 		} else {
5689 			isp->isp_fphccmplt++;
5690 		}
5691 #else
5692 		isp_prt(isp, ISP_LOGWARN, "unexpected ASYNC CTIO done");
5693 #endif
5694 		break;
5695 	case ASYNC_LIP_ERROR:
5696 	case ASYNC_LIP_F8:
5697 	case ASYNC_LIP_OCCURRED:
5698 	case ASYNC_PTPMODE:
5699 		/*
5700 		 * These are broadcast events that have to be sent across
5701 		 * all active channels.
5702 		 */
5703 		for (chan = 0; chan < isp->isp_nchan; chan++) {
5704 			fcparam *fcp = FCPARAM(isp, chan);
5705 			int topo = fcp->isp_topo;
5706 
5707 			if (fcp->role == ISP_ROLE_NONE) {
5708 				continue;
5709 			}
5710 
5711 			fcp->isp_fwstate = FW_CONFIG_WAIT;
5712 			fcp->isp_loopstate = LOOP_LIP_RCVD;
5713 			ISP_SET_SENDMARKER(isp, chan, 1);
5714 			ISP_MARK_PORTDB(isp, chan, 1);
5715 			isp_async(isp, ISPASYNC_LIP, chan);
5716 #ifdef	ISP_TARGET_MODE
5717 			if (isp_target_async(isp, chan, mbox)) {
5718 				acked = 1;
5719 			}
5720 #endif
5721 			/*
5722 			 * We've had problems with data corruption occuring on
5723 			 * commands that complete (with no apparent error) after
5724 			 * we receive a LIP. This has been observed mostly on
5725 			 * Local Loop topologies. To be safe, let's just mark
5726 			 * all active initiator commands as dead.
5727 			 */
5728 			if (topo == TOPO_NL_PORT || topo == TOPO_FL_PORT) {
5729 				int i, j;
5730 				for (i = j = 0; i < isp->isp_maxcmds; i++) {
5731 					XS_T *xs;
5732 					isp_hdl_t *hdp;
5733 
5734 					hdp = &isp->isp_xflist[i];
5735 					if (ISP_H2HT(hdp->handle) != ISP_HANDLE_INITIATOR) {
5736 						continue;
5737 					}
5738 					xs = hdp->cmd;
5739 					if (XS_CHANNEL(xs) != chan) {
5740 						continue;
5741 					}
5742 					j++;
5743 					XS_SETERR(xs, HBA_BUSRESET);
5744 				}
5745 				if (j) {
5746 					isp_prt(isp, ISP_LOGERR, lipd, chan, j);
5747 				}
5748 			}
5749 		}
5750 		break;
5751 
5752 	case ASYNC_LOOP_UP:
5753 		/*
5754 		 * This is a broadcast event that has to be sent across
5755 		 * all active channels.
5756 		 */
5757 		for (chan = 0; chan < isp->isp_nchan; chan++) {
5758 			fcparam *fcp = FCPARAM(isp, chan);
5759 
5760 			if (fcp->role == ISP_ROLE_NONE) {
5761 				continue;
5762 			}
5763 
5764 			ISP_SET_SENDMARKER(isp, chan, 1);
5765 
5766 			fcp->isp_fwstate = FW_CONFIG_WAIT;
5767 			fcp->isp_loopstate = LOOP_LIP_RCVD;
5768 			ISP_MARK_PORTDB(isp, chan, 1);
5769 			isp_async(isp, ISPASYNC_LOOP_UP, chan);
5770 #ifdef	ISP_TARGET_MODE
5771 			if (isp_target_async(isp, chan, mbox)) {
5772 				acked = 1;
5773 			}
5774 #endif
5775 		}
5776 		break;
5777 
5778 	case ASYNC_LOOP_DOWN:
5779 		/*
5780 		 * This is a broadcast event that has to be sent across
5781 		 * all active channels.
5782 		 */
5783 		for (chan = 0; chan < isp->isp_nchan; chan++) {
5784 			fcparam *fcp = FCPARAM(isp, chan);
5785 
5786 			if (fcp->role == ISP_ROLE_NONE) {
5787 				continue;
5788 			}
5789 
5790 			ISP_SET_SENDMARKER(isp, chan, 1);
5791 			fcp->isp_fwstate = FW_CONFIG_WAIT;
5792 			fcp->isp_loopstate = LOOP_NIL;
5793 			ISP_MARK_PORTDB(isp, chan, 1);
5794 			isp_async(isp, ISPASYNC_LOOP_DOWN, chan);
5795 #ifdef	ISP_TARGET_MODE
5796 			if (isp_target_async(isp, chan, mbox)) {
5797 				acked = 1;
5798 			}
5799 #endif
5800 		}
5801 		break;
5802 
5803 	case ASYNC_LOOP_RESET:
5804 		/*
5805 		 * This is a broadcast event that has to be sent across
5806 		 * all active channels.
5807 		 */
5808 		for (chan = 0; chan < isp->isp_nchan; chan++) {
5809 			fcparam *fcp = FCPARAM(isp, chan);
5810 
5811 			if (fcp->role == ISP_ROLE_NONE) {
5812 				continue;
5813 			}
5814 
5815 			ISP_SET_SENDMARKER(isp, chan, 1);
5816 			fcp->isp_fwstate = FW_CONFIG_WAIT;
5817 			fcp->isp_loopstate = LOOP_NIL;
5818 			ISP_MARK_PORTDB(isp, chan, 1);
5819 			isp_async(isp, ISPASYNC_LOOP_RESET, chan);
5820 #ifdef	ISP_TARGET_MODE
5821 			if (isp_target_async(isp, chan, mbox)) {
5822 				acked = 1;
5823 			}
5824 #endif
5825 		}
5826 		break;
5827 
5828 	case ASYNC_PDB_CHANGED:
5829 	{
5830 		int nphdl, nlstate, reason;
5831 		/*
5832 		 * We *should* get a channel out of the 24XX, but we don't seem
5833 		 * to get more than a PDB CHANGED on channel 0, so turn it into
5834 		 * a broadcast event.
5835 		 */
5836 		if (IS_24XX(isp)) {
5837 			nphdl = ISP_READ(isp, OUTMAILBOX1);
5838 			nlstate = ISP_READ(isp, OUTMAILBOX2);
5839 			reason = ISP_READ(isp, OUTMAILBOX3) >> 8;
5840 		} else {
5841 			nphdl = NIL_HANDLE;
5842 			nlstate = reason = 0;
5843 		}
5844 		for (chan = 0; chan < isp->isp_nchan; chan++) {
5845 			fcparam *fcp = FCPARAM(isp, chan);
5846 
5847 			if (fcp->role == ISP_ROLE_NONE) {
5848 				continue;
5849 			}
5850 			ISP_SET_SENDMARKER(isp, chan, 1);
5851 			fcp->isp_loopstate = LOOP_PDB_RCVD;
5852 			ISP_MARK_PORTDB(isp, chan, 1);
5853 			isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_PDB, nphdl, nlstate, reason);
5854 		}
5855 		break;
5856 	}
5857 	case ASYNC_CHANGE_NOTIFY:
5858 	{
5859 		int lochan, hichan;
5860 
5861 		if (ISP_FW_NEWER_THAN(isp, 4, 0, 25) && ISP_CAP_MULTI_ID(isp)) {
5862 			GET_24XX_BUS(isp, chan, "ASYNC_CHANGE_NOTIFY");
5863 			lochan = chan;
5864 			hichan = chan + 1;
5865 		} else {
5866 			lochan = 0;
5867 			hichan = isp->isp_nchan;
5868 		}
5869 		for (chan = lochan; chan < hichan; chan++) {
5870 			fcparam *fcp = FCPARAM(isp, chan);
5871 
5872 			if (fcp->role == ISP_ROLE_NONE) {
5873 				continue;
5874 			}
5875 
5876 			if (fcp->isp_topo == TOPO_F_PORT) {
5877 				fcp->isp_loopstate = LOOP_LSCAN_DONE;
5878 			} else {
5879 				fcp->isp_loopstate = LOOP_PDB_RCVD;
5880 			}
5881 			ISP_MARK_PORTDB(isp, chan, 1);
5882 			isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_SNS);
5883 		}
5884 		break;
5885 	}
5886 
5887 	case ASYNC_CONNMODE:
5888 		/*
5889 		 * This only applies to 2100 amd 2200 cards
5890 		 */
5891 		if (!IS_2200(isp) && !IS_2100(isp)) {
5892 			isp_prt(isp, ISP_LOGWARN, "bad card for ASYNC_CONNMODE event");
5893 			break;
5894 		}
5895 		chan = 0;
5896 		mbox = ISP_READ(isp, OUTMAILBOX1);
5897 		ISP_MARK_PORTDB(isp, chan, 1);
5898 		switch (mbox) {
5899 		case ISP_CONN_LOOP:
5900 			isp_prt(isp, ISP_LOGINFO,
5901 			    "Point-to-Point -> Loop mode");
5902 			break;
5903 		case ISP_CONN_PTP:
5904 			isp_prt(isp, ISP_LOGINFO,
5905 			    "Loop -> Point-to-Point mode");
5906 			break;
5907 		case ISP_CONN_BADLIP:
5908 			isp_prt(isp, ISP_LOGWARN,
5909 			    "Point-to-Point -> Loop mode (BAD LIP)");
5910 			break;
5911 		case ISP_CONN_FATAL:
5912 			isp->isp_dead = 1;
5913 			isp->isp_state = ISP_CRASHED;
5914 			isp_prt(isp, ISP_LOGERR, "FATAL CONNECTION ERROR");
5915 			isp_async(isp, ISPASYNC_FW_CRASH);
5916 			return (-1);
5917 		case ISP_CONN_LOOPBACK:
5918 			isp_prt(isp, ISP_LOGWARN,
5919 			    "Looped Back in Point-to-Point mode");
5920 			break;
5921 		default:
5922 			isp_prt(isp, ISP_LOGWARN,
5923 			    "Unknown connection mode (0x%x)", mbox);
5924 			break;
5925 		}
5926 		isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_OTHER);
5927 		FCPARAM(isp, chan)->sendmarker = 1;
5928 		FCPARAM(isp, chan)->isp_fwstate = FW_CONFIG_WAIT;
5929 		FCPARAM(isp, chan)->isp_loopstate = LOOP_LIP_RCVD;
5930 		break;
5931 
5932 	case ASYNC_RCV_ERR:
5933 		if (IS_24XX(isp)) {
5934 			isp_prt(isp, ISP_LOGWARN, "Receive Error");
5935 		} else {
5936 			isp_prt(isp, ISP_LOGWARN, "unexpected ASYNC_RCV_ERR");
5937 		}
5938 		break;
5939 	case ASYNC_RJT_SENT:	/* same as ASYNC_QFULL_SENT */
5940 		if (IS_24XX(isp)) {
5941 			isp_prt(isp, ISP_LOGTDEBUG0, "LS_RJT sent");
5942 			break;
5943 		} else if (IS_2200(isp)) {
5944 			isp_prt(isp, ISP_LOGTDEBUG0, "QFULL sent");
5945 			break;
5946 		}
5947 		/* FALLTHROUGH */
5948 	default:
5949 		isp_prt(isp, ISP_LOGWARN, "Unknown Async Code 0x%x", mbox);
5950 		break;
5951 	}
5952 	if (mbox != ASYNC_CTIO_DONE && mbox != ASYNC_CMD_CMPLT) {
5953 		isp->isp_intoasync++;
5954 	}
5955 	return (acked);
5956 }
5957 
5958 /*
5959  * Handle other response entries. A pointer to the request queue output
5960  * index is here in case we want to eat several entries at once, although
5961  * this is not used currently.
5962  */
5963 
5964 static int
5965 isp_handle_other_response(ispsoftc_t *isp, int type, isphdr_t *hp, uint32_t *optrp)
5966 {
5967 	switch (type) {
5968 	case RQSTYPE_STATUS_CONT:
5969 		isp_prt(isp, ISP_LOGDEBUG0, "Ignored Continuation Response");
5970 		return (1);
5971 	case RQSTYPE_MARKER:
5972 		isp_prt(isp, ISP_LOGDEBUG0, "Marker Response");
5973 		return (1);
5974 	case RQSTYPE_ATIO:
5975 	case RQSTYPE_CTIO:
5976 	case RQSTYPE_ENABLE_LUN:
5977 	case RQSTYPE_MODIFY_LUN:
5978 	case RQSTYPE_NOTIFY:
5979 	case RQSTYPE_NOTIFY_ACK:
5980 	case RQSTYPE_CTIO1:
5981 	case RQSTYPE_ATIO2:
5982 	case RQSTYPE_CTIO2:
5983 	case RQSTYPE_CTIO3:
5984 	case RQSTYPE_CTIO7:
5985 	case RQSTYPE_ABTS_RCVD:
5986 	case RQSTYPE_ABTS_RSP:
5987 		isp->isp_rsltccmplt++;	/* count as a response completion */
5988 #ifdef	ISP_TARGET_MODE
5989 		if (isp_target_notify(isp, (ispstatusreq_t *) hp, optrp)) {
5990 			return (1);
5991 		}
5992 #endif
5993 		/* FALLTHROUGH */
5994 	case RQSTYPE_RPT_ID_ACQ:
5995 		if (IS_24XX(isp)) {
5996 			isp_ridacq_t rid;
5997 			isp_get_ridacq(isp, (isp_ridacq_t *)hp, &rid);
5998 			if (rid.ridacq_format == 0) {
5999 			}
6000 			return (1);
6001 		}
6002 		/* FALLTHROUGH */
6003 	case RQSTYPE_REQUEST:
6004 	default:
6005 		ISP_DELAY(100);
6006 		if (type != isp_get_response_type(isp, hp)) {
6007 			/*
6008 			 * This is questionable- we're just papering over
6009 			 * something we've seen on SMP linux in target
6010 			 * mode- we don't really know what's happening
6011 			 * here that causes us to think we've gotten
6012 			 * an entry, but that either the entry isn't
6013 			 * filled out yet or our CPU read data is stale.
6014 			 */
6015 			isp_prt(isp, ISP_LOGINFO,
6016 				"unstable type in response queue");
6017 			return (-1);
6018 		}
6019 		isp_prt(isp, ISP_LOGWARN, "Unhandled Response Type 0x%x",
6020 		    isp_get_response_type(isp, hp));
6021 		return (0);
6022 	}
6023 }
6024 
6025 static void
6026 isp_parse_status(ispsoftc_t *isp, ispstatusreq_t *sp, XS_T *xs, long *rp)
6027 {
6028 	switch (sp->req_completion_status & 0xff) {
6029 	case RQCS_COMPLETE:
6030 		if (XS_NOERR(xs)) {
6031 			XS_SETERR(xs, HBA_NOERROR);
6032 		}
6033 		return;
6034 
6035 	case RQCS_INCOMPLETE:
6036 		if ((sp->req_state_flags & RQSF_GOT_TARGET) == 0) {
6037 			isp_xs_prt(isp, xs, ISP_LOGDEBUG1, "Selection Timeout");
6038 			if (XS_NOERR(xs)) {
6039 				XS_SETERR(xs, HBA_SELTIMEOUT);
6040 				*rp = XS_XFRLEN(xs);
6041 			}
6042 			return;
6043 		}
6044 		isp_xs_prt(isp, xs, ISP_LOGERR, "Command Incomplete, state 0x%x", sp->req_state_flags);
6045 		break;
6046 
6047 	case RQCS_DMA_ERROR:
6048 		isp_xs_prt(isp, xs, ISP_LOGERR, "DMA Error");
6049 		*rp = XS_XFRLEN(xs);
6050 		break;
6051 
6052 	case RQCS_TRANSPORT_ERROR:
6053 	{
6054 		char buf[172];
6055 		ISP_SNPRINTF(buf, sizeof (buf), "states=>");
6056 		if (sp->req_state_flags & RQSF_GOT_BUS) {
6057 			ISP_SNPRINTF(buf, sizeof (buf), "%s GOT_BUS", buf);
6058 		}
6059 		if (sp->req_state_flags & RQSF_GOT_TARGET) {
6060 			ISP_SNPRINTF(buf, sizeof (buf), "%s GOT_TGT", buf);
6061 		}
6062 		if (sp->req_state_flags & RQSF_SENT_CDB) {
6063 			ISP_SNPRINTF(buf, sizeof (buf), "%s SENT_CDB", buf);
6064 		}
6065 		if (sp->req_state_flags & RQSF_XFRD_DATA) {
6066 			ISP_SNPRINTF(buf, sizeof (buf), "%s XFRD_DATA", buf);
6067 		}
6068 		if (sp->req_state_flags & RQSF_GOT_STATUS) {
6069 			ISP_SNPRINTF(buf, sizeof (buf), "%s GOT_STS", buf);
6070 		}
6071 		if (sp->req_state_flags & RQSF_GOT_SENSE) {
6072 			ISP_SNPRINTF(buf, sizeof (buf), "%s GOT_SNS", buf);
6073 		}
6074 		if (sp->req_state_flags & RQSF_XFER_COMPLETE) {
6075 			ISP_SNPRINTF(buf, sizeof (buf), "%s XFR_CMPLT", buf);
6076 		}
6077 		ISP_SNPRINTF(buf, sizeof (buf), "%s\nstatus=>", buf);
6078 		if (sp->req_status_flags & RQSTF_DISCONNECT) {
6079 			ISP_SNPRINTF(buf, sizeof (buf), "%s Disconnect", buf);
6080 		}
6081 		if (sp->req_status_flags & RQSTF_SYNCHRONOUS) {
6082 			ISP_SNPRINTF(buf, sizeof (buf), "%s Sync_xfr", buf);
6083 		}
6084 		if (sp->req_status_flags & RQSTF_PARITY_ERROR) {
6085 			ISP_SNPRINTF(buf, sizeof (buf), "%s Parity", buf);
6086 		}
6087 		if (sp->req_status_flags & RQSTF_BUS_RESET) {
6088 			ISP_SNPRINTF(buf, sizeof (buf), "%s Bus_Reset", buf);
6089 		}
6090 		if (sp->req_status_flags & RQSTF_DEVICE_RESET) {
6091 			ISP_SNPRINTF(buf, sizeof (buf), "%s Device_Reset", buf);
6092 		}
6093 		if (sp->req_status_flags & RQSTF_ABORTED) {
6094 			ISP_SNPRINTF(buf, sizeof (buf), "%s Aborted", buf);
6095 		}
6096 		if (sp->req_status_flags & RQSTF_TIMEOUT) {
6097 			ISP_SNPRINTF(buf, sizeof (buf), "%s Timeout", buf);
6098 		}
6099 		if (sp->req_status_flags & RQSTF_NEGOTIATION) {
6100 			ISP_SNPRINTF(buf, sizeof (buf), "%s Negotiation", buf);
6101 		}
6102 		isp_xs_prt(isp, xs,  ISP_LOGERR, "Transport Error: %s", buf);
6103 		*rp = XS_XFRLEN(xs);
6104 		break;
6105 	}
6106 	case RQCS_RESET_OCCURRED:
6107 	{
6108 		int chan;
6109 		isp_xs_prt(isp, xs, ISP_LOGWARN, "Bus Reset destroyed command");
6110 		for (chan = 0; chan < isp->isp_nchan; chan++) {
6111 			FCPARAM(isp, chan)->sendmarker = 1;
6112 		}
6113 		if (XS_NOERR(xs)) {
6114 			XS_SETERR(xs, HBA_BUSRESET);
6115 		}
6116 		*rp = XS_XFRLEN(xs);
6117 		return;
6118 	}
6119 	case RQCS_ABORTED:
6120 		isp_xs_prt(isp, xs, ISP_LOGERR, "Command Aborted");
6121 		ISP_SET_SENDMARKER(isp, XS_CHANNEL(xs), 1);
6122 		if (XS_NOERR(xs)) {
6123 			XS_SETERR(xs, HBA_ABORTED);
6124 		}
6125 		return;
6126 
6127 	case RQCS_TIMEOUT:
6128 		isp_xs_prt(isp, xs, ISP_LOGWARN, "Command timed out");
6129 		/*
6130 		 * XXX: Check to see if we logged out of the device.
6131 		 */
6132 		if (XS_NOERR(xs)) {
6133 			XS_SETERR(xs, HBA_CMDTIMEOUT);
6134 		}
6135 		return;
6136 
6137 	case RQCS_DATA_OVERRUN:
6138 		XS_SET_RESID(xs, sp->req_resid);
6139 		isp_xs_prt(isp, xs, ISP_LOGERR, "data overrun (%ld)", (long) XS_GET_RESID(xs));
6140 		if (XS_NOERR(xs)) {
6141 			XS_SETERR(xs, HBA_DATAOVR);
6142 		}
6143 		return;
6144 
6145 	case RQCS_COMMAND_OVERRUN:
6146 		isp_xs_prt(isp, xs, ISP_LOGERR, "command overrun");
6147 		break;
6148 
6149 	case RQCS_STATUS_OVERRUN:
6150 		isp_xs_prt(isp, xs, ISP_LOGERR, "status overrun");
6151 		break;
6152 
6153 	case RQCS_BAD_MESSAGE:
6154 		isp_xs_prt(isp, xs, ISP_LOGERR, "msg not COMMAND COMPLETE after status");
6155 		break;
6156 
6157 	case RQCS_NO_MESSAGE_OUT:
6158 		isp_xs_prt(isp, xs, ISP_LOGERR, "No MESSAGE OUT phase after selection");
6159 		break;
6160 
6161 	case RQCS_EXT_ID_FAILED:
6162 		isp_xs_prt(isp, xs, ISP_LOGERR, "EXTENDED IDENTIFY failed");
6163 		break;
6164 
6165 	case RQCS_IDE_MSG_FAILED:
6166 		isp_xs_prt(isp, xs, ISP_LOGERR, "INITIATOR DETECTED ERROR rejected");
6167 		break;
6168 
6169 	case RQCS_ABORT_MSG_FAILED:
6170 		isp_xs_prt(isp, xs, ISP_LOGERR, "ABORT OPERATION rejected");
6171 		break;
6172 
6173 	case RQCS_REJECT_MSG_FAILED:
6174 		isp_xs_prt(isp, xs, ISP_LOGERR, "MESSAGE REJECT rejected");
6175 		break;
6176 
6177 	case RQCS_NOP_MSG_FAILED:
6178 		isp_xs_prt(isp, xs, ISP_LOGERR, "NOP rejected");
6179 		break;
6180 
6181 	case RQCS_PARITY_ERROR_MSG_FAILED:
6182 		isp_xs_prt(isp, xs, ISP_LOGERR, "MESSAGE PARITY ERROR rejected");
6183 		break;
6184 
6185 	case RQCS_DEVICE_RESET_MSG_FAILED:
6186 		isp_xs_prt(isp, xs, ISP_LOGWARN, "BUS DEVICE RESET rejected");
6187 		break;
6188 
6189 	case RQCS_ID_MSG_FAILED:
6190 		isp_xs_prt(isp, xs, ISP_LOGERR, "IDENTIFY rejected");
6191 		break;
6192 
6193 	case RQCS_UNEXP_BUS_FREE:
6194 		isp_xs_prt(isp, xs, ISP_LOGERR, "Unexpected Bus Free");
6195 		break;
6196 
6197 	case RQCS_DATA_UNDERRUN:
6198 	{
6199 		if (IS_FC(isp)) {
6200 			int ru_marked = (sp->req_scsi_status & RQCS_RU) != 0;
6201 			if (!ru_marked || sp->req_resid > XS_XFRLEN(xs)) {
6202 				isp_xs_prt(isp, xs, ISP_LOGWARN, bun, XS_XFRLEN(xs), sp->req_resid, (ru_marked)? "marked" : "not marked");
6203 				if (XS_NOERR(xs)) {
6204 					XS_SETERR(xs, HBA_BOTCH);
6205 				}
6206 				return;
6207 			}
6208 		}
6209 		XS_SET_RESID(xs, sp->req_resid);
6210 		if (XS_NOERR(xs)) {
6211 			XS_SETERR(xs, HBA_NOERROR);
6212 		}
6213 		return;
6214 	}
6215 
6216 	case RQCS_XACT_ERR1:
6217 		isp_xs_prt(isp, xs, ISP_LOGERR, "HBA attempted queued transaction with disconnect not set");
6218 		break;
6219 
6220 	case RQCS_XACT_ERR2:
6221 		isp_xs_prt(isp, xs, ISP_LOGERR, "HBA attempted queued transaction to target routine %d", XS_LUN(xs));
6222 		break;
6223 
6224 	case RQCS_XACT_ERR3:
6225 		isp_xs_prt(isp, xs, ISP_LOGERR, "HBA attempted queued cmd when queueing disabled");
6226 		break;
6227 
6228 	case RQCS_BAD_ENTRY:
6229 		isp_prt(isp, ISP_LOGERR, "Invalid IOCB entry type detected");
6230 		break;
6231 
6232 	case RQCS_QUEUE_FULL:
6233 		isp_xs_prt(isp, xs, ISP_LOGDEBUG0, "internal queues full status 0x%x", *XS_STSP(xs));
6234 
6235 		/*
6236 		 * If QFULL or some other status byte is set, then this
6237 		 * isn't an error, per se.
6238 		 *
6239 		 * Unfortunately, some QLogic f/w writers have, in
6240 		 * some cases, ommitted to *set* status to QFULL.
6241 		 *
6242 
6243 		if (*XS_STSP(xs) != SCSI_GOOD && XS_NOERR(xs)) {
6244 			XS_SETERR(xs, HBA_NOERROR);
6245 			return;
6246 		}
6247 
6248 		 *
6249 		 *
6250 		 */
6251 
6252 		*XS_STSP(xs) = SCSI_QFULL;
6253 		XS_SETERR(xs, HBA_NOERROR);
6254 		return;
6255 
6256 	case RQCS_PHASE_SKIPPED:
6257 		isp_xs_prt(isp, xs, ISP_LOGERR, "SCSI phase skipped");
6258 		break;
6259 
6260 	case RQCS_ARQS_FAILED:
6261 		isp_xs_prt(isp, xs, ISP_LOGERR, "Auto Request Sense Failed");
6262 		if (XS_NOERR(xs)) {
6263 			XS_SETERR(xs, HBA_ARQFAIL);
6264 		}
6265 		return;
6266 
6267 	case RQCS_WIDE_FAILED:
6268 		isp_xs_prt(isp, xs, ISP_LOGERR, "Wide Negotiation Failed");
6269 		if (IS_SCSI(isp)) {
6270 			sdparam *sdp = SDPARAM(isp, XS_CHANNEL(xs));
6271 			sdp->isp_devparam[XS_TGT(xs)].goal_flags &= ~DPARM_WIDE;
6272 			sdp->isp_devparam[XS_TGT(xs)].dev_update = 1;
6273 			sdp->update = 1;
6274 		}
6275 		if (XS_NOERR(xs)) {
6276 			XS_SETERR(xs, HBA_NOERROR);
6277 		}
6278 		return;
6279 
6280 	case RQCS_SYNCXFER_FAILED:
6281 		isp_xs_prt(isp, xs, ISP_LOGERR, "SDTR Message Failed");
6282 		if (IS_SCSI(isp)) {
6283 			sdparam *sdp = SDPARAM(isp, XS_CHANNEL(xs));
6284 			sdp += XS_CHANNEL(xs);
6285 			sdp->isp_devparam[XS_TGT(xs)].goal_flags &= ~DPARM_SYNC;
6286 			sdp->isp_devparam[XS_TGT(xs)].dev_update = 1;
6287 			sdp->update = 1;
6288 		}
6289 		break;
6290 
6291 	case RQCS_LVD_BUSERR:
6292 		isp_xs_prt(isp, xs, ISP_LOGERR, "Bad LVD condition");
6293 		break;
6294 
6295 	case RQCS_PORT_UNAVAILABLE:
6296 		/*
6297 		 * No such port on the loop. Moral equivalent of SELTIMEO
6298 		 */
6299 	case RQCS_PORT_LOGGED_OUT:
6300 	{
6301 		const char *reason;
6302 		uint8_t sts = sp->req_completion_status & 0xff;
6303 
6304 		/*
6305 		 * It was there (maybe)- treat as a selection timeout.
6306 		 */
6307 		if (sts == RQCS_PORT_UNAVAILABLE) {
6308 			reason = "unavailable";
6309 		} else {
6310 			reason = "logout";
6311 		}
6312 
6313 		isp_prt(isp, ISP_LOGINFO, "port %s for target %d",
6314 		    reason, XS_TGT(xs));
6315 
6316 		/*
6317 		 * If we're on a local loop, force a LIP (which is overkill)
6318 		 * to force a re-login of this unit. If we're on fabric,
6319 		 * then we'll have to log in again as a matter of course.
6320 		 */
6321 		if (FCPARAM(isp, 0)->isp_topo == TOPO_NL_PORT ||
6322 		    FCPARAM(isp, 0)->isp_topo == TOPO_FL_PORT) {
6323 			mbreg_t mbs;
6324 			MBSINIT(&mbs, MBOX_INIT_LIP, MBLOGALL, 0);
6325 			if (ISP_CAP_2KLOGIN(isp)) {
6326 				mbs.ibits = (1 << 10);
6327 			}
6328 			isp_mboxcmd_qnw(isp, &mbs, 1);
6329 		}
6330 		if (XS_NOERR(xs)) {
6331 			XS_SETERR(xs, HBA_SELTIMEOUT);
6332 		}
6333 		return;
6334 	}
6335 	case RQCS_PORT_CHANGED:
6336 		isp_prt(isp, ISP_LOGWARN,
6337 		    "port changed for target %d", XS_TGT(xs));
6338 		if (XS_NOERR(xs)) {
6339 			XS_SETERR(xs, HBA_SELTIMEOUT);
6340 		}
6341 		return;
6342 
6343 	case RQCS_PORT_BUSY:
6344 		isp_prt(isp, ISP_LOGWARN,
6345 		    "port busy for target %d", XS_TGT(xs));
6346 		if (XS_NOERR(xs)) {
6347 			XS_SETERR(xs, HBA_TGTBSY);
6348 		}
6349 		return;
6350 
6351 	default:
6352 		isp_prt(isp, ISP_LOGERR, "Unknown Completion Status 0x%x",
6353 		    sp->req_completion_status);
6354 		break;
6355 	}
6356 	if (XS_NOERR(xs)) {
6357 		XS_SETERR(xs, HBA_BOTCH);
6358 	}
6359 }
6360 
6361 static void
6362 isp_parse_status_24xx(ispsoftc_t *isp, isp24xx_statusreq_t *sp, XS_T *xs, long *rp)
6363 {
6364 	int ru_marked, sv_marked;
6365 	int chan = XS_CHANNEL(xs);
6366 
6367 	switch (sp->req_completion_status) {
6368 	case RQCS_COMPLETE:
6369 		if (XS_NOERR(xs)) {
6370 			XS_SETERR(xs, HBA_NOERROR);
6371 		}
6372 		return;
6373 
6374 	case RQCS_DMA_ERROR:
6375 		isp_xs_prt(isp, xs, ISP_LOGERR, "DMA error");
6376 		break;
6377 
6378 	case RQCS_TRANSPORT_ERROR:
6379 		isp_xs_prt(isp, xs,  ISP_LOGERR, "Transport Error");
6380 		break;
6381 
6382 	case RQCS_RESET_OCCURRED:
6383 		isp_xs_prt(isp, xs, ISP_LOGWARN, "reset destroyed command");
6384 		FCPARAM(isp, chan)->sendmarker = 1;
6385 		if (XS_NOERR(xs)) {
6386 			XS_SETERR(xs, HBA_BUSRESET);
6387 		}
6388 		return;
6389 
6390 	case RQCS_ABORTED:
6391 		isp_xs_prt(isp, xs, ISP_LOGERR, "Command Aborted");
6392 		FCPARAM(isp, chan)->sendmarker = 1;
6393 		if (XS_NOERR(xs)) {
6394 			XS_SETERR(xs, HBA_ABORTED);
6395 		}
6396 		return;
6397 
6398 	case RQCS_TIMEOUT:
6399 		isp_xs_prt(isp, xs, ISP_LOGWARN, "Command Timed Out");
6400 		if (XS_NOERR(xs)) {
6401 			XS_SETERR(xs, HBA_CMDTIMEOUT);
6402 		}
6403 		return;
6404 
6405 	case RQCS_DATA_OVERRUN:
6406 		XS_SET_RESID(xs, sp->req_resid);
6407 		isp_xs_prt(isp, xs, ISP_LOGERR, "Data Overrun");
6408 		if (XS_NOERR(xs)) {
6409 			XS_SETERR(xs, HBA_DATAOVR);
6410 		}
6411 		return;
6412 
6413 	case RQCS_24XX_DRE:	/* data reassembly error */
6414 		isp_prt(isp, ISP_LOGERR,
6415 		    "Chan %d data reassembly error for target %d",
6416 		    chan, XS_TGT(xs));
6417 		if (XS_NOERR(xs)) {
6418 			XS_SETERR(xs, HBA_ABORTED);
6419 		}
6420 		*rp = XS_XFRLEN(xs);
6421 		return;
6422 
6423 	case RQCS_24XX_TABORT:	/* aborted by target */
6424 		isp_prt(isp, ISP_LOGERR, "Chan %d target %d sent ABTS",
6425 		    chan, XS_TGT(xs));
6426 		if (XS_NOERR(xs)) {
6427 			XS_SETERR(xs, HBA_ABORTED);
6428 		}
6429 		return;
6430 
6431 	case RQCS_DATA_UNDERRUN:
6432 		ru_marked = (sp->req_scsi_status & RQCS_RU) != 0;
6433 		/*
6434 		 * We can get an underrun w/o things being marked
6435 		 * if we got a non-zero status.
6436 		 */
6437 		sv_marked = (sp->req_scsi_status & (RQCS_SV|RQCS_RV)) != 0;
6438 		if ((ru_marked == 0 && sv_marked == 0) ||
6439 		    (sp->req_resid > XS_XFRLEN(xs))) {
6440 			isp_xs_prt(isp, xs, ISP_LOGWARN, bun, XS_XFRLEN(xs), sp->req_resid, (ru_marked)? "marked" : "not marked");
6441 			if (XS_NOERR(xs)) {
6442 				XS_SETERR(xs, HBA_BOTCH);
6443 			}
6444 			return;
6445 		}
6446 		XS_SET_RESID(xs, sp->req_resid);
6447 		isp_xs_prt(isp, xs, ISP_LOGDEBUG0, "Data Underrun (%d) for command 0x%x", sp->req_resid, XS_CDBP(xs)[0] & 0xff);
6448 		if (XS_NOERR(xs)) {
6449 			XS_SETERR(xs, HBA_NOERROR);
6450 		}
6451 		return;
6452 
6453 	case RQCS_PORT_UNAVAILABLE:
6454 		/*
6455 		 * No such port on the loop. Moral equivalent of SELTIMEO
6456 		 */
6457 	case RQCS_PORT_LOGGED_OUT:
6458 	{
6459 		const char *reason;
6460 		uint8_t sts = sp->req_completion_status & 0xff;
6461 
6462 		/*
6463 		 * It was there (maybe)- treat as a selection timeout.
6464 		 */
6465 		if (sts == RQCS_PORT_UNAVAILABLE) {
6466 			reason = "unavailable";
6467 		} else {
6468 			reason = "logout";
6469 		}
6470 
6471 		isp_prt(isp, ISP_LOGINFO, "Chan %d port %s for target %d",
6472 		    chan, reason, XS_TGT(xs));
6473 
6474 		/*
6475 		 * There is no MBOX_INIT_LIP for the 24XX.
6476 		 */
6477 		if (XS_NOERR(xs)) {
6478 			XS_SETERR(xs, HBA_SELTIMEOUT);
6479 		}
6480 		return;
6481 	}
6482 	case RQCS_PORT_CHANGED:
6483 		isp_prt(isp, ISP_LOGWARN,
6484 		    "port changed for target %d chan %d", XS_TGT(xs), chan);
6485 		if (XS_NOERR(xs)) {
6486 			XS_SETERR(xs, HBA_SELTIMEOUT);
6487 		}
6488 		return;
6489 
6490 
6491 	case RQCS_24XX_ENOMEM:	/* f/w resource unavailable */
6492 		isp_prt(isp, ISP_LOGWARN,
6493 		    "f/w resource unavailable for target %d chan %d",
6494 		    XS_TGT(xs), chan);
6495 		if (XS_NOERR(xs)) {
6496 			*XS_STSP(xs) = SCSI_BUSY;
6497 			XS_SETERR(xs, HBA_TGTBSY);
6498 		}
6499 		return;
6500 
6501 	case RQCS_24XX_TMO:	/* task management overrun */
6502 		isp_prt(isp, ISP_LOGWARN,
6503 		    "command for target %d overlapped task management for "
6504 		    "chan %d", XS_TGT(xs), chan);
6505 		if (XS_NOERR(xs)) {
6506 			*XS_STSP(xs) = SCSI_BUSY;
6507 			XS_SETERR(xs, HBA_TGTBSY);
6508 		}
6509 		return;
6510 
6511 	default:
6512 		isp_prt(isp, ISP_LOGERR,
6513 		    "Unknown Completion Status 0x%x on chan %d",
6514 		    sp->req_completion_status, chan);
6515 		break;
6516 	}
6517 	if (XS_NOERR(xs)) {
6518 		XS_SETERR(xs, HBA_BOTCH);
6519 	}
6520 }
6521 
6522 static void
6523 isp_fastpost_complete(ispsoftc_t *isp, uint32_t fph)
6524 {
6525 	XS_T *xs;
6526 
6527 	if (fph == 0) {
6528 		return;
6529 	}
6530 	xs = isp_find_xs(isp, fph);
6531 	if (xs == NULL) {
6532 		isp_prt(isp, ISP_LOGWARN,
6533 		    "Command for fast post handle 0x%x not found", fph);
6534 		return;
6535 	}
6536 	isp_destroy_handle(isp, fph);
6537 
6538 	/*
6539 	 * Since we don't have a result queue entry item,
6540 	 * we must believe that SCSI status is zero and
6541 	 * that all data transferred.
6542 	 */
6543 	XS_SET_RESID(xs, 0);
6544 	*XS_STSP(xs) = SCSI_GOOD;
6545 	if (XS_XFRLEN(xs)) {
6546 		ISP_DMAFREE(isp, xs, fph);
6547 	}
6548 	if (isp->isp_nactive) {
6549 		isp->isp_nactive--;
6550 	}
6551 	isp->isp_fphccmplt++;
6552 	isp_done(xs);
6553 }
6554 
6555 static int
6556 isp_mbox_continue(ispsoftc_t *isp)
6557 {
6558 	mbreg_t mbs;
6559 	uint16_t *ptr;
6560 	uint32_t offset;
6561 
6562 	switch (isp->isp_lastmbxcmd) {
6563 	case MBOX_WRITE_RAM_WORD:
6564 	case MBOX_READ_RAM_WORD:
6565 	case MBOX_WRITE_RAM_WORD_EXTENDED:
6566 	case MBOX_READ_RAM_WORD_EXTENDED:
6567 		break;
6568 	default:
6569 		return (1);
6570 	}
6571 	if (isp->isp_mboxtmp[0] != MBOX_COMMAND_COMPLETE) {
6572 		isp->isp_mbxwrk0 = 0;
6573 		return (-1);
6574 	}
6575 
6576 	/*
6577 	 * Clear the previous interrupt.
6578 	 */
6579 	if (IS_24XX(isp)) {
6580 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_CLEAR_RISC_INT);
6581 	} else {
6582 		ISP_WRITE(isp, HCCR, HCCR_CMD_CLEAR_RISC_INT);
6583 		ISP_WRITE(isp, BIU_SEMA, 0);
6584 	}
6585 
6586 	/*
6587 	 * Continue with next word.
6588 	 */
6589 	ISP_MEMZERO(&mbs, sizeof (mbs));
6590 	ptr = isp->isp_mbxworkp;
6591 	switch (isp->isp_lastmbxcmd) {
6592 	case MBOX_WRITE_RAM_WORD:
6593 		mbs.param[1] = isp->isp_mbxwrk1++;
6594 		mbs.param[2] = *ptr++;
6595 		break;
6596 	case MBOX_READ_RAM_WORD:
6597 		*ptr++ = isp->isp_mboxtmp[2];
6598 		mbs.param[1] = isp->isp_mbxwrk1++;
6599 		break;
6600 	case MBOX_WRITE_RAM_WORD_EXTENDED:
6601 		if (IS_24XX(isp)) {
6602 			uint32_t *lptr = (uint32_t *)ptr;
6603 			mbs.param[2] = lptr[0];
6604 			mbs.param[3] = lptr[0] >> 16;
6605 			lptr++;
6606 			ptr = (uint16_t *)lptr;
6607 		} else {
6608 			mbs.param[2] = *ptr++;
6609 		}
6610 		offset = isp->isp_mbxwrk1;
6611 		offset |= isp->isp_mbxwrk8 << 16;
6612 		mbs.param[1] = offset;
6613 		mbs.param[8] = offset >> 16;
6614 		offset++;
6615 		isp->isp_mbxwrk1 = offset;
6616 		isp->isp_mbxwrk8 = offset >> 16;
6617 		break;
6618 	case MBOX_READ_RAM_WORD_EXTENDED:
6619 		if (IS_24XX(isp)) {
6620 			uint32_t *lptr = (uint32_t *)ptr;
6621 			uint32_t val = isp->isp_mboxtmp[2];
6622 			val |= (isp->isp_mboxtmp[3]) << 16;
6623 			*lptr++ = val;
6624 			ptr = (uint16_t *)lptr;
6625 		} else {
6626 			*ptr++ = isp->isp_mboxtmp[2];
6627 		}
6628 		offset = isp->isp_mbxwrk1;
6629 		offset |= isp->isp_mbxwrk8 << 16;
6630 		mbs.param[1] = offset;
6631 		mbs.param[8] = offset >> 16;
6632 		offset++;
6633 		isp->isp_mbxwrk1 = offset;
6634 		isp->isp_mbxwrk8 = offset >> 16;
6635 		break;
6636 	}
6637 	isp->isp_mbxworkp = ptr;
6638 	isp->isp_mbxwrk0--;
6639 	mbs.param[0] = isp->isp_lastmbxcmd;
6640 	mbs.logval = MBLOGALL;
6641 	isp_mboxcmd_qnw(isp, &mbs, 0);
6642 	return (0);
6643 }
6644 
6645 #define	HIWRD(x)			((x) >> 16)
6646 #define	LOWRD(x)			((x)  & 0xffff)
6647 #define	ISPOPMAP(a, b)			(((a) << 16) | (b))
6648 static const uint32_t mbpscsi[] = {
6649 	ISPOPMAP(0x01, 0x01),	/* 0x00: MBOX_NO_OP */
6650 	ISPOPMAP(0x1f, 0x01),	/* 0x01: MBOX_LOAD_RAM */
6651 	ISPOPMAP(0x03, 0x01),	/* 0x02: MBOX_EXEC_FIRMWARE */
6652 	ISPOPMAP(0x1f, 0x01),	/* 0x03: MBOX_DUMP_RAM */
6653 	ISPOPMAP(0x07, 0x07),	/* 0x04: MBOX_WRITE_RAM_WORD */
6654 	ISPOPMAP(0x03, 0x07),	/* 0x05: MBOX_READ_RAM_WORD */
6655 	ISPOPMAP(0x3f, 0x3f),	/* 0x06: MBOX_MAILBOX_REG_TEST */
6656 	ISPOPMAP(0x07, 0x07),	/* 0x07: MBOX_VERIFY_CHECKSUM	*/
6657 	ISPOPMAP(0x01, 0x0f),	/* 0x08: MBOX_ABOUT_FIRMWARE */
6658 	ISPOPMAP(0x00, 0x00),	/* 0x09: */
6659 	ISPOPMAP(0x00, 0x00),	/* 0x0a: */
6660 	ISPOPMAP(0x00, 0x00),	/* 0x0b: */
6661 	ISPOPMAP(0x00, 0x00),	/* 0x0c: */
6662 	ISPOPMAP(0x00, 0x00),	/* 0x0d: */
6663 	ISPOPMAP(0x01, 0x05),	/* 0x0e: MBOX_CHECK_FIRMWARE */
6664 	ISPOPMAP(0x00, 0x00),	/* 0x0f: */
6665 	ISPOPMAP(0x1f, 0x1f),	/* 0x10: MBOX_INIT_REQ_QUEUE */
6666 	ISPOPMAP(0x3f, 0x3f),	/* 0x11: MBOX_INIT_RES_QUEUE */
6667 	ISPOPMAP(0x0f, 0x0f),	/* 0x12: MBOX_EXECUTE_IOCB */
6668 	ISPOPMAP(0x03, 0x03),	/* 0x13: MBOX_WAKE_UP	*/
6669 	ISPOPMAP(0x01, 0x3f),	/* 0x14: MBOX_STOP_FIRMWARE */
6670 	ISPOPMAP(0x0f, 0x0f),	/* 0x15: MBOX_ABORT */
6671 	ISPOPMAP(0x03, 0x03),	/* 0x16: MBOX_ABORT_DEVICE */
6672 	ISPOPMAP(0x07, 0x07),	/* 0x17: MBOX_ABORT_TARGET */
6673 	ISPOPMAP(0x07, 0x07),	/* 0x18: MBOX_BUS_RESET */
6674 	ISPOPMAP(0x03, 0x07),	/* 0x19: MBOX_STOP_QUEUE */
6675 	ISPOPMAP(0x03, 0x07),	/* 0x1a: MBOX_START_QUEUE */
6676 	ISPOPMAP(0x03, 0x07),	/* 0x1b: MBOX_SINGLE_STEP_QUEUE */
6677 	ISPOPMAP(0x03, 0x07),	/* 0x1c: MBOX_ABORT_QUEUE */
6678 	ISPOPMAP(0x03, 0x4f),	/* 0x1d: MBOX_GET_DEV_QUEUE_STATUS */
6679 	ISPOPMAP(0x00, 0x00),	/* 0x1e: */
6680 	ISPOPMAP(0x01, 0x07),	/* 0x1f: MBOX_GET_FIRMWARE_STATUS */
6681 	ISPOPMAP(0x01, 0x07),	/* 0x20: MBOX_GET_INIT_SCSI_ID */
6682 	ISPOPMAP(0x01, 0x07),	/* 0x21: MBOX_GET_SELECT_TIMEOUT */
6683 	ISPOPMAP(0x01, 0xc7),	/* 0x22: MBOX_GET_RETRY_COUNT	*/
6684 	ISPOPMAP(0x01, 0x07),	/* 0x23: MBOX_GET_TAG_AGE_LIMIT */
6685 	ISPOPMAP(0x01, 0x03),	/* 0x24: MBOX_GET_CLOCK_RATE */
6686 	ISPOPMAP(0x01, 0x07),	/* 0x25: MBOX_GET_ACT_NEG_STATE */
6687 	ISPOPMAP(0x01, 0x07),	/* 0x26: MBOX_GET_ASYNC_DATA_SETUP_TIME */
6688 	ISPOPMAP(0x01, 0x07),	/* 0x27: MBOX_GET_PCI_PARAMS */
6689 	ISPOPMAP(0x03, 0x4f),	/* 0x28: MBOX_GET_TARGET_PARAMS */
6690 	ISPOPMAP(0x03, 0x0f),	/* 0x29: MBOX_GET_DEV_QUEUE_PARAMS */
6691 	ISPOPMAP(0x01, 0x07),	/* 0x2a: MBOX_GET_RESET_DELAY_PARAMS */
6692 	ISPOPMAP(0x00, 0x00),	/* 0x2b: */
6693 	ISPOPMAP(0x00, 0x00),	/* 0x2c: */
6694 	ISPOPMAP(0x00, 0x00),	/* 0x2d: */
6695 	ISPOPMAP(0x00, 0x00),	/* 0x2e: */
6696 	ISPOPMAP(0x00, 0x00),	/* 0x2f: */
6697 	ISPOPMAP(0x03, 0x03),	/* 0x30: MBOX_SET_INIT_SCSI_ID */
6698 	ISPOPMAP(0x07, 0x07),	/* 0x31: MBOX_SET_SELECT_TIMEOUT */
6699 	ISPOPMAP(0xc7, 0xc7),	/* 0x32: MBOX_SET_RETRY_COUNT	*/
6700 	ISPOPMAP(0x07, 0x07),	/* 0x33: MBOX_SET_TAG_AGE_LIMIT */
6701 	ISPOPMAP(0x03, 0x03),	/* 0x34: MBOX_SET_CLOCK_RATE */
6702 	ISPOPMAP(0x07, 0x07),	/* 0x35: MBOX_SET_ACT_NEG_STATE */
6703 	ISPOPMAP(0x07, 0x07),	/* 0x36: MBOX_SET_ASYNC_DATA_SETUP_TIME */
6704 	ISPOPMAP(0x07, 0x07),	/* 0x37: MBOX_SET_PCI_CONTROL_PARAMS */
6705 	ISPOPMAP(0x4f, 0x4f),	/* 0x38: MBOX_SET_TARGET_PARAMS */
6706 	ISPOPMAP(0x0f, 0x0f),	/* 0x39: MBOX_SET_DEV_QUEUE_PARAMS */
6707 	ISPOPMAP(0x07, 0x07),	/* 0x3a: MBOX_SET_RESET_DELAY_PARAMS */
6708 	ISPOPMAP(0x00, 0x00),	/* 0x3b: */
6709 	ISPOPMAP(0x00, 0x00),	/* 0x3c: */
6710 	ISPOPMAP(0x00, 0x00),	/* 0x3d: */
6711 	ISPOPMAP(0x00, 0x00),	/* 0x3e: */
6712 	ISPOPMAP(0x00, 0x00),	/* 0x3f: */
6713 	ISPOPMAP(0x01, 0x03),	/* 0x40: MBOX_RETURN_BIOS_BLOCK_ADDR */
6714 	ISPOPMAP(0x3f, 0x01),	/* 0x41: MBOX_WRITE_FOUR_RAM_WORDS */
6715 	ISPOPMAP(0x03, 0x07),	/* 0x42: MBOX_EXEC_BIOS_IOCB */
6716 	ISPOPMAP(0x00, 0x00),	/* 0x43: */
6717 	ISPOPMAP(0x00, 0x00),	/* 0x44: */
6718 	ISPOPMAP(0x03, 0x03),	/* 0x45: SET SYSTEM PARAMETER */
6719 	ISPOPMAP(0x01, 0x03),	/* 0x46: GET SYSTEM PARAMETER */
6720 	ISPOPMAP(0x00, 0x00),	/* 0x47: */
6721 	ISPOPMAP(0x01, 0xcf),	/* 0x48: GET SCAM CONFIGURATION */
6722 	ISPOPMAP(0xcf, 0xcf),	/* 0x49: SET SCAM CONFIGURATION */
6723 	ISPOPMAP(0x03, 0x03),	/* 0x4a: MBOX_SET_FIRMWARE_FEATURES */
6724 	ISPOPMAP(0x01, 0x03),	/* 0x4b: MBOX_GET_FIRMWARE_FEATURES */
6725 	ISPOPMAP(0x00, 0x00),	/* 0x4c: */
6726 	ISPOPMAP(0x00, 0x00),	/* 0x4d: */
6727 	ISPOPMAP(0x00, 0x00),	/* 0x4e: */
6728 	ISPOPMAP(0x00, 0x00),	/* 0x4f: */
6729 	ISPOPMAP(0xdf, 0xdf),	/* 0x50: LOAD RAM A64 */
6730 	ISPOPMAP(0xdf, 0xdf),	/* 0x51: DUMP RAM A64 */
6731 	ISPOPMAP(0xdf, 0xff),	/* 0x52: INITIALIZE REQUEST QUEUE A64 */
6732 	ISPOPMAP(0xef, 0xff),	/* 0x53: INITIALIZE RESPONSE QUEUE A64 */
6733 	ISPOPMAP(0xcf, 0x01),	/* 0x54: EXECUCUTE COMMAND IOCB A64 */
6734 	ISPOPMAP(0x07, 0x01),	/* 0x55: ENABLE TARGET MODE */
6735 	ISPOPMAP(0x03, 0x0f),	/* 0x56: GET TARGET STATUS */
6736 	ISPOPMAP(0x00, 0x00),	/* 0x57: */
6737 	ISPOPMAP(0x00, 0x00),	/* 0x58: */
6738 	ISPOPMAP(0x00, 0x00),	/* 0x59: */
6739 	ISPOPMAP(0x03, 0x03),	/* 0x5a: SET DATA OVERRUN RECOVERY MODE */
6740 	ISPOPMAP(0x01, 0x03),	/* 0x5b: GET DATA OVERRUN RECOVERY MODE */
6741 	ISPOPMAP(0x0f, 0x0f),	/* 0x5c: SET HOST DATA */
6742 	ISPOPMAP(0x01, 0x01)	/* 0x5d: GET NOST DATA */
6743 };
6744 
6745 static const char *scsi_mbcmd_names[] = {
6746 	"NO-OP",
6747 	"LOAD RAM",
6748 	"EXEC FIRMWARE",
6749 	"DUMP RAM",
6750 	"WRITE RAM WORD",
6751 	"READ RAM WORD",
6752 	"MAILBOX REG TEST",
6753 	"VERIFY CHECKSUM",
6754 	"ABOUT FIRMWARE",
6755 	NULL,
6756 	NULL,
6757 	NULL,
6758 	NULL,
6759 	NULL,
6760 	"CHECK FIRMWARE",
6761 	NULL,
6762 	"INIT REQUEST QUEUE",
6763 	"INIT RESULT QUEUE",
6764 	"EXECUTE IOCB",
6765 	"WAKE UP",
6766 	"STOP FIRMWARE",
6767 	"ABORT",
6768 	"ABORT DEVICE",
6769 	"ABORT TARGET",
6770 	"BUS RESET",
6771 	"STOP QUEUE",
6772 	"START QUEUE",
6773 	"SINGLE STEP QUEUE",
6774 	"ABORT QUEUE",
6775 	"GET DEV QUEUE STATUS",
6776 	NULL,
6777 	"GET FIRMWARE STATUS",
6778 	"GET INIT SCSI ID",
6779 	"GET SELECT TIMEOUT",
6780 	"GET RETRY COUNT",
6781 	"GET TAG AGE LIMIT",
6782 	"GET CLOCK RATE",
6783 	"GET ACT NEG STATE",
6784 	"GET ASYNC DATA SETUP TIME",
6785 	"GET PCI PARAMS",
6786 	"GET TARGET PARAMS",
6787 	"GET DEV QUEUE PARAMS",
6788 	"GET RESET DELAY PARAMS",
6789 	NULL,
6790 	NULL,
6791 	NULL,
6792 	NULL,
6793 	NULL,
6794 	"SET INIT SCSI ID",
6795 	"SET SELECT TIMEOUT",
6796 	"SET RETRY COUNT",
6797 	"SET TAG AGE LIMIT",
6798 	"SET CLOCK RATE",
6799 	"SET ACT NEG STATE",
6800 	"SET ASYNC DATA SETUP TIME",
6801 	"SET PCI CONTROL PARAMS",
6802 	"SET TARGET PARAMS",
6803 	"SET DEV QUEUE PARAMS",
6804 	"SET RESET DELAY PARAMS",
6805 	NULL,
6806 	NULL,
6807 	NULL,
6808 	NULL,
6809 	NULL,
6810 	"RETURN BIOS BLOCK ADDR",
6811 	"WRITE FOUR RAM WORDS",
6812 	"EXEC BIOS IOCB",
6813 	NULL,
6814 	NULL,
6815 	"SET SYSTEM PARAMETER",
6816 	"GET SYSTEM PARAMETER",
6817 	NULL,
6818 	"GET SCAM CONFIGURATION",
6819 	"SET SCAM CONFIGURATION",
6820 	"SET FIRMWARE FEATURES",
6821 	"GET FIRMWARE FEATURES",
6822 	NULL,
6823 	NULL,
6824 	NULL,
6825 	NULL,
6826 	"LOAD RAM A64",
6827 	"DUMP RAM A64",
6828 	"INITIALIZE REQUEST QUEUE A64",
6829 	"INITIALIZE RESPONSE QUEUE A64",
6830 	"EXECUTE IOCB A64",
6831 	"ENABLE TARGET MODE",
6832 	"GET TARGET MODE STATE",
6833 	NULL,
6834 	NULL,
6835 	NULL,
6836 	"SET DATA OVERRUN RECOVERY MODE",
6837 	"GET DATA OVERRUN RECOVERY MODE",
6838 	"SET HOST DATA",
6839 	"GET NOST DATA",
6840 };
6841 
6842 static const uint32_t mbpfc[] = {
6843 	ISPOPMAP(0x01, 0x01),	/* 0x00: MBOX_NO_OP */
6844 	ISPOPMAP(0x1f, 0x01),	/* 0x01: MBOX_LOAD_RAM */
6845 	ISPOPMAP(0x0f, 0x01),	/* 0x02: MBOX_EXEC_FIRMWARE */
6846 	ISPOPMAP(0xdf, 0x01),	/* 0x03: MBOX_DUMP_RAM */
6847 	ISPOPMAP(0x07, 0x07),	/* 0x04: MBOX_WRITE_RAM_WORD */
6848 	ISPOPMAP(0x03, 0x07),	/* 0x05: MBOX_READ_RAM_WORD */
6849 	ISPOPMAP(0xff, 0xff),	/* 0x06: MBOX_MAILBOX_REG_TEST */
6850 	ISPOPMAP(0x07, 0x07),	/* 0x07: MBOX_VERIFY_CHECKSUM	*/
6851 	ISPOPMAP(0x01, 0x4f),	/* 0x08: MBOX_ABOUT_FIRMWARE */
6852 	ISPOPMAP(0xdf, 0x01),	/* 0x09: MBOX_LOAD_RISC_RAM_2100 */
6853 	ISPOPMAP(0xdf, 0x01),	/* 0x0a: DUMP RAM */
6854 	ISPOPMAP(0x1ff, 0x01),	/* 0x0b: MBOX_LOAD_RISC_RAM */
6855 	ISPOPMAP(0x00, 0x00),	/* 0x0c: */
6856 	ISPOPMAP(0x10f, 0x01),	/* 0x0d: MBOX_WRITE_RAM_WORD_EXTENDED */
6857 	ISPOPMAP(0x01, 0x05),	/* 0x0e: MBOX_CHECK_FIRMWARE */
6858 	ISPOPMAP(0x103, 0x0d),	/* 0x0f: MBOX_READ_RAM_WORD_EXTENDED */
6859 	ISPOPMAP(0x1f, 0x11),	/* 0x10: MBOX_INIT_REQ_QUEUE */
6860 	ISPOPMAP(0x2f, 0x21),	/* 0x11: MBOX_INIT_RES_QUEUE */
6861 	ISPOPMAP(0x0f, 0x01),	/* 0x12: MBOX_EXECUTE_IOCB */
6862 	ISPOPMAP(0x03, 0x03),	/* 0x13: MBOX_WAKE_UP	*/
6863 	ISPOPMAP(0x01, 0xff),	/* 0x14: MBOX_STOP_FIRMWARE */
6864 	ISPOPMAP(0x4f, 0x01),	/* 0x15: MBOX_ABORT */
6865 	ISPOPMAP(0x07, 0x01),	/* 0x16: MBOX_ABORT_DEVICE */
6866 	ISPOPMAP(0x07, 0x01),	/* 0x17: MBOX_ABORT_TARGET */
6867 	ISPOPMAP(0x03, 0x03),	/* 0x18: MBOX_BUS_RESET */
6868 	ISPOPMAP(0x07, 0x05),	/* 0x19: MBOX_STOP_QUEUE */
6869 	ISPOPMAP(0x07, 0x05),	/* 0x1a: MBOX_START_QUEUE */
6870 	ISPOPMAP(0x07, 0x05),	/* 0x1b: MBOX_SINGLE_STEP_QUEUE */
6871 	ISPOPMAP(0x07, 0x05),	/* 0x1c: MBOX_ABORT_QUEUE */
6872 	ISPOPMAP(0x07, 0x03),	/* 0x1d: MBOX_GET_DEV_QUEUE_STATUS */
6873 	ISPOPMAP(0x00, 0x00),	/* 0x1e: */
6874 	ISPOPMAP(0x01, 0x07),	/* 0x1f: MBOX_GET_FIRMWARE_STATUS */
6875 	ISPOPMAP(0x01, 0x4f),	/* 0x20: MBOX_GET_LOOP_ID */
6876 	ISPOPMAP(0x00, 0x00),	/* 0x21: */
6877 	ISPOPMAP(0x01, 0x07),	/* 0x22: MBOX_GET_RETRY_COUNT	*/
6878 	ISPOPMAP(0x00, 0x00),	/* 0x23: */
6879 	ISPOPMAP(0x00, 0x00),	/* 0x24: */
6880 	ISPOPMAP(0x00, 0x00),	/* 0x25: */
6881 	ISPOPMAP(0x00, 0x00),	/* 0x26: */
6882 	ISPOPMAP(0x00, 0x00),	/* 0x27: */
6883 	ISPOPMAP(0x01, 0x03),	/* 0x28: MBOX_GET_FIRMWARE_OPTIONS */
6884 	ISPOPMAP(0x03, 0x07),	/* 0x29: MBOX_GET_PORT_QUEUE_PARAMS */
6885 	ISPOPMAP(0x00, 0x00),	/* 0x2a: */
6886 	ISPOPMAP(0x00, 0x00),	/* 0x2b: */
6887 	ISPOPMAP(0x00, 0x00),	/* 0x2c: */
6888 	ISPOPMAP(0x00, 0x00),	/* 0x2d: */
6889 	ISPOPMAP(0x00, 0x00),	/* 0x2e: */
6890 	ISPOPMAP(0x00, 0x00),	/* 0x2f: */
6891 	ISPOPMAP(0x00, 0x00),	/* 0x30: */
6892 	ISPOPMAP(0x00, 0x00),	/* 0x31: */
6893 	ISPOPMAP(0x07, 0x07),	/* 0x32: MBOX_SET_RETRY_COUNT	*/
6894 	ISPOPMAP(0x00, 0x00),	/* 0x33: */
6895 	ISPOPMAP(0x00, 0x00),	/* 0x34: */
6896 	ISPOPMAP(0x00, 0x00),	/* 0x35: */
6897 	ISPOPMAP(0x00, 0x00),	/* 0x36: */
6898 	ISPOPMAP(0x00, 0x00),	/* 0x37: */
6899 	ISPOPMAP(0x0f, 0x01),	/* 0x38: MBOX_SET_FIRMWARE_OPTIONS */
6900 	ISPOPMAP(0x0f, 0x07),	/* 0x39: MBOX_SET_PORT_QUEUE_PARAMS */
6901 	ISPOPMAP(0x00, 0x00),	/* 0x3a: */
6902 	ISPOPMAP(0x00, 0x00),	/* 0x3b: */
6903 	ISPOPMAP(0x00, 0x00),	/* 0x3c: */
6904 	ISPOPMAP(0x00, 0x00),	/* 0x3d: */
6905 	ISPOPMAP(0x00, 0x00),	/* 0x3e: */
6906 	ISPOPMAP(0x00, 0x00),	/* 0x3f: */
6907 	ISPOPMAP(0x03, 0x01),	/* 0x40: MBOX_LOOP_PORT_BYPASS */
6908 	ISPOPMAP(0x03, 0x01),	/* 0x41: MBOX_LOOP_PORT_ENABLE */
6909 	ISPOPMAP(0x03, 0x07),	/* 0x42: MBOX_GET_RESOURCE_COUNT */
6910 	ISPOPMAP(0x01, 0x01),	/* 0x43: MBOX_REQUEST_OFFLINE_MODE */
6911 	ISPOPMAP(0x00, 0x00),	/* 0x44: */
6912 	ISPOPMAP(0x00, 0x00),	/* 0x45: */
6913 	ISPOPMAP(0x00, 0x00),	/* 0x46: */
6914 	ISPOPMAP(0xcf, 0x03),	/* 0x47: GET PORT_DATABASE ENHANCED */
6915 	ISPOPMAP(0xcd, 0x01),	/* 0x48: MBOX_INIT_FIRMWARE_MULTI_ID */
6916 	ISPOPMAP(0xcd, 0x01),	/* 0x49: MBOX_GET_VP_DATABASE */
6917 	ISPOPMAP(0x2cd, 0x01),	/* 0x4a: MBOX_GET_VP_DATABASE_ENTRY */
6918 	ISPOPMAP(0x00, 0x00),	/* 0x4b: */
6919 	ISPOPMAP(0x00, 0x00),	/* 0x4c: */
6920 	ISPOPMAP(0x00, 0x00),	/* 0x4d: */
6921 	ISPOPMAP(0x00, 0x00),	/* 0x4e: */
6922 	ISPOPMAP(0x00, 0x00),	/* 0x4f: */
6923 	ISPOPMAP(0x00, 0x00),	/* 0x50: */
6924 	ISPOPMAP(0x00, 0x00),	/* 0x51: */
6925 	ISPOPMAP(0x00, 0x00),	/* 0x52: */
6926 	ISPOPMAP(0x00, 0x00),	/* 0x53: */
6927 	ISPOPMAP(0xcf, 0x01),	/* 0x54: EXECUTE IOCB A64 */
6928 	ISPOPMAP(0x00, 0x00),	/* 0x55: */
6929 	ISPOPMAP(0x00, 0x00),	/* 0x56: */
6930 	ISPOPMAP(0x00, 0x00),	/* 0x57: */
6931 	ISPOPMAP(0x00, 0x00),	/* 0x58: */
6932 	ISPOPMAP(0x00, 0x00),	/* 0x59: */
6933 	ISPOPMAP(0x00, 0x00),	/* 0x5a: */
6934 	ISPOPMAP(0x03, 0x01),	/* 0x5b: MBOX_DRIVER_HEARTBEAT */
6935 	ISPOPMAP(0xcf, 0x01),	/* 0x5c: MBOX_FW_HEARTBEAT */
6936 	ISPOPMAP(0x07, 0x03),	/* 0x5d: MBOX_GET_SET_DATA_RATE */
6937 	ISPOPMAP(0x00, 0x00),	/* 0x5e: */
6938 	ISPOPMAP(0x00, 0x00),	/* 0x5f: */
6939 	ISPOPMAP(0xcd, 0x01),	/* 0x60: MBOX_INIT_FIRMWARE */
6940 	ISPOPMAP(0x00, 0x00),	/* 0x61: */
6941 	ISPOPMAP(0x01, 0x01),	/* 0x62: MBOX_INIT_LIP */
6942 	ISPOPMAP(0xcd, 0x03),	/* 0x63: MBOX_GET_FC_AL_POSITION_MAP */
6943 	ISPOPMAP(0xcf, 0x01),	/* 0x64: MBOX_GET_PORT_DB */
6944 	ISPOPMAP(0x07, 0x01),	/* 0x65: MBOX_CLEAR_ACA */
6945 	ISPOPMAP(0x07, 0x01),	/* 0x66: MBOX_TARGET_RESET */
6946 	ISPOPMAP(0x07, 0x01),	/* 0x67: MBOX_CLEAR_TASK_SET */
6947 	ISPOPMAP(0x07, 0x01),	/* 0x68: MBOX_ABORT_TASK_SET */
6948 	ISPOPMAP(0x01, 0x07),	/* 0x69: MBOX_GET_FW_STATE */
6949 	ISPOPMAP(0x03, 0xcf),	/* 0x6a: MBOX_GET_PORT_NAME */
6950 	ISPOPMAP(0xcf, 0x01),	/* 0x6b: MBOX_GET_LINK_STATUS */
6951 	ISPOPMAP(0x0f, 0x01),	/* 0x6c: MBOX_INIT_LIP_RESET */
6952 	ISPOPMAP(0x00, 0x00),	/* 0x6d: */
6953 	ISPOPMAP(0xcf, 0x03),	/* 0x6e: MBOX_SEND_SNS */
6954 	ISPOPMAP(0x0f, 0x07),	/* 0x6f: MBOX_FABRIC_LOGIN */
6955 	ISPOPMAP(0x03, 0x01),	/* 0x70: MBOX_SEND_CHANGE_REQUEST */
6956 	ISPOPMAP(0x03, 0x03),	/* 0x71: MBOX_FABRIC_LOGOUT */
6957 	ISPOPMAP(0x0f, 0x0f),	/* 0x72: MBOX_INIT_LIP_LOGIN */
6958 	ISPOPMAP(0x00, 0x00),	/* 0x73: */
6959 	ISPOPMAP(0x07, 0x01),	/* 0x74: LOGIN LOOP PORT */
6960 	ISPOPMAP(0xcf, 0x03),	/* 0x75: GET PORT/NODE NAME LIST */
6961 	ISPOPMAP(0x4f, 0x01),	/* 0x76: SET VENDOR ID */
6962 	ISPOPMAP(0xcd, 0x01),	/* 0x77: INITIALIZE IP MAILBOX */
6963 	ISPOPMAP(0x00, 0x00),	/* 0x78: */
6964 	ISPOPMAP(0x00, 0x00),	/* 0x79: */
6965 	ISPOPMAP(0x00, 0x00),	/* 0x7a: */
6966 	ISPOPMAP(0x00, 0x00),	/* 0x7b: */
6967 	ISPOPMAP(0x4f, 0x03),	/* 0x7c: Get ID List */
6968 	ISPOPMAP(0xcf, 0x01),	/* 0x7d: SEND LFA */
6969 	ISPOPMAP(0x0f, 0x01)	/* 0x7e: LUN RESET */
6970 };
6971 /*
6972  * Footnotes
6973  *
6974  * (1): this sets bits 21..16 in mailbox register #8, which we nominally
6975  *	do not access at this time in the core driver. The caller is
6976  *	responsible for setting this register first (Gross!). The assumption
6977  *	is that we won't overflow.
6978  */
6979 
6980 static const char *fc_mbcmd_names[] = {
6981 	"NO-OP",
6982 	"LOAD RAM",
6983 	"EXEC FIRMWARE",
6984 	"DUMP RAM",
6985 	"WRITE RAM WORD",
6986 	"READ RAM WORD",
6987 	"MAILBOX REG TEST",
6988 	"VERIFY CHECKSUM",
6989 	"ABOUT FIRMWARE",
6990 	"LOAD RAM (2100)",
6991 	"DUMP RAM",
6992 	"LOAD RISC RAM",
6993 	NULL,
6994 	"WRITE RAM WORD EXTENDED",
6995 	"CHECK FIRMWARE",
6996 	"READ RAM WORD EXTENDED",
6997 	"INIT REQUEST QUEUE",
6998 	"INIT RESULT QUEUE",
6999 	"EXECUTE IOCB",
7000 	"WAKE UP",
7001 	"STOP FIRMWARE",
7002 	"ABORT",
7003 	"ABORT DEVICE",
7004 	"ABORT TARGET",
7005 	"BUS RESET",
7006 	"STOP QUEUE",
7007 	"START QUEUE",
7008 	"SINGLE STEP QUEUE",
7009 	"ABORT QUEUE",
7010 	"GET DEV QUEUE STATUS",
7011 	NULL,
7012 	"GET FIRMWARE STATUS",
7013 	"GET LOOP ID",
7014 	NULL,
7015 	"GET RETRY COUNT",
7016 	NULL,
7017 	NULL,
7018 	NULL,
7019 	NULL,
7020 	NULL,
7021 	"GET FIRMWARE OPTIONS",
7022 	"GET PORT QUEUE PARAMS",
7023 	NULL,
7024 	NULL,
7025 	NULL,
7026 	NULL,
7027 	NULL,
7028 	NULL,
7029 	NULL,
7030 	NULL,
7031 	"SET RETRY COUNT",
7032 	NULL,
7033 	NULL,
7034 	NULL,
7035 	NULL,
7036 	NULL,
7037 	"SET FIRMWARE OPTIONS",
7038 	"SET PORT QUEUE PARAMS",
7039 	NULL,
7040 	NULL,
7041 	NULL,
7042 	NULL,
7043 	NULL,
7044 	NULL,
7045 	"LOOP PORT BYPASS",
7046 	"LOOP PORT ENABLE",
7047 	"GET RESOURCE COUNT",
7048 	"REQUEST NON PARTICIPATING MODE",
7049 	NULL,
7050 	NULL,
7051 	NULL,
7052 	"GET PORT DATABASE ENHANCED",
7053 	"INIT FIRMWARE MULTI ID",
7054 	"GET VP DATABASE",
7055 	"GET VP DATABASE ENTRY",
7056 	NULL,
7057 	NULL,
7058 	NULL,
7059 	NULL,
7060 	NULL,
7061 	NULL,
7062 	NULL,
7063 	NULL,
7064 	NULL,
7065 	"EXECUTE IOCB A64",
7066 	NULL,
7067 	NULL,
7068 	NULL,
7069 	NULL,
7070 	NULL,
7071 	NULL,
7072 	"DRIVER HEARTBEAT",
7073 	NULL,
7074 	"GET/SET DATA RATE",
7075 	NULL,
7076 	NULL,
7077 	"INIT FIRMWARE",
7078 	NULL,
7079 	"INIT LIP",
7080 	"GET FC-AL POSITION MAP",
7081 	"GET PORT DATABASE",
7082 	"CLEAR ACA",
7083 	"TARGET RESET",
7084 	"CLEAR TASK SET",
7085 	"ABORT TASK SET",
7086 	"GET FW STATE",
7087 	"GET PORT NAME",
7088 	"GET LINK STATUS",
7089 	"INIT LIP RESET",
7090 	NULL,
7091 	"SEND SNS",
7092 	"FABRIC LOGIN",
7093 	"SEND CHANGE REQUEST",
7094 	"FABRIC LOGOUT",
7095 	"INIT LIP LOGIN",
7096 	NULL,
7097 	"LOGIN LOOP PORT",
7098 	"GET PORT/NODE NAME LIST",
7099 	"SET VENDOR ID",
7100 	"INITIALIZE IP MAILBOX",
7101 	NULL,
7102 	NULL,
7103 	NULL,
7104 	NULL,
7105 	"Get ID List",
7106 	"SEND LFA",
7107 	"Lun RESET"
7108 };
7109 
7110 static void
7111 isp_mboxcmd_qnw(ispsoftc_t *isp, mbreg_t *mbp, int nodelay)
7112 {
7113 	unsigned int ibits, obits, box, opcode;
7114 	const uint32_t *mcp;
7115 
7116 	if (IS_FC(isp)) {
7117 		mcp = mbpfc;
7118 	} else {
7119 		mcp = mbpscsi;
7120 	}
7121 	opcode = mbp->param[0];
7122 	ibits = HIWRD(mcp[opcode]) & NMBOX_BMASK(isp);
7123 	obits = LOWRD(mcp[opcode]) & NMBOX_BMASK(isp);
7124 	ibits |= mbp->ibits;
7125 	obits |= mbp->obits;
7126 	for (box = 0; box < MAX_MAILBOX(isp); box++) {
7127 		if (ibits & (1 << box)) {
7128 			ISP_WRITE(isp, MBOX_OFF(box), mbp->param[box]);
7129 		}
7130 		if (nodelay == 0) {
7131 			isp->isp_mboxtmp[box] = mbp->param[box] = 0;
7132 		}
7133 	}
7134 	if (nodelay == 0) {
7135 		isp->isp_lastmbxcmd = opcode;
7136 		isp->isp_obits = obits;
7137 		isp->isp_mboxbsy = 1;
7138 	}
7139 	if (IS_24XX(isp)) {
7140 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_SET_HOST_INT);
7141 	} else {
7142 		ISP_WRITE(isp, HCCR, HCCR_CMD_SET_HOST_INT);
7143 	}
7144 	/*
7145 	 * Oddly enough, if we're not delaying for an answer,
7146 	 * delay a bit to give the f/w a chance to pick up the
7147 	 * command.
7148 	 */
7149 	if (nodelay) {
7150 		ISP_DELAY(1000);
7151 	}
7152 }
7153 
7154 static void
7155 isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
7156 {
7157 	const char *cname, *xname;
7158 	char tname[16], mname[16];
7159 	unsigned int lim, ibits, obits, box, opcode;
7160 	const uint32_t *mcp;
7161 
7162 	if (IS_FC(isp)) {
7163 		mcp = mbpfc;
7164 		lim = NELEM(mbpfc);
7165 	} else {
7166 		mcp = mbpscsi;
7167 		lim = NELEM(mbpscsi);
7168 	}
7169 
7170 	if ((opcode = mbp->param[0]) >= lim) {
7171 		mbp->param[0] = MBOX_INVALID_COMMAND;
7172 		isp_prt(isp, ISP_LOGERR, "Unknown Command 0x%x", opcode);
7173 		return;
7174 	}
7175 
7176 	ibits = HIWRD(mcp[opcode]) & NMBOX_BMASK(isp);
7177 	obits = LOWRD(mcp[opcode]) & NMBOX_BMASK(isp);
7178 
7179 	/*
7180 	 * Pick up any additional bits that the caller might have set.
7181 	 */
7182 	ibits |= mbp->ibits;
7183 	obits |= mbp->obits;
7184 
7185 	if (ibits == 0 && obits == 0) {
7186 		mbp->param[0] = MBOX_COMMAND_PARAM_ERROR;
7187 		isp_prt(isp, ISP_LOGERR, "no parameters for 0x%x", opcode);
7188 		return;
7189 	}
7190 
7191 	/*
7192 	 * Get exclusive usage of mailbox registers.
7193 	 */
7194 	if (MBOX_ACQUIRE(isp)) {
7195 		mbp->param[0] = MBOX_REGS_BUSY;
7196 		goto out;
7197 	}
7198 
7199 	for (box = 0; box < MAX_MAILBOX(isp); box++) {
7200 		if (ibits & (1 << box)) {
7201 			isp_prt(isp, ISP_LOGDEBUG3, "IN mbox %d = 0x%04x", box,
7202 			    mbp->param[box]);
7203 			ISP_WRITE(isp, MBOX_OFF(box), mbp->param[box]);
7204 		}
7205 		isp->isp_mboxtmp[box] = mbp->param[box] = 0;
7206 	}
7207 
7208 	isp->isp_lastmbxcmd = opcode;
7209 
7210 	/*
7211 	 * We assume that we can't overwrite a previous command.
7212 	 */
7213 	isp->isp_obits = obits;
7214 	isp->isp_mboxbsy = 1;
7215 
7216 	/*
7217 	 * Set Host Interrupt condition so that RISC will pick up mailbox regs.
7218 	 */
7219 	if (IS_24XX(isp)) {
7220 		ISP_WRITE(isp, BIU2400_HCCR, HCCR_2400_CMD_SET_HOST_INT);
7221 	} else {
7222 		ISP_WRITE(isp, HCCR, HCCR_CMD_SET_HOST_INT);
7223 	}
7224 
7225 	/*
7226 	 * While we haven't finished the command, spin our wheels here.
7227 	 */
7228 	MBOX_WAIT_COMPLETE(isp, mbp);
7229 
7230 	/*
7231 	 * Did the command time out?
7232 	 */
7233 	if (mbp->param[0] == MBOX_TIMEOUT) {
7234 		isp->isp_mboxbsy = 0;
7235 		MBOX_RELEASE(isp);
7236 		goto out;
7237 	}
7238 
7239 	/*
7240 	 * Copy back output registers.
7241 	 */
7242 	for (box = 0; box < MAX_MAILBOX(isp); box++) {
7243 		if (obits & (1 << box)) {
7244 			mbp->param[box] = isp->isp_mboxtmp[box];
7245 			isp_prt(isp, ISP_LOGDEBUG3, "OUT mbox %d = 0x%04x", box,
7246 			    mbp->param[box]);
7247 		}
7248 	}
7249 
7250 	isp->isp_mboxbsy = 0;
7251 	MBOX_RELEASE(isp);
7252  out:
7253 	if (mbp->logval == 0 || opcode == MBOX_EXEC_FIRMWARE) {
7254 		return;
7255 	}
7256 	cname = (IS_FC(isp))? fc_mbcmd_names[opcode] : scsi_mbcmd_names[opcode];
7257 	if (cname == NULL) {
7258 		cname = tname;
7259 		ISP_SNPRINTF(tname, sizeof tname, "opcode %x", opcode);
7260 	}
7261 
7262 	/*
7263 	 * Just to be chatty here...
7264 	 */
7265 	xname = NULL;
7266 	switch (mbp->param[0]) {
7267 	case MBOX_COMMAND_COMPLETE:
7268 		break;
7269 	case MBOX_INVALID_COMMAND:
7270 		if (mbp->logval & MBLOGMASK(MBOX_COMMAND_COMPLETE)) {
7271 			xname = "INVALID COMMAND";
7272 		}
7273 		break;
7274 	case MBOX_HOST_INTERFACE_ERROR:
7275 		if (mbp->logval & MBLOGMASK(MBOX_HOST_INTERFACE_ERROR)) {
7276 			xname = "HOST INTERFACE ERROR";
7277 		}
7278 		break;
7279 	case MBOX_TEST_FAILED:
7280 		if (mbp->logval & MBLOGMASK(MBOX_TEST_FAILED)) {
7281 			xname = "TEST FAILED";
7282 		}
7283 		break;
7284 	case MBOX_COMMAND_ERROR:
7285 		if (mbp->logval & MBLOGMASK(MBOX_COMMAND_ERROR)) {
7286 			xname = "COMMAND ERROR";
7287 		}
7288 		break;
7289 	case MBOX_COMMAND_PARAM_ERROR:
7290 		if (mbp->logval & MBLOGMASK(MBOX_COMMAND_PARAM_ERROR)) {
7291 			xname = "COMMAND PARAMETER ERROR";
7292 		}
7293 		break;
7294 	case MBOX_LOOP_ID_USED:
7295 		if (mbp->logval & MBLOGMASK(MBOX_LOOP_ID_USED)) {
7296 			xname = "LOOP ID ALREADY IN USE";
7297 		}
7298 		break;
7299 	case MBOX_PORT_ID_USED:
7300 		if (mbp->logval & MBLOGMASK(MBOX_PORT_ID_USED)) {
7301 			xname = "PORT ID ALREADY IN USE";
7302 		}
7303 		break;
7304 	case MBOX_ALL_IDS_USED:
7305 		if (mbp->logval & MBLOGMASK(MBOX_ALL_IDS_USED)) {
7306 			xname = "ALL LOOP IDS IN USE";
7307 		}
7308 		break;
7309 	case MBOX_REGS_BUSY:
7310 		xname = "REGISTERS BUSY";
7311 		break;
7312 	case MBOX_TIMEOUT:
7313 		xname = "TIMEOUT";
7314 		break;
7315 	default:
7316 		ISP_SNPRINTF(mname, sizeof mname, "error 0x%x", mbp->param[0]);
7317 		xname = mname;
7318 		break;
7319 	}
7320 	if (xname) {
7321 		isp_prt(isp, ISP_LOGALL, "Mailbox Command '%s' failed (%s)",
7322 		    cname, xname);
7323 	}
7324 }
7325 
7326 static void
7327 isp_fw_state(ispsoftc_t *isp, int chan)
7328 {
7329 	if (IS_FC(isp)) {
7330 		mbreg_t mbs;
7331 		fcparam *fcp = FCPARAM(isp, chan);
7332 
7333 		MBSINIT(&mbs, MBOX_GET_FW_STATE, MBLOGALL, 0);
7334 		isp_mboxcmd(isp, &mbs);
7335 		if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
7336 			fcp->isp_fwstate = mbs.param[1];
7337 		}
7338 	}
7339 }
7340 
7341 static void
7342 isp_spi_update(ispsoftc_t *isp, int chan)
7343 {
7344 	int tgt;
7345 	mbreg_t mbs;
7346 	sdparam *sdp;
7347 
7348 	if (IS_FC(isp)) {
7349 		/*
7350 		 * There are no 'per-bus' settings for Fibre Channel.
7351 		 */
7352 		return;
7353 	}
7354 	sdp = SDPARAM(isp, chan);
7355 	sdp->update = 0;
7356 
7357 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
7358 		uint16_t flags, period, offset;
7359 		int get;
7360 
7361 		if (sdp->isp_devparam[tgt].dev_enable == 0) {
7362 			sdp->isp_devparam[tgt].dev_update = 0;
7363 			sdp->isp_devparam[tgt].dev_refresh = 0;
7364 			isp_prt(isp, ISP_LOGDEBUG0, "skipping target %d bus %d update", tgt, chan);
7365 			continue;
7366 		}
7367 		/*
7368 		 * If the goal is to update the status of the device,
7369 		 * take what's in goal_flags and try and set the device
7370 		 * toward that. Otherwise, if we're just refreshing the
7371 		 * current device state, get the current parameters.
7372 		 */
7373 
7374 		MBSINIT(&mbs, 0, MBLOGALL, 0);
7375 
7376 		/*
7377 		 * Refresh overrides set
7378 		 */
7379 		if (sdp->isp_devparam[tgt].dev_refresh) {
7380 			mbs.param[0] = MBOX_GET_TARGET_PARAMS;
7381 			get = 1;
7382 		} else if (sdp->isp_devparam[tgt].dev_update) {
7383 			mbs.param[0] = MBOX_SET_TARGET_PARAMS;
7384 
7385 			/*
7386 			 * Make sure goal_flags has "Renegotiate on Error"
7387 			 * on and "Freeze Queue on Error" off.
7388 			 */
7389 			sdp->isp_devparam[tgt].goal_flags |= DPARM_RENEG;
7390 			sdp->isp_devparam[tgt].goal_flags &= ~DPARM_QFRZ;
7391 			mbs.param[2] = sdp->isp_devparam[tgt].goal_flags;
7392 
7393 			/*
7394 			 * Insist that PARITY must be enabled
7395 			 * if SYNC or WIDE is enabled.
7396 			 */
7397 			if ((mbs.param[2] & (DPARM_SYNC|DPARM_WIDE)) != 0) {
7398 				mbs.param[2] |= DPARM_PARITY;
7399 			}
7400 
7401 			if (mbs.param[2] & DPARM_SYNC) {
7402 				mbs.param[3] =
7403 				    (sdp->isp_devparam[tgt].goal_offset << 8) |
7404 				    (sdp->isp_devparam[tgt].goal_period);
7405 			}
7406 			/*
7407 			 * A command completion later that has
7408 			 * RQSTF_NEGOTIATION set can cause
7409 			 * the dev_refresh/announce cycle also.
7410 			 *
7411 			 * Note: It is really important to update our current
7412 			 * flags with at least the state of TAG capabilities-
7413 			 * otherwise we might try and send a tagged command
7414 			 * when we have it all turned off. So change it here
7415 			 * to say that current already matches goal.
7416 			 */
7417 			sdp->isp_devparam[tgt].actv_flags &= ~DPARM_TQING;
7418 			sdp->isp_devparam[tgt].actv_flags |=
7419 			    (sdp->isp_devparam[tgt].goal_flags & DPARM_TQING);
7420 			isp_prt(isp, ISP_LOGDEBUG0, "bus %d set tgt %d flags 0x%x off 0x%x period 0x%x",
7421 			    chan, tgt, mbs.param[2], mbs.param[3] >> 8, mbs.param[3] & 0xff);
7422 			get = 0;
7423 		} else {
7424 			continue;
7425 		}
7426 		mbs.param[1] = (chan << 15) | (tgt << 8);
7427 		isp_mboxcmd(isp, &mbs);
7428 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
7429 			continue;
7430 		}
7431 		if (get == 0) {
7432 			sdp->sendmarker = 1;
7433 			sdp->isp_devparam[tgt].dev_update = 0;
7434 			sdp->isp_devparam[tgt].dev_refresh = 1;
7435 		} else {
7436 			sdp->isp_devparam[tgt].dev_refresh = 0;
7437 			flags = mbs.param[2];
7438 			period = mbs.param[3] & 0xff;
7439 			offset = mbs.param[3] >> 8;
7440 			sdp->isp_devparam[tgt].actv_flags = flags;
7441 			sdp->isp_devparam[tgt].actv_period = period;
7442 			sdp->isp_devparam[tgt].actv_offset = offset;
7443 			isp_async(isp, ISPASYNC_NEW_TGT_PARAMS, chan, tgt);
7444 		}
7445 	}
7446 
7447 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
7448 		if (sdp->isp_devparam[tgt].dev_update ||
7449 		    sdp->isp_devparam[tgt].dev_refresh) {
7450 			sdp->update = 1;
7451 			break;
7452 		}
7453 	}
7454 }
7455 
7456 static void
7457 isp_setdfltsdparm(ispsoftc_t *isp)
7458 {
7459 	int tgt;
7460 	sdparam *sdp, *sdp1;
7461 
7462 	sdp = SDPARAM(isp, 0);
7463 	sdp->role = GET_DEFAULT_ROLE(isp, 0);
7464 	if (IS_DUALBUS(isp)) {
7465 		sdp1 = sdp + 1;
7466 		sdp1->role = GET_DEFAULT_ROLE(isp, 1);
7467 	} else {
7468 		sdp1 = NULL;
7469 	}
7470 
7471 	/*
7472 	 * Establish some default parameters.
7473 	 */
7474 	sdp->isp_cmd_dma_burst_enable = 0;
7475 	sdp->isp_data_dma_burst_enabl = 1;
7476 	sdp->isp_fifo_threshold = 0;
7477 	sdp->isp_initiator_id = DEFAULT_IID(isp, 0);
7478 	if (isp->isp_type >= ISP_HA_SCSI_1040) {
7479 		sdp->isp_async_data_setup = 9;
7480 	} else {
7481 		sdp->isp_async_data_setup = 6;
7482 	}
7483 	sdp->isp_selection_timeout = 250;
7484 	sdp->isp_max_queue_depth = MAXISPREQUEST(isp);
7485 	sdp->isp_tag_aging = 8;
7486 	sdp->isp_bus_reset_delay = 5;
7487 	/*
7488 	 * Don't retry selection, busy or queue full automatically- reflect
7489 	 * these back to us.
7490 	 */
7491 	sdp->isp_retry_count = 0;
7492 	sdp->isp_retry_delay = 0;
7493 
7494 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
7495 		sdp->isp_devparam[tgt].exc_throttle = ISP_EXEC_THROTTLE;
7496 		sdp->isp_devparam[tgt].dev_enable = 1;
7497 	}
7498 
7499 	/*
7500 	 * The trick here is to establish a default for the default (honk!)
7501 	 * state (goal_flags). Then try and get the current status from
7502 	 * the card to fill in the current state. We don't, in fact, set
7503 	 * the default to the SAFE default state- that's not the goal state.
7504 	 */
7505 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
7506 		uint8_t off, per;
7507 		sdp->isp_devparam[tgt].actv_offset = 0;
7508 		sdp->isp_devparam[tgt].actv_period = 0;
7509 		sdp->isp_devparam[tgt].actv_flags = 0;
7510 
7511 		sdp->isp_devparam[tgt].goal_flags =
7512 		    sdp->isp_devparam[tgt].nvrm_flags = DPARM_DEFAULT;
7513 
7514 		/*
7515 		 * We default to Wide/Fast for versions less than a 1040
7516 		 * (unless it's SBus).
7517 		 */
7518 		if (IS_ULTRA3(isp)) {
7519 			off = ISP_80M_SYNCPARMS >> 8;
7520 			per = ISP_80M_SYNCPARMS & 0xff;
7521 		} else if (IS_ULTRA2(isp)) {
7522 			off = ISP_40M_SYNCPARMS >> 8;
7523 			per = ISP_40M_SYNCPARMS & 0xff;
7524 		} else if (IS_1240(isp)) {
7525 			off = ISP_20M_SYNCPARMS >> 8;
7526 			per = ISP_20M_SYNCPARMS & 0xff;
7527 		} else if ((isp->isp_bustype == ISP_BT_SBUS &&
7528 		    isp->isp_type < ISP_HA_SCSI_1020A) ||
7529 		    (isp->isp_bustype == ISP_BT_PCI &&
7530 		    isp->isp_type < ISP_HA_SCSI_1040) ||
7531 		    (isp->isp_clock && isp->isp_clock < 60) ||
7532 		    (sdp->isp_ultramode == 0)) {
7533 			off = ISP_10M_SYNCPARMS >> 8;
7534 			per = ISP_10M_SYNCPARMS & 0xff;
7535 		} else {
7536 			off = ISP_20M_SYNCPARMS_1040 >> 8;
7537 			per = ISP_20M_SYNCPARMS_1040 & 0xff;
7538 		}
7539 		sdp->isp_devparam[tgt].goal_offset =
7540 		    sdp->isp_devparam[tgt].nvrm_offset = off;
7541 		sdp->isp_devparam[tgt].goal_period =
7542 		    sdp->isp_devparam[tgt].nvrm_period = per;
7543 
7544 	}
7545 
7546 	/*
7547 	 * If we're a dual bus card, just copy the data over
7548 	 */
7549 	if (sdp1) {
7550 		*sdp1 = *sdp;
7551 		sdp1->isp_initiator_id = DEFAULT_IID(isp, 1);
7552 	}
7553 
7554 	/*
7555 	 * If we've not been told to avoid reading NVRAM, try and read it.
7556 	 * If we're successful reading it, we can then return because NVRAM
7557 	 * will tell us what the desired settings are. Otherwise, we establish
7558 	 * some reasonable 'fake' nvram and goal defaults.
7559 	 */
7560 	if ((isp->isp_confopts & ISP_CFG_NONVRAM) == 0) {
7561 		mbreg_t mbs;
7562 
7563 		if (isp_read_nvram(isp, 0) == 0) {
7564 			if (IS_DUALBUS(isp)) {
7565 				if (isp_read_nvram(isp, 1) == 0) {
7566 					return;
7567 				}
7568 			}
7569 		}
7570 		MBSINIT(&mbs, MBOX_GET_ACT_NEG_STATE, MBLOGNONE, 0);
7571 		isp_mboxcmd(isp, &mbs);
7572 		if (mbs.param[0] != MBOX_COMMAND_COMPLETE) {
7573 			sdp->isp_req_ack_active_neg = 1;
7574 			sdp->isp_data_line_active_neg = 1;
7575 			if (sdp1) {
7576 				sdp1->isp_req_ack_active_neg = 1;
7577 				sdp1->isp_data_line_active_neg = 1;
7578 			}
7579 		} else {
7580 			sdp->isp_req_ack_active_neg =
7581 			    (mbs.param[1] >> 4) & 0x1;
7582 			sdp->isp_data_line_active_neg =
7583 			    (mbs.param[1] >> 5) & 0x1;
7584 			if (sdp1) {
7585 				sdp1->isp_req_ack_active_neg =
7586 				    (mbs.param[2] >> 4) & 0x1;
7587 				sdp1->isp_data_line_active_neg =
7588 				    (mbs.param[2] >> 5) & 0x1;
7589 			}
7590 		}
7591 	}
7592 
7593 }
7594 
7595 static void
7596 isp_setdfltfcparm(ispsoftc_t *isp, int chan)
7597 {
7598 	fcparam *fcp = FCPARAM(isp, chan);
7599 
7600 	/*
7601 	 * Establish some default parameters.
7602 	 */
7603 	fcp->role = GET_DEFAULT_ROLE(isp, chan);
7604 	fcp->isp_maxalloc = ICB_DFLT_ALLOC;
7605 	fcp->isp_retry_delay = ICB_DFLT_RDELAY;
7606 	fcp->isp_retry_count = ICB_DFLT_RCOUNT;
7607 	fcp->isp_loopid = DEFAULT_LOOPID(isp, chan);
7608 	fcp->isp_wwnn_nvram = DEFAULT_NODEWWN(isp, chan);
7609 	fcp->isp_wwpn_nvram = DEFAULT_PORTWWN(isp, chan);
7610 	fcp->isp_fwoptions = 0;
7611 	fcp->isp_lasthdl = NIL_HANDLE;
7612 
7613 	if (IS_24XX(isp)) {
7614 		fcp->isp_fwoptions |= ICB2400_OPT1_FAIRNESS;
7615 		fcp->isp_fwoptions |= ICB2400_OPT1_HARD_ADDRESS;
7616 		if (isp->isp_confopts & ISP_CFG_FULL_DUPLEX) {
7617 			fcp->isp_fwoptions |= ICB2400_OPT1_FULL_DUPLEX;
7618 		}
7619 		fcp->isp_fwoptions |= ICB2400_OPT1_BOTH_WWNS;
7620 	} else {
7621 		fcp->isp_fwoptions |= ICBOPT_FAIRNESS;
7622 		fcp->isp_fwoptions |= ICBOPT_PDBCHANGE_AE;
7623 		fcp->isp_fwoptions |= ICBOPT_HARD_ADDRESS;
7624 		if (isp->isp_confopts & ISP_CFG_FULL_DUPLEX) {
7625 			fcp->isp_fwoptions |= ICBOPT_FULL_DUPLEX;
7626 		}
7627 		/*
7628 		 * Make sure this is turned off now until we get
7629 		 * extended options from NVRAM
7630 		 */
7631 		fcp->isp_fwoptions &= ~ICBOPT_EXTENDED;
7632 	}
7633 
7634 
7635 	/*
7636 	 * Now try and read NVRAM unless told to not do so.
7637 	 * This will set fcparam's isp_wwnn_nvram && isp_wwpn_nvram.
7638 	 */
7639 	if ((isp->isp_confopts & ISP_CFG_NONVRAM) == 0) {
7640 		int i, j = 0;
7641 		/*
7642 		 * Give a couple of tries at reading NVRAM.
7643 		 */
7644 		for (i = 0; i < 2; i++) {
7645 			j = isp_read_nvram(isp, chan);
7646 			if (j == 0) {
7647 				break;
7648 			}
7649 		}
7650 		if (j) {
7651 			isp->isp_confopts |= ISP_CFG_NONVRAM;
7652 		}
7653 	}
7654 
7655 	fcp->isp_wwnn = ACTIVE_NODEWWN(isp, chan);
7656 	fcp->isp_wwpn = ACTIVE_PORTWWN(isp, chan);
7657 	isp_prt(isp, ISP_LOGCONFIG, "Chan %d 0x%08x%08x/0x%08x%08x Role %s",
7658 	    chan, (uint32_t) (fcp->isp_wwnn >> 32), (uint32_t) (fcp->isp_wwnn),
7659 	    (uint32_t) (fcp->isp_wwpn >> 32), (uint32_t) (fcp->isp_wwpn),
7660 	    isp_class3_roles[fcp->role]);
7661 }
7662 
7663 /*
7664  * Re-initialize the ISP and complete all orphaned commands
7665  * with a 'botched' notice. The reset/init routines should
7666  * not disturb an already active list of commands.
7667  */
7668 
7669 void
7670 isp_reinit(ispsoftc_t *isp, int do_load_defaults)
7671 {
7672 	int i;
7673 
7674 	isp_reset(isp, do_load_defaults);
7675 
7676 	if (isp->isp_state != ISP_RESETSTATE) {
7677 		isp_prt(isp, ISP_LOGERR, "%s: cannot reset card", __func__);
7678 		ISP_DISABLE_INTS(isp);
7679 		goto cleanup;
7680 	}
7681 
7682 	isp_init(isp);
7683 
7684 	if (isp->isp_state == ISP_INITSTATE) {
7685 		isp->isp_state = ISP_RUNSTATE;
7686 	}
7687 
7688 	if (isp->isp_state != ISP_RUNSTATE) {
7689 #ifndef	ISP_TARGET_MODE
7690 		isp_prt(isp, ISP_LOGWARN, "%s: not at runstate", __func__);
7691 #endif
7692 		ISP_DISABLE_INTS(isp);
7693 		if (IS_FC(isp)) {
7694 			/*
7695 			 * If we're in ISP_ROLE_NONE, turn off the lasers.
7696 			 */
7697 			if (!IS_24XX(isp)) {
7698 				ISP_WRITE(isp, BIU2100_CSR, BIU2100_FPM0_REGS);
7699 				ISP_WRITE(isp, FPM_DIAG_CONFIG, FPM_SOFT_RESET);
7700 				ISP_WRITE(isp, BIU2100_CSR, BIU2100_FB_REGS);
7701 				ISP_WRITE(isp, FBM_CMD, FBMCMD_FIFO_RESET_ALL);
7702 				ISP_WRITE(isp, BIU2100_CSR, BIU2100_RISC_REGS);
7703 			}
7704 		}
7705 	}
7706 
7707  cleanup:
7708 
7709 	isp->isp_nactive = 0;
7710 
7711 	isp_clear_commands(isp);
7712 	if (IS_FC(isp)) {
7713 		for (i = 0; i < isp->isp_nchan; i++) {
7714 			ISP_MARK_PORTDB(isp, i, -1);
7715 		}
7716 	}
7717 }
7718 
7719 /*
7720  * NVRAM Routines
7721  */
7722 static int
7723 isp_read_nvram(ispsoftc_t *isp, int bus)
7724 {
7725 	int i, amt, retval;
7726 	uint8_t csum, minversion;
7727 	union {
7728 		uint8_t _x[ISP2400_NVRAM_SIZE];
7729 		uint16_t _s[ISP2400_NVRAM_SIZE>>1];
7730 	} _n;
7731 #define	nvram_data	_n._x
7732 #define	nvram_words	_n._s
7733 
7734 	if (IS_24XX(isp)) {
7735 		return (isp_read_nvram_2400(isp, nvram_data));
7736 	} else if (IS_FC(isp)) {
7737 		amt = ISP2100_NVRAM_SIZE;
7738 		minversion = 1;
7739 	} else if (IS_ULTRA2(isp)) {
7740 		amt = ISP1080_NVRAM_SIZE;
7741 		minversion = 0;
7742 	} else {
7743 		amt = ISP_NVRAM_SIZE;
7744 		minversion = 2;
7745 	}
7746 
7747 	for (i = 0; i < amt>>1; i++) {
7748 		isp_rdnvram_word(isp, i, &nvram_words[i]);
7749 	}
7750 
7751 	if (nvram_data[0] != 'I' || nvram_data[1] != 'S' ||
7752 	    nvram_data[2] != 'P') {
7753 		if (isp->isp_bustype != ISP_BT_SBUS) {
7754 			isp_prt(isp, ISP_LOGWARN, "invalid NVRAM header");
7755 			isp_prt(isp, ISP_LOGDEBUG0, "%x %x %x", nvram_data[0], nvram_data[1], nvram_data[2]);
7756 		}
7757 		retval = -1;
7758 		goto out;
7759 	}
7760 
7761 	for (csum = 0, i = 0; i < amt; i++) {
7762 		csum += nvram_data[i];
7763 	}
7764 	if (csum != 0) {
7765 		isp_prt(isp, ISP_LOGWARN, "invalid NVRAM checksum");
7766 		retval = -1;
7767 		goto out;
7768 	}
7769 
7770 	if (ISP_NVRAM_VERSION(nvram_data) < minversion) {
7771 		isp_prt(isp, ISP_LOGWARN, "version %d NVRAM not understood",
7772 		    ISP_NVRAM_VERSION(nvram_data));
7773 		retval = -1;
7774 		goto out;
7775 	}
7776 
7777 	if (IS_ULTRA3(isp)) {
7778 		isp_parse_nvram_12160(isp, bus, nvram_data);
7779 	} else if (IS_1080(isp)) {
7780 		isp_parse_nvram_1080(isp, bus, nvram_data);
7781 	} else if (IS_1280(isp) || IS_1240(isp)) {
7782 		isp_parse_nvram_1080(isp, bus, nvram_data);
7783 	} else if (IS_SCSI(isp)) {
7784 		isp_parse_nvram_1020(isp, nvram_data);
7785 	} else {
7786 		isp_parse_nvram_2100(isp, nvram_data);
7787 	}
7788 	retval = 0;
7789 out:
7790 	return (retval);
7791 #undef	nvram_data
7792 #undef	nvram_words
7793 }
7794 
7795 static int
7796 isp_read_nvram_2400(ispsoftc_t *isp, uint8_t *nvram_data)
7797 {
7798 	int retval = 0;
7799 	uint32_t addr, csum, lwrds, *dptr;
7800 
7801 	if (isp->isp_port) {
7802 		addr = ISP2400_NVRAM_PORT1_ADDR;
7803 	} else {
7804 		addr = ISP2400_NVRAM_PORT0_ADDR;
7805 	}
7806 
7807 	dptr = (uint32_t *) nvram_data;
7808 	for (lwrds = 0; lwrds < ISP2400_NVRAM_SIZE >> 2; lwrds++) {
7809 		isp_rd_2400_nvram(isp, addr++, dptr++);
7810 	}
7811 	if (nvram_data[0] != 'I' || nvram_data[1] != 'S' ||
7812 	    nvram_data[2] != 'P') {
7813 		isp_prt(isp, ISP_LOGWARN, "invalid NVRAM header (%x %x %x)",
7814 		    nvram_data[0], nvram_data[1], nvram_data[2]);
7815 		retval = -1;
7816 		goto out;
7817 	}
7818 	dptr = (uint32_t *) nvram_data;
7819 	for (csum = 0, lwrds = 0; lwrds < ISP2400_NVRAM_SIZE >> 2; lwrds++) {
7820 		uint32_t tmp;
7821 		ISP_IOXGET_32(isp, &dptr[lwrds], tmp);
7822 		csum += tmp;
7823 	}
7824 	if (csum != 0) {
7825 		isp_prt(isp, ISP_LOGWARN, "invalid NVRAM checksum");
7826 		retval = -1;
7827 		goto out;
7828 	}
7829 	isp_parse_nvram_2400(isp, nvram_data);
7830 out:
7831 	return (retval);
7832 }
7833 
7834 static void
7835 isp_rdnvram_word(ispsoftc_t *isp, int wo, uint16_t *rp)
7836 {
7837 	int i, cbits;
7838 	uint16_t bit, rqst, junk;
7839 
7840 	ISP_WRITE(isp, BIU_NVRAM, BIU_NVRAM_SELECT);
7841 	ISP_DELAY(10);
7842 	ISP_WRITE(isp, BIU_NVRAM, BIU_NVRAM_SELECT|BIU_NVRAM_CLOCK);
7843 	ISP_DELAY(10);
7844 
7845 	if (IS_FC(isp)) {
7846 		wo &= ((ISP2100_NVRAM_SIZE >> 1) - 1);
7847 		if (IS_2312(isp) && isp->isp_port) {
7848 			wo += 128;
7849 		}
7850 		rqst = (ISP_NVRAM_READ << 8) | wo;
7851 		cbits = 10;
7852 	} else if (IS_ULTRA2(isp)) {
7853 		wo &= ((ISP1080_NVRAM_SIZE >> 1) - 1);
7854 		rqst = (ISP_NVRAM_READ << 8) | wo;
7855 		cbits = 10;
7856 	} else {
7857 		wo &= ((ISP_NVRAM_SIZE >> 1) - 1);
7858 		rqst = (ISP_NVRAM_READ << 6) | wo;
7859 		cbits = 8;
7860 	}
7861 
7862 	/*
7863 	 * Clock the word select request out...
7864 	 */
7865 	for (i = cbits; i >= 0; i--) {
7866 		if ((rqst >> i) & 1) {
7867 			bit = BIU_NVRAM_SELECT | BIU_NVRAM_DATAOUT;
7868 		} else {
7869 			bit = BIU_NVRAM_SELECT;
7870 		}
7871 		ISP_WRITE(isp, BIU_NVRAM, bit);
7872 		ISP_DELAY(10);
7873 		junk = ISP_READ(isp, BIU_NVRAM);	/* force PCI flush */
7874 		ISP_WRITE(isp, BIU_NVRAM, bit | BIU_NVRAM_CLOCK);
7875 		ISP_DELAY(10);
7876 		junk = ISP_READ(isp, BIU_NVRAM);	/* force PCI flush */
7877 		ISP_WRITE(isp, BIU_NVRAM, bit);
7878 		ISP_DELAY(10);
7879 		junk = ISP_READ(isp, BIU_NVRAM);	/* force PCI flush */
7880 	}
7881 	/*
7882 	 * Now read the result back in (bits come back in MSB format).
7883 	 */
7884 	*rp = 0;
7885 	for (i = 0; i < 16; i++) {
7886 		uint16_t rv;
7887 		*rp <<= 1;
7888 		ISP_WRITE(isp, BIU_NVRAM, BIU_NVRAM_SELECT|BIU_NVRAM_CLOCK);
7889 		ISP_DELAY(10);
7890 		rv = ISP_READ(isp, BIU_NVRAM);
7891 		if (rv & BIU_NVRAM_DATAIN) {
7892 			*rp |= 1;
7893 		}
7894 		ISP_DELAY(10);
7895 		ISP_WRITE(isp, BIU_NVRAM, BIU_NVRAM_SELECT);
7896 		ISP_DELAY(10);
7897 		junk = ISP_READ(isp, BIU_NVRAM);	/* force PCI flush */
7898 	}
7899 	ISP_WRITE(isp, BIU_NVRAM, 0);
7900 	ISP_DELAY(10);
7901 	junk = ISP_READ(isp, BIU_NVRAM);	/* force PCI flush */
7902 	ISP_SWIZZLE_NVRAM_WORD(isp, rp);
7903 }
7904 
7905 static void
7906 isp_rd_2400_nvram(ispsoftc_t *isp, uint32_t addr, uint32_t *rp)
7907 {
7908 	int loops = 0;
7909 	uint32_t base = 0x7ffe0000;
7910 	uint32_t tmp = 0;
7911 
7912 	if (IS_25XX(isp)) {
7913 		base = 0x7ff00000 | 0x48000;
7914 	}
7915 	ISP_WRITE(isp, BIU2400_FLASH_ADDR, base | addr);
7916 	for (loops = 0; loops < 5000; loops++) {
7917 		ISP_DELAY(10);
7918 		tmp = ISP_READ(isp, BIU2400_FLASH_ADDR);
7919 		if ((tmp & (1U << 31)) != 0) {
7920 			break;
7921 		}
7922 	}
7923 	if (tmp & (1U << 31)) {
7924 		*rp = ISP_READ(isp, BIU2400_FLASH_DATA);
7925 		ISP_SWIZZLE_NVRAM_LONG(isp, rp);
7926 	} else {
7927 		*rp = 0xffffffff;
7928 	}
7929 }
7930 
7931 static void
7932 isp_parse_nvram_1020(ispsoftc_t *isp, uint8_t *nvram_data)
7933 {
7934 	sdparam *sdp = SDPARAM(isp, 0);
7935 	int tgt;
7936 
7937 	sdp->isp_fifo_threshold =
7938 		ISP_NVRAM_FIFO_THRESHOLD(nvram_data) |
7939 		(ISP_NVRAM_FIFO_THRESHOLD_128(nvram_data) << 2);
7940 
7941 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0)
7942 		sdp->isp_initiator_id =
7943 			ISP_NVRAM_INITIATOR_ID(nvram_data);
7944 
7945 	sdp->isp_bus_reset_delay =
7946 		ISP_NVRAM_BUS_RESET_DELAY(nvram_data);
7947 
7948 	sdp->isp_retry_count =
7949 		ISP_NVRAM_BUS_RETRY_COUNT(nvram_data);
7950 
7951 	sdp->isp_retry_delay =
7952 		ISP_NVRAM_BUS_RETRY_DELAY(nvram_data);
7953 
7954 	sdp->isp_async_data_setup =
7955 		ISP_NVRAM_ASYNC_DATA_SETUP_TIME(nvram_data);
7956 
7957 	if (isp->isp_type >= ISP_HA_SCSI_1040) {
7958 		if (sdp->isp_async_data_setup < 9) {
7959 			sdp->isp_async_data_setup = 9;
7960 		}
7961 	} else {
7962 		if (sdp->isp_async_data_setup != 6) {
7963 			sdp->isp_async_data_setup = 6;
7964 		}
7965 	}
7966 
7967 	sdp->isp_req_ack_active_neg =
7968 		ISP_NVRAM_REQ_ACK_ACTIVE_NEGATION(nvram_data);
7969 
7970 	sdp->isp_data_line_active_neg =
7971 		ISP_NVRAM_DATA_LINE_ACTIVE_NEGATION(nvram_data);
7972 
7973 	sdp->isp_data_dma_burst_enabl =
7974 		ISP_NVRAM_DATA_DMA_BURST_ENABLE(nvram_data);
7975 
7976 	sdp->isp_cmd_dma_burst_enable =
7977 		ISP_NVRAM_CMD_DMA_BURST_ENABLE(nvram_data);
7978 
7979 	sdp->isp_tag_aging =
7980 		ISP_NVRAM_TAG_AGE_LIMIT(nvram_data);
7981 
7982 	sdp->isp_selection_timeout =
7983 		ISP_NVRAM_SELECTION_TIMEOUT(nvram_data);
7984 
7985 	sdp->isp_max_queue_depth =
7986 		ISP_NVRAM_MAX_QUEUE_DEPTH(nvram_data);
7987 
7988 	sdp->isp_fast_mttr = ISP_NVRAM_FAST_MTTR_ENABLE(nvram_data);
7989 
7990 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
7991 		sdp->isp_devparam[tgt].dev_enable =
7992 			ISP_NVRAM_TGT_DEVICE_ENABLE(nvram_data, tgt);
7993 		sdp->isp_devparam[tgt].exc_throttle =
7994 			ISP_NVRAM_TGT_EXEC_THROTTLE(nvram_data, tgt);
7995 		sdp->isp_devparam[tgt].nvrm_offset =
7996 			ISP_NVRAM_TGT_SYNC_OFFSET(nvram_data, tgt);
7997 		sdp->isp_devparam[tgt].nvrm_period =
7998 			ISP_NVRAM_TGT_SYNC_PERIOD(nvram_data, tgt);
7999 		/*
8000 		 * We probably shouldn't lie about this, but it
8001 		 * it makes it much safer if we limit NVRAM values
8002 		 * to sanity.
8003 		 */
8004 		if (isp->isp_type < ISP_HA_SCSI_1040) {
8005 			/*
8006 			 * If we're not ultra, we can't possibly
8007 			 * be a shorter period than this.
8008 			 */
8009 			if (sdp->isp_devparam[tgt].nvrm_period < 0x19) {
8010 				sdp->isp_devparam[tgt].nvrm_period = 0x19;
8011 			}
8012 			if (sdp->isp_devparam[tgt].nvrm_offset > 0xc) {
8013 				sdp->isp_devparam[tgt].nvrm_offset = 0x0c;
8014 			}
8015 		} else {
8016 			if (sdp->isp_devparam[tgt].nvrm_offset > 0x8) {
8017 				sdp->isp_devparam[tgt].nvrm_offset = 0x8;
8018 			}
8019 		}
8020 		sdp->isp_devparam[tgt].nvrm_flags = 0;
8021 		if (ISP_NVRAM_TGT_RENEG(nvram_data, tgt))
8022 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_RENEG;
8023 		sdp->isp_devparam[tgt].nvrm_flags |= DPARM_ARQ;
8024 		if (ISP_NVRAM_TGT_TQING(nvram_data, tgt))
8025 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_TQING;
8026 		if (ISP_NVRAM_TGT_SYNC(nvram_data, tgt))
8027 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_SYNC;
8028 		if (ISP_NVRAM_TGT_WIDE(nvram_data, tgt))
8029 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_WIDE;
8030 		if (ISP_NVRAM_TGT_PARITY(nvram_data, tgt))
8031 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_PARITY;
8032 		if (ISP_NVRAM_TGT_DISC(nvram_data, tgt))
8033 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_DISC;
8034 		sdp->isp_devparam[tgt].actv_flags = 0; /* we don't know */
8035 		sdp->isp_devparam[tgt].goal_offset =
8036 		    sdp->isp_devparam[tgt].nvrm_offset;
8037 		sdp->isp_devparam[tgt].goal_period =
8038 		    sdp->isp_devparam[tgt].nvrm_period;
8039 		sdp->isp_devparam[tgt].goal_flags =
8040 		    sdp->isp_devparam[tgt].nvrm_flags;
8041 	}
8042 }
8043 
8044 static void
8045 isp_parse_nvram_1080(ispsoftc_t *isp, int bus, uint8_t *nvram_data)
8046 {
8047 	sdparam *sdp = SDPARAM(isp, bus);
8048 	int tgt;
8049 
8050 	sdp->isp_fifo_threshold =
8051 	    ISP1080_NVRAM_FIFO_THRESHOLD(nvram_data);
8052 
8053 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0)
8054 		sdp->isp_initiator_id =
8055 		    ISP1080_NVRAM_INITIATOR_ID(nvram_data, bus);
8056 
8057 	sdp->isp_bus_reset_delay =
8058 	    ISP1080_NVRAM_BUS_RESET_DELAY(nvram_data, bus);
8059 
8060 	sdp->isp_retry_count =
8061 	    ISP1080_NVRAM_BUS_RETRY_COUNT(nvram_data, bus);
8062 
8063 	sdp->isp_retry_delay =
8064 	    ISP1080_NVRAM_BUS_RETRY_DELAY(nvram_data, bus);
8065 
8066 	sdp->isp_async_data_setup =
8067 	    ISP1080_NVRAM_ASYNC_DATA_SETUP_TIME(nvram_data, bus);
8068 
8069 	sdp->isp_req_ack_active_neg =
8070 	    ISP1080_NVRAM_REQ_ACK_ACTIVE_NEGATION(nvram_data, bus);
8071 
8072 	sdp->isp_data_line_active_neg =
8073 	    ISP1080_NVRAM_DATA_LINE_ACTIVE_NEGATION(nvram_data, bus);
8074 
8075 	sdp->isp_data_dma_burst_enabl =
8076 	    ISP1080_NVRAM_BURST_ENABLE(nvram_data);
8077 
8078 	sdp->isp_cmd_dma_burst_enable =
8079 	    ISP1080_NVRAM_BURST_ENABLE(nvram_data);
8080 
8081 	sdp->isp_selection_timeout =
8082 	    ISP1080_NVRAM_SELECTION_TIMEOUT(nvram_data, bus);
8083 
8084 	sdp->isp_max_queue_depth =
8085 	     ISP1080_NVRAM_MAX_QUEUE_DEPTH(nvram_data, bus);
8086 
8087 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
8088 		sdp->isp_devparam[tgt].dev_enable =
8089 		    ISP1080_NVRAM_TGT_DEVICE_ENABLE(nvram_data, tgt, bus);
8090 		sdp->isp_devparam[tgt].exc_throttle =
8091 			ISP1080_NVRAM_TGT_EXEC_THROTTLE(nvram_data, tgt, bus);
8092 		sdp->isp_devparam[tgt].nvrm_offset =
8093 			ISP1080_NVRAM_TGT_SYNC_OFFSET(nvram_data, tgt, bus);
8094 		sdp->isp_devparam[tgt].nvrm_period =
8095 			ISP1080_NVRAM_TGT_SYNC_PERIOD(nvram_data, tgt, bus);
8096 		sdp->isp_devparam[tgt].nvrm_flags = 0;
8097 		if (ISP1080_NVRAM_TGT_RENEG(nvram_data, tgt, bus))
8098 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_RENEG;
8099 		sdp->isp_devparam[tgt].nvrm_flags |= DPARM_ARQ;
8100 		if (ISP1080_NVRAM_TGT_TQING(nvram_data, tgt, bus))
8101 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_TQING;
8102 		if (ISP1080_NVRAM_TGT_SYNC(nvram_data, tgt, bus))
8103 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_SYNC;
8104 		if (ISP1080_NVRAM_TGT_WIDE(nvram_data, tgt, bus))
8105 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_WIDE;
8106 		if (ISP1080_NVRAM_TGT_PARITY(nvram_data, tgt, bus))
8107 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_PARITY;
8108 		if (ISP1080_NVRAM_TGT_DISC(nvram_data, tgt, bus))
8109 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_DISC;
8110 		sdp->isp_devparam[tgt].actv_flags = 0;
8111 		sdp->isp_devparam[tgt].goal_offset =
8112 		    sdp->isp_devparam[tgt].nvrm_offset;
8113 		sdp->isp_devparam[tgt].goal_period =
8114 		    sdp->isp_devparam[tgt].nvrm_period;
8115 		sdp->isp_devparam[tgt].goal_flags =
8116 		    sdp->isp_devparam[tgt].nvrm_flags;
8117 	}
8118 }
8119 
8120 static void
8121 isp_parse_nvram_12160(ispsoftc_t *isp, int bus, uint8_t *nvram_data)
8122 {
8123 	sdparam *sdp = SDPARAM(isp, bus);
8124 	int tgt;
8125 
8126 	sdp->isp_fifo_threshold =
8127 	    ISP12160_NVRAM_FIFO_THRESHOLD(nvram_data);
8128 
8129 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0)
8130 		sdp->isp_initiator_id =
8131 		    ISP12160_NVRAM_INITIATOR_ID(nvram_data, bus);
8132 
8133 	sdp->isp_bus_reset_delay =
8134 	    ISP12160_NVRAM_BUS_RESET_DELAY(nvram_data, bus);
8135 
8136 	sdp->isp_retry_count =
8137 	    ISP12160_NVRAM_BUS_RETRY_COUNT(nvram_data, bus);
8138 
8139 	sdp->isp_retry_delay =
8140 	    ISP12160_NVRAM_BUS_RETRY_DELAY(nvram_data, bus);
8141 
8142 	sdp->isp_async_data_setup =
8143 	    ISP12160_NVRAM_ASYNC_DATA_SETUP_TIME(nvram_data, bus);
8144 
8145 	sdp->isp_req_ack_active_neg =
8146 	    ISP12160_NVRAM_REQ_ACK_ACTIVE_NEGATION(nvram_data, bus);
8147 
8148 	sdp->isp_data_line_active_neg =
8149 	    ISP12160_NVRAM_DATA_LINE_ACTIVE_NEGATION(nvram_data, bus);
8150 
8151 	sdp->isp_data_dma_burst_enabl =
8152 	    ISP12160_NVRAM_BURST_ENABLE(nvram_data);
8153 
8154 	sdp->isp_cmd_dma_burst_enable =
8155 	    ISP12160_NVRAM_BURST_ENABLE(nvram_data);
8156 
8157 	sdp->isp_selection_timeout =
8158 	    ISP12160_NVRAM_SELECTION_TIMEOUT(nvram_data, bus);
8159 
8160 	sdp->isp_max_queue_depth =
8161 	     ISP12160_NVRAM_MAX_QUEUE_DEPTH(nvram_data, bus);
8162 
8163 	for (tgt = 0; tgt < MAX_TARGETS; tgt++) {
8164 		sdp->isp_devparam[tgt].dev_enable =
8165 		    ISP12160_NVRAM_TGT_DEVICE_ENABLE(nvram_data, tgt, bus);
8166 		sdp->isp_devparam[tgt].exc_throttle =
8167 			ISP12160_NVRAM_TGT_EXEC_THROTTLE(nvram_data, tgt, bus);
8168 		sdp->isp_devparam[tgt].nvrm_offset =
8169 			ISP12160_NVRAM_TGT_SYNC_OFFSET(nvram_data, tgt, bus);
8170 		sdp->isp_devparam[tgt].nvrm_period =
8171 			ISP12160_NVRAM_TGT_SYNC_PERIOD(nvram_data, tgt, bus);
8172 		sdp->isp_devparam[tgt].nvrm_flags = 0;
8173 		if (ISP12160_NVRAM_TGT_RENEG(nvram_data, tgt, bus))
8174 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_RENEG;
8175 		sdp->isp_devparam[tgt].nvrm_flags |= DPARM_ARQ;
8176 		if (ISP12160_NVRAM_TGT_TQING(nvram_data, tgt, bus))
8177 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_TQING;
8178 		if (ISP12160_NVRAM_TGT_SYNC(nvram_data, tgt, bus))
8179 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_SYNC;
8180 		if (ISP12160_NVRAM_TGT_WIDE(nvram_data, tgt, bus))
8181 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_WIDE;
8182 		if (ISP12160_NVRAM_TGT_PARITY(nvram_data, tgt, bus))
8183 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_PARITY;
8184 		if (ISP12160_NVRAM_TGT_DISC(nvram_data, tgt, bus))
8185 			sdp->isp_devparam[tgt].nvrm_flags |= DPARM_DISC;
8186 		sdp->isp_devparam[tgt].actv_flags = 0;
8187 		sdp->isp_devparam[tgt].goal_offset =
8188 		    sdp->isp_devparam[tgt].nvrm_offset;
8189 		sdp->isp_devparam[tgt].goal_period =
8190 		    sdp->isp_devparam[tgt].nvrm_period;
8191 		sdp->isp_devparam[tgt].goal_flags =
8192 		    sdp->isp_devparam[tgt].nvrm_flags;
8193 	}
8194 }
8195 
8196 static void
8197 isp_parse_nvram_2100(ispsoftc_t *isp, uint8_t *nvram_data)
8198 {
8199 	fcparam *fcp = FCPARAM(isp, 0);
8200 	uint64_t wwn;
8201 
8202 	/*
8203 	 * There is NVRAM storage for both Port and Node entities-
8204 	 * but the Node entity appears to be unused on all the cards
8205 	 * I can find. However, we should account for this being set
8206 	 * at some point in the future.
8207 	 *
8208 	 * Qlogic WWNs have an NAA of 2, but usually nothing shows up in
8209 	 * bits 48..60. In the case of the 2202, it appears that they do
8210 	 * use bit 48 to distinguish between the two instances on the card.
8211 	 * The 2204, which I've never seen, *probably* extends this method.
8212 	 */
8213 	wwn = ISP2100_NVRAM_PORT_NAME(nvram_data);
8214 	if (wwn) {
8215 		isp_prt(isp, ISP_LOGCONFIG, "NVRAM Port WWN 0x%08x%08x",
8216 		    (uint32_t) (wwn >> 32), (uint32_t) (wwn));
8217 		if ((wwn >> 60) == 0) {
8218 			wwn |= (((uint64_t) 2)<< 60);
8219 		}
8220 	}
8221 	fcp->isp_wwpn_nvram = wwn;
8222 	if (IS_2200(isp) || IS_23XX(isp)) {
8223 		wwn = ISP2100_NVRAM_NODE_NAME(nvram_data);
8224 		if (wwn) {
8225 			isp_prt(isp, ISP_LOGCONFIG, "NVRAM Node WWN 0x%08x%08x",
8226 			    (uint32_t) (wwn >> 32),
8227 			    (uint32_t) (wwn));
8228 			if ((wwn >> 60) == 0) {
8229 				wwn |= (((uint64_t) 2)<< 60);
8230 			}
8231 		} else {
8232 			wwn = fcp->isp_wwpn_nvram & ~((uint64_t) 0xfff << 48);
8233 		}
8234 	} else {
8235 		wwn &= ~((uint64_t) 0xfff << 48);
8236 	}
8237 	fcp->isp_wwnn_nvram = wwn;
8238 
8239 	fcp->isp_maxalloc = ISP2100_NVRAM_MAXIOCBALLOCATION(nvram_data);
8240 	if ((isp->isp_confopts & ISP_CFG_OWNFSZ) == 0) {
8241 		DEFAULT_FRAMESIZE(isp) =
8242 		    ISP2100_NVRAM_MAXFRAMELENGTH(nvram_data);
8243 	}
8244 	fcp->isp_retry_delay = ISP2100_NVRAM_RETRY_DELAY(nvram_data);
8245 	fcp->isp_retry_count = ISP2100_NVRAM_RETRY_COUNT(nvram_data);
8246 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0) {
8247 		fcp->isp_loopid = ISP2100_NVRAM_HARDLOOPID(nvram_data);
8248 	}
8249 	if ((isp->isp_confopts & ISP_CFG_OWNEXCTHROTTLE) == 0) {
8250 		DEFAULT_EXEC_THROTTLE(isp) =
8251 			ISP2100_NVRAM_EXECUTION_THROTTLE(nvram_data);
8252 	}
8253 	fcp->isp_fwoptions = ISP2100_NVRAM_OPTIONS(nvram_data);
8254 	isp_prt(isp, ISP_LOGDEBUG0,
8255 	    "NVRAM 0x%08x%08x 0x%08x%08x maxalloc %d maxframelen %d",
8256 	    (uint32_t) (fcp->isp_wwnn_nvram >> 32),
8257 	    (uint32_t) fcp->isp_wwnn_nvram,
8258 	    (uint32_t) (fcp->isp_wwpn_nvram >> 32),
8259 	    (uint32_t) fcp->isp_wwpn_nvram,
8260 	    ISP2100_NVRAM_MAXIOCBALLOCATION(nvram_data),
8261 	    ISP2100_NVRAM_MAXFRAMELENGTH(nvram_data));
8262 	isp_prt(isp, ISP_LOGDEBUG0,
8263 	    "execthrottle %d fwoptions 0x%x hardloop %d tov %d",
8264 	    ISP2100_NVRAM_EXECUTION_THROTTLE(nvram_data),
8265 	    ISP2100_NVRAM_OPTIONS(nvram_data),
8266 	    ISP2100_NVRAM_HARDLOOPID(nvram_data),
8267 	    ISP2100_NVRAM_TOV(nvram_data));
8268 	fcp->isp_xfwoptions = ISP2100_XFW_OPTIONS(nvram_data);
8269 	fcp->isp_zfwoptions = ISP2100_ZFW_OPTIONS(nvram_data);
8270 	isp_prt(isp, ISP_LOGDEBUG0, "xfwoptions 0x%x zfw options 0x%x",
8271 	    ISP2100_XFW_OPTIONS(nvram_data), ISP2100_ZFW_OPTIONS(nvram_data));
8272 }
8273 
8274 static void
8275 isp_parse_nvram_2400(ispsoftc_t *isp, uint8_t *nvram_data)
8276 {
8277 	fcparam *fcp = FCPARAM(isp, 0);
8278 	uint64_t wwn;
8279 
8280 	isp_prt(isp, ISP_LOGDEBUG0,
8281 	    "NVRAM 0x%08x%08x 0x%08x%08x exchg_cnt %d maxframelen %d",
8282 	    (uint32_t) (ISP2400_NVRAM_NODE_NAME(nvram_data) >> 32),
8283 	    (uint32_t) (ISP2400_NVRAM_NODE_NAME(nvram_data)),
8284 	    (uint32_t) (ISP2400_NVRAM_PORT_NAME(nvram_data) >> 32),
8285 	    (uint32_t) (ISP2400_NVRAM_PORT_NAME(nvram_data)),
8286 	    ISP2400_NVRAM_EXCHANGE_COUNT(nvram_data),
8287 	    ISP2400_NVRAM_MAXFRAMELENGTH(nvram_data));
8288 	isp_prt(isp, ISP_LOGDEBUG0,
8289 	    "NVRAM execthr %d loopid %d fwopt1 0x%x fwopt2 0x%x fwopt3 0x%x",
8290 	    ISP2400_NVRAM_EXECUTION_THROTTLE(nvram_data),
8291 	    ISP2400_NVRAM_HARDLOOPID(nvram_data),
8292 	    ISP2400_NVRAM_FIRMWARE_OPTIONS1(nvram_data),
8293 	    ISP2400_NVRAM_FIRMWARE_OPTIONS2(nvram_data),
8294 	    ISP2400_NVRAM_FIRMWARE_OPTIONS3(nvram_data));
8295 
8296 	wwn = ISP2400_NVRAM_PORT_NAME(nvram_data);
8297 	fcp->isp_wwpn_nvram = wwn;
8298 
8299 	wwn = ISP2400_NVRAM_NODE_NAME(nvram_data);
8300 	if (wwn) {
8301 		if ((wwn >> 60) != 2 && (wwn >> 60) != 5) {
8302 			wwn = 0;
8303 		}
8304 	}
8305 	if (wwn == 0 && (fcp->isp_wwpn_nvram >> 60) == 2) {
8306 		wwn = fcp->isp_wwpn_nvram;
8307 		wwn &= ~((uint64_t) 0xfff << 48);
8308 	}
8309 	fcp->isp_wwnn_nvram = wwn;
8310 
8311 	if (ISP2400_NVRAM_EXCHANGE_COUNT(nvram_data)) {
8312 		fcp->isp_maxalloc = ISP2400_NVRAM_EXCHANGE_COUNT(nvram_data);
8313 	}
8314 	if ((isp->isp_confopts & ISP_CFG_OWNFSZ) == 0) {
8315 		DEFAULT_FRAMESIZE(isp) =
8316 		    ISP2400_NVRAM_MAXFRAMELENGTH(nvram_data);
8317 	}
8318 	if ((isp->isp_confopts & ISP_CFG_OWNLOOPID) == 0) {
8319 		fcp->isp_loopid = ISP2400_NVRAM_HARDLOOPID(nvram_data);
8320 	}
8321 	if ((isp->isp_confopts & ISP_CFG_OWNEXCTHROTTLE) == 0) {
8322 		DEFAULT_EXEC_THROTTLE(isp) =
8323 			ISP2400_NVRAM_EXECUTION_THROTTLE(nvram_data);
8324 	}
8325 	fcp->isp_fwoptions = ISP2400_NVRAM_FIRMWARE_OPTIONS1(nvram_data);
8326 	fcp->isp_xfwoptions = ISP2400_NVRAM_FIRMWARE_OPTIONS2(nvram_data);
8327 	fcp->isp_zfwoptions = ISP2400_NVRAM_FIRMWARE_OPTIONS3(nvram_data);
8328 }
8329