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