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