summaryrefslogtreecommitdiffstats
path: root/sys/dev/isp
diff options
context:
space:
mode:
authormav <mav@FreeBSD.org>2015-11-30 21:37:22 +0000
committermav <mav@FreeBSD.org>2015-11-30 21:37:22 +0000
commitd293293f6c10a65571fdd26d677924c1e7fba125 (patch)
treefeb91741af14ae68f4c305e10d147fa50dbb6aae /sys/dev/isp
parent93803f9b80b5a92f9d83877435a9fdd625c2e4ac (diff)
downloadFreeBSD-src-d293293f6c10a65571fdd26d677924c1e7fba125.zip
FreeBSD-src-d293293f6c10a65571fdd26d677924c1e7fba125.tar.gz
MFC r290993, r290994: Unify and cleanup FC ports scan.
Diffstat (limited to 'sys/dev/isp')
-rw-r--r--sys/dev/isp/isp.c317
-rw-r--r--sys/dev/isp/isp_library.c38
-rw-r--r--sys/dev/isp/ispvar.h15
3 files changed, 153 insertions, 217 deletions
diff --git a/sys/dev/isp/isp.c b/sys/dev/isp/isp.c
index ff67ab7..3710a52 100644
--- a/sys/dev/isp/isp.c
+++ b/sys/dev/isp/isp.c
@@ -64,12 +64,6 @@ __FBSDID("$FreeBSD$");
* General defines
*/
#define MBOX_DELAY_COUNT 1000000 / 100
-#define ISP_MARK_PORTDB(a, b, c) \
- do { \
- isp_prt(isp, ISP_LOG_SANCFG, \
- "Chan %d ISP_MARK_PORTDB@LINE %d", (b), __LINE__); \
- isp_mark_portdb((a), (b), (c)); \
- } while (0)
/*
* Local static data
@@ -132,7 +126,7 @@ static int isp_login_device(ispsoftc_t *, int, uint32_t, isp_pdb_t *, uint16_t *
static int isp_register_fc4_type(ispsoftc_t *, int);
static int isp_register_fc4_type_24xx(ispsoftc_t *, int);
static uint16_t isp_next_handle(ispsoftc_t *, uint16_t *);
-static void isp_fw_state(ispsoftc_t *, int);
+static int isp_fw_state(ispsoftc_t *, int);
static void isp_mboxcmd_qnw(ispsoftc_t *, mbreg_t *, int);
static void isp_mboxcmd(ispsoftc_t *, mbreg_t *);
@@ -149,6 +143,19 @@ static void isp_parse_nvram_12160(ispsoftc_t *, int, uint8_t *);
static void isp_parse_nvram_2100(ispsoftc_t *, uint8_t *);
static void isp_parse_nvram_2400(ispsoftc_t *, uint8_t *);
+static void
+isp_change_fw_state(ispsoftc_t *isp, int chan, int state)
+{
+ fcparam *fcp = FCPARAM(isp, chan);
+
+ if (fcp->isp_fwstate == state)
+ return;
+ isp_prt(isp, ISP_LOGCONFIG|ISP_LOG_SANCFG,
+ "Chan %d Firmware state <%s->%s>", chan,
+ isp_fc_fw_statename(fcp->isp_fwstate), isp_fc_fw_statename(state));
+ fcp->isp_fwstate = state;
+}
+
/*
* Reset Hardware.
*
@@ -1267,8 +1274,9 @@ isp_reset(ispsoftc_t *isp, int do_load_defaults)
isp->isp_nchan = 1;
}
}
- for (i = 0; i < isp->isp_nchan; i++) {
- isp_fw_state(isp, i);
+ if (IS_FC(isp)) {
+ for (i = 0; i < isp->isp_nchan; i++)
+ isp_change_fw_state(isp, i, FW_CONFIG_WAIT);
}
if (isp->isp_dead) {
isp_shutdown(isp);
@@ -2577,7 +2585,10 @@ isp_getpdb(ispsoftc_t *isp, int chan, uint16_t id, isp_pdb_t *pdb, int dolock)
pdb->portid = BITS2WORD_24XX(un.bill.pdb_portid_bits);
ISP_MEMCPY(pdb->portname, un.bill.pdb_portname, 8);
ISP_MEMCPY(pdb->nodename, un.bill.pdb_nodename, 8);
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d handle 0x%x Port 0x%06x flags 0x%x curstate %x", chan, id, pdb->portid, un.bill.pdb_flags, un.bill.pdb_curstate);
+ isp_prt(isp, ISP_LOGDEBUG1,
+ "Chan %d handle 0x%x Port 0x%06x flags 0x%x curstate %x",
+ chan, id, pdb->portid, un.bill.pdb_flags,
+ un.bill.pdb_curstate);
if (un.bill.pdb_curstate < PDB2400_STATE_PLOGI_DONE || un.bill.pdb_curstate > PDB2400_STATE_LOGGED_IN) {
mbs.param[0] = MBOX_NOT_LOGGED_IN;
if (dolock) {
@@ -2592,6 +2603,8 @@ isp_getpdb(ispsoftc_t *isp, int chan, uint16_t id, isp_pdb_t *pdb, int dolock)
pdb->portid = BITS2WORD(un.fred.pdb_portid_bits);
ISP_MEMCPY(pdb->portname, un.fred.pdb_portname, 8);
ISP_MEMCPY(pdb->nodename, un.fred.pdb_nodename, 8);
+ isp_prt(isp, ISP_LOGDEBUG1,
+ "Chan %d handle 0x%x Port 0x%06x", chan, id, pdb->portid);
}
if (dolock) {
FC_SCRATCH_RELEASE(isp, chan);
@@ -2699,13 +2712,8 @@ static uint64_t
isp_get_wwn(ispsoftc_t *isp, int chan, int loopid, int nodename)
{
uint64_t wwn = INI_NONE;
- fcparam *fcp = FCPARAM(isp, chan);
mbreg_t mbs;
- if (fcp->isp_fwstate < FW_READY ||
- fcp->isp_loopstate < LOOP_PDB_RCVD) {
- return (wwn);
- }
MBSINIT(&mbs, MBOX_GET_PORT_NAME,
MBLOGALL & ~MBLOGMASK(MBOX_COMMAND_PARAM_ERROR), 500000);
if (ISP_CAP_2KLOGIN(isp)) {
@@ -2758,7 +2766,6 @@ isp_fclink_test(ispsoftc_t *isp, int chan, int usdelay)
{
mbreg_t mbs;
int check_for_fabric, r;
- uint8_t lwfs;
int loopid;
fcparam *fcp;
fcportdb_t *lp;
@@ -2767,20 +2774,21 @@ isp_fclink_test(ispsoftc_t *isp, int chan, int usdelay)
fcp = FCPARAM(isp, chan);
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC Link Test Entry", chan);
- ISP_MARK_PORTDB(isp, chan, 1);
+ /* Mark port database entries for following scan. */
+ isp_mark_portdb(isp, chan, 1);
+
+ if (fcp->isp_loopstate >= LOOP_LTEST_DONE)
+ return (0);
+
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC link test", chan);
+ fcp->isp_loopstate = LOOP_TESTING_LINK;
/*
* Wait up to N microseconds for F/W to go to a ready state.
*/
- lwfs = FW_CONFIG_WAIT;
GET_NANOTIME(&hra);
while (1) {
- isp_fw_state(isp, chan);
- if (lwfs != fcp->isp_fwstate) {
- isp_prt(isp, ISP_LOGCONFIG|ISP_LOG_SANCFG, "Chan %d Firmware State <%s->%s>", chan, isp_fc_fw_statename((int)lwfs), isp_fc_fw_statename((int)fcp->isp_fwstate));
- lwfs = fcp->isp_fwstate;
- }
+ isp_change_fw_state(isp, chan, isp_fw_state(isp, chan));
if (fcp->isp_fwstate == FW_READY) {
break;
}
@@ -2794,7 +2802,9 @@ isp_fclink_test(ispsoftc_t *isp, int chan, int usdelay)
* If we haven't gone to 'ready' state, return.
*/
if (fcp->isp_fwstate != FW_READY) {
- isp_prt(isp, ISP_LOG_SANCFG, "%s: chan %d not at FW_READY state", __func__, chan);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Firmware is not ready (%s)",
+ chan, isp_fc_fw_statename(fcp->isp_fwstate));
return (-1);
}
@@ -2860,7 +2870,7 @@ isp_fclink_test(ispsoftc_t *isp, int chan, int usdelay)
}
if (alpa_map[i] && fcp->isp_loopid != i) {
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d deriving loopid %d from AL_PA map (AL_PA 0x%x) and ignoring returned value %d (AL_PA 0x%x)",
+ "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);
fcp->isp_loopid = i;
}
@@ -2953,11 +2963,12 @@ not_on_fabric:
}
}
+ fcp->isp_loopstate = LOOP_LTEST_DONE;
/*
* Announce ourselves, too.
*/
isp_prt(isp, ISP_LOG_SANCFG|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));
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC Link Test Complete", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC link test done", chan);
return (0);
}
@@ -2967,19 +2978,10 @@ not_on_fabric:
* At this point, we've scanned the local loop (if any) and the fabric
* and performed fabric logins on all new devices.
*
- * Our task here is to go through our port database and remove any entities
+ * Our task here is to go through our port database removing any entities
* that are still marked probational (issuing PLOGO for ones which we had
- * PLOGI'd into) or are dead.
- *
- * Our task here is to also check policy to decide whether devices which
- * have *changed* in some way should still be kept active. For example,
- * if a device has just changed PortID, we can either elect to treat it
- * as an old device or as a newly arrived device (and notify the outer
- * layer appropriately).
- *
- * We also do initiator map target id assignment here for new initiator
- * devices and refresh old ones ot make sure that they point to the correct
- * entities.
+ * PLOGI'd into) or are dead, and notifying upper layers about new/changed
+ * devices.
*/
static int
isp_pdb_sync(ispsoftc_t *isp, int chan)
@@ -2988,44 +2990,14 @@ isp_pdb_sync(ispsoftc_t *isp, int chan)
fcportdb_t *lp;
uint16_t dbidx;
- if (fcp->isp_loopstate == LOOP_READY) {
- return (0);
- }
-
- /*
- * Make sure we're okay for doing this right now.
- */
- if (fcp->isp_loopstate != LOOP_PDB_RCVD &&
- fcp->isp_loopstate != LOOP_FSCAN_DONE &&
- fcp->isp_loopstate != LOOP_LSCAN_DONE) {
- isp_prt(isp, ISP_LOGWARN, "isp_pdb_sync: bad loopstate %d",
- fcp->isp_loopstate);
+ if (fcp->isp_loopstate < LOOP_FSCAN_DONE) {
return (-1);
}
-
- if (fcp->isp_topo == TOPO_FL_PORT ||
- fcp->isp_topo == TOPO_NL_PORT ||
- fcp->isp_topo == TOPO_N_PORT) {
- if (fcp->isp_loopstate < LOOP_LSCAN_DONE) {
- if (isp_scan_loop(isp, chan) != 0) {
- isp_prt(isp, ISP_LOGWARN,
- "isp_pdb_sync: isp_scan_loop failed");
- return (-1);
- }
- }
- }
-
- if (fcp->isp_topo == TOPO_F_PORT || fcp->isp_topo == TOPO_FL_PORT) {
- if (fcp->isp_loopstate < LOOP_FSCAN_DONE) {
- if (isp_scan_fabric(isp, chan) != 0) {
- isp_prt(isp, ISP_LOGWARN,
- "isp_pdb_sync: isp_scan_fabric failed");
- return (-1);
- }
- }
+ if (fcp->isp_loopstate > LOOP_SYNCING_PDB) {
+ return (0);
}
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Synchronizing PDBs", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC PDB sync", chan);
fcp->isp_loopstate = LOOP_SYNCING_PDB;
@@ -3101,6 +3073,7 @@ isp_pdb_sync(ispsoftc_t *isp, int chan)
*/
fcp->loop_seen_once = 1;
fcp->isp_loopstate = LOOP_READY;
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC PDB sync done", chan);
return (0);
}
@@ -3117,36 +3090,34 @@ isp_scan_loop(ispsoftc_t *isp, int chan)
uint16_t handles[LOCAL_LOOP_LIM];
uint16_t handle;
- if (fcp->isp_fwstate < FW_READY ||
- fcp->isp_loopstate < LOOP_PDB_RCVD) {
+ if (fcp->isp_loopstate < LOOP_LTEST_DONE) {
return (-1);
}
if (fcp->isp_loopstate > LOOP_SCANNING_LOOP) {
return (0);
}
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC loop scan", chan);
if (fcp->isp_topo != TOPO_NL_PORT && fcp->isp_topo != TOPO_FL_PORT &&
fcp->isp_topo != TOPO_N_PORT) {
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d no loop topology to scan", chan);
+ "Chan %d FC loop scan done (no loop)", chan);
fcp->isp_loopstate = LOOP_LSCAN_DONE;
return (0);
}
-
fcp->isp_loopstate = LOOP_SCANNING_LOOP;
lim = LOCAL_LOOP_LIM;
r = isp_gethandles(isp, chan, handles, &lim, 1, 1);
if (r != 0) {
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d getting list of handles failed with %x", chan, r);
+ "Chan %d Getting list of handles failed with %x", chan, r);
fail:
- ISP_MARK_PORTDB(isp, chan, 1);
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d FC scan loop DONE (bad)", chan);
+ "Chan %d FC loop scan done (bad)", chan);
return (-1);
}
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC scan loop -- %d ports",
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Got %d handles",
chan, lim);
/*
@@ -3172,8 +3143,12 @@ fail:
*/
if (IS_2100(isp) || IS_2200(isp)) {
uint64_t node_wwn = isp_get_wwn(isp, chan, handle, 1);
- if (fcp->isp_loopstate < LOOP_SCANNING_LOOP)
- goto fail;
+ if (fcp->isp_loopstate < LOOP_SCANNING_LOOP) {
+abort:
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d FC loop scan done (abort)", chan);
+ return (-1);
+ }
if (node_wwn == INI_NONE) {
continue;
}
@@ -3185,15 +3160,15 @@ fail:
r = isp_getpdb(isp, chan, handle, &pdb, 1);
if (r != 0) {
isp_prt(isp, ISP_LOGDEBUG1,
- "Chan %d FC scan loop handle %d returned %x",
+ "Chan %d FC Scan Loop handle %d returned %x",
chan, handle, r);
if (fcp->isp_loopstate < LOOP_SCANNING_LOOP)
- goto fail;
+ goto abort;
continue;
}
if (fcp->isp_loopstate < LOOP_SCANNING_LOOP)
- goto fail;
+ goto abort;
/*
* On *very* old 2100 firmware we would end up sometimes
@@ -3279,7 +3254,9 @@ fail:
lp->new_portid = tmp.portid;
lp->new_prli_word3 = tmp.prli_word3;
lp->state = FC_PORTDB_STATE_PENDING_VALID;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Loop Port 0x%06x@0x%04x Pending Valid", chan, tmp.portid, tmp.handle);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Loop port 0x%06x@0x%04x now pending valid",
+ chan, tmp.portid, tmp.handle);
continue;
}
@@ -3293,7 +3270,9 @@ fail:
* Claim that this has changed and let somebody else
* decide what to do.
*/
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Loop Port 0x%06x@0x%04x changed", chan, tmp.portid, tmp.handle);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Loop port 0x%06x@0x%04x changed",
+ chan, tmp.portid, tmp.handle);
lp->state = FC_PORTDB_STATE_CHANGED;
lp->new_portid = tmp.portid;
lp->new_prli_word3 = tmp.prli_word3;
@@ -3324,10 +3303,14 @@ fail:
lp->handle = tmp.handle;
lp->port_wwn = tmp.port_wwn;
lp->node_wwn = tmp.node_wwn;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Loop Port 0x%06x@0x%04x is New Entry", chan, tmp.portid, tmp.handle);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Loop port 0x%06x@0x%04x is a new entry",
+ chan, tmp.portid, tmp.handle);
}
+ if (fcp->isp_loopstate < LOOP_SCANNING_LOOP)
+ goto abort;
fcp->isp_loopstate = LOOP_LSCAN_DONE;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC scan loop DONE", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC loop scan done", chan);
return (0);
}
@@ -3513,28 +3496,33 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
int portidx, portlim, r;
sns_gid_ft_rsp_t *rs0, *rs1;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC Scan Fabric", chan);
- if (fcp->isp_fwstate != FW_READY || fcp->isp_loopstate < LOOP_LSCAN_DONE) {
+ if (fcp->isp_loopstate < LOOP_LSCAN_DONE) {
return (-1);
}
if (fcp->isp_loopstate > LOOP_SCANNING_FABRIC) {
return (0);
}
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC fabric scan", chan);
if (fcp->isp_topo != TOPO_FL_PORT && fcp->isp_topo != TOPO_F_PORT) {
fcp->isp_loopstate = LOOP_FSCAN_DONE;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC Scan Fabric Done (no fabric)", chan);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d FC fabric scan done (no fabric)", chan);
return (0);
}
-
fcp->isp_loopstate = LOOP_SCANNING_FABRIC;
+
if (FC_SCRATCH_ACQUIRE(isp, chan)) {
isp_prt(isp, ISP_LOGERR, sacq);
- ISP_MARK_PORTDB(isp, chan, 1);
+fail:
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d FC fabric scan done (bad)", chan);
return (-1);
}
if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+abort:
FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d FC fabric scan done (abort)", chan);
return (-1);
}
@@ -3551,10 +3539,9 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
isp_dump_chip_portdb(isp, chan, 0);
}
if (r) {
- fcp->isp_loopstate = LOOP_PDB_RCVD;
+ fcp->isp_loopstate = LOOP_LTEST_DONE;
FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ goto fail;
}
if (IS_24XX(isp)) {
@@ -3564,9 +3551,7 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
}
if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ goto abort;
}
if (r > 0) {
@@ -3574,7 +3559,7 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
FC_SCRATCH_RELEASE(isp, chan);
return (0);
} else if (r < 0) {
- fcp->isp_loopstate = LOOP_PDB_RCVD; /* try again */
+ fcp->isp_loopstate = LOOP_LTEST_DONE; /* try again */
FC_SCRATCH_RELEASE(isp, chan);
return (0);
}
@@ -3584,9 +3569,7 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
rs1 = (sns_gid_ft_rsp_t *) ((uint8_t *)fcp->isp_scratch+OGPOFF);
isp_get_gid_ft_response(isp, rs0, rs1, NGENT);
if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ goto abort;
}
if (rs1->snscb_cthdr.ct_cmd_resp != LS_ACC) {
int level;
@@ -3631,7 +3614,7 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
}
portlim = portidx + 1;
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d got %d ports back from name server", chan, portlim);
+ "Chan %d Got %d ports back from name server", chan, portlim);
for (portidx = 0; portidx < portlim; portidx++) {
int npidx;
@@ -3686,35 +3669,19 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
if (portid == 0) {
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d skipping null PortID at idx %d",
+ "Chan %d Skipping null PortID at idx %d",
chan, portidx);
continue;
}
- /*
- * Skip ourselves here and on other channels. If we're
- * multi-id, we can't check the portids in other FCPARAM
- * arenas because the resolutions here aren't synchronized.
- * The best way to do this is to exclude looking at portids
- * that have the same domain and area code as our own
- * portid.
- */
- if (ISP_CAP_MULTI_ID(isp) && isp->isp_nchan > 1) {
- if ((portid >> 8) == (fcp->isp_portid >> 8)) {
- isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d skip PortID 0x%06x",
- chan, portid);
- continue;
- }
- } else if (portid == fcp->isp_portid) {
+ if (portid == fcp->isp_portid) {
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d skip ourselves on @ PortID 0x%06x",
- chan, portid);
+ "Chan %d Skipping our PortID 0x%06x", chan, portid);
continue;
}
isp_prt(isp, ISP_LOG_SANCFG,
- "Chan %d Checking Fabric Port 0x%06x", chan, portid);
+ "Chan %d Checking fabric port 0x%06x", chan, portid);
/*
* We now search our Port Database for any
@@ -3759,10 +3726,8 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
*/
r = isp_getpdb(isp, chan, lp->handle, &pdb, 0);
- if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+ goto abort;
}
if (r != 0) {
lp->new_portid = portid;
@@ -3806,19 +3771,14 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
&FCPARAM(isp, 0)->isp_lasthdl)) {
lp->new_portid = portid;
lp->state = FC_PORTDB_STATE_DEAD;
- if (fcp->isp_loopstate !=
+ if (fcp->isp_loopstate <
LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ goto abort;
}
continue;
}
- if (fcp->isp_loopstate !=
- LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+ goto abort;
}
MAKE_WWN_FROM_NODE_NAME(wwnn, pdb.nodename);
MAKE_WWN_FROM_NODE_NAME(wwpn, pdb.portname);
@@ -3852,10 +3812,14 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
lp->new_portid = portid;
lp->new_prli_word3 = nr;
if (pdb.portid != lp->portid || nr != lp->prli_word3 || handle_changed) {
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Fabric Port 0x%06x changed", chan, portid);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Fabric port 0x%06x changed",
+ chan, portid);
lp->state = FC_PORTDB_STATE_CHANGED;
} else {
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Fabric Port 0x%06x Now Pending Valid", chan, portid);
+ isp_prt(isp, ISP_LOG_SANCFG,
+ "Chan %d Fabric port 0x%06x now pending valid",
+ chan, portid);
lp->state = FC_PORTDB_STATE_PENDING_VALID;
}
continue;
@@ -3922,17 +3886,13 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
*/
if (isp_login_device(isp, chan, portid, &pdb,
&FCPARAM(isp, 0)->isp_lasthdl)) {
- if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+ goto abort;
}
continue;
}
- if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
- FC_SCRATCH_RELEASE(isp, chan);
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+ goto abort;
}
handle = pdb.handle;
@@ -3964,7 +3924,7 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
lp->new_portid = portid;
lp->new_prli_word3 = nr;
lp->state = FC_PORTDB_STATE_NEW;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Fabric Port 0x%06x is a New Entry", chan, portid);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Fabric port 0x%06x is a new entry", chan, portid);
continue;
}
@@ -3993,21 +3953,20 @@ isp_scan_fabric(ispsoftc_t *isp, int chan)
lp->new_portid = portid;
lp->new_prli_word3 = nr;
if (lp->portid != portid || lp->prli_word3 != nr) {
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Zombie Fabric Port 0x%06x Now Changed", chan, portid);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Zombie fabric port 0x%06x now changed", chan, portid);
lp->state = FC_PORTDB_STATE_CHANGED;
} else {
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Zombie Fabric Port 0x%06x Now Pending Valid", chan, portid);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d Zombie fabric port 0x%06x now pending valid", chan, portid);
lp->state = FC_PORTDB_STATE_PENDING_VALID;
}
}
- FC_SCRATCH_RELEASE(isp, chan);
- if (fcp->isp_loopstate != LOOP_SCANNING_FABRIC) {
- ISP_MARK_PORTDB(isp, chan, 1);
- return (-1);
+ if (fcp->isp_loopstate < LOOP_SCANNING_FABRIC) {
+ goto abort;
}
+ FC_SCRATCH_RELEASE(isp, chan);
fcp->isp_loopstate = LOOP_FSCAN_DONE;
- isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC Scan Fabric Done", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "Chan %d FC fabric scan done", chan);
return (0);
}
@@ -4359,7 +4318,7 @@ isp_start(XS_T *xs)
/*
* Try again later.
*/
- if (fcp->isp_fwstate != FW_READY || fcp->isp_loopstate != LOOP_READY) {
+ if (fcp->isp_loopstate != LOOP_READY) {
return (CMD_RQLATER);
}
@@ -5850,7 +5809,7 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
isp->isp_dead = 1;
isp->isp_state = ISP_CRASHED;
FCPARAM(isp, chan)->isp_loopstate = LOOP_NIL;
- FCPARAM(isp, chan)->isp_fwstate = FW_CONFIG_WAIT;
+ isp_change_fw_state(isp, chan, FW_CONFIG_WAIT);
/*
* Were we waiting for a mailbox command to complete?
* If so, it's dead, so wake up the waiter.
@@ -5923,10 +5882,8 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
continue;
}
- fcp->isp_fwstate = FW_CONFIG_WAIT;
- fcp->isp_loopstate = LOOP_LIP_RCVD;
+ fcp->isp_loopstate = LOOP_NIL;
ISP_SET_SENDMARKER(isp, chan, 1);
- ISP_MARK_PORTDB(isp, chan, 1);
isp_async(isp, ISPASYNC_LIP, chan);
#ifdef ISP_TARGET_MODE
if (isp_target_async(isp, chan, mbox)) {
@@ -5982,10 +5939,6 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
}
ISP_SET_SENDMARKER(isp, chan, 1);
-
- fcp->isp_fwstate = FW_CONFIG_WAIT;
- fcp->isp_loopstate = LOOP_LIP_RCVD;
- ISP_MARK_PORTDB(isp, chan, 1);
isp_async(isp, ISPASYNC_LOOP_UP, chan);
#ifdef ISP_TARGET_MODE
if (isp_target_async(isp, chan, mbox)) {
@@ -6008,10 +5961,9 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
}
ISP_SET_SENDMARKER(isp, chan, 1);
- fcp->isp_fwstate = FW_CONFIG_WAIT;
fcp->isp_loopstate = LOOP_NIL;
- ISP_MARK_PORTDB(isp, chan, 1);
isp_async(isp, ISPASYNC_LOOP_DOWN, chan);
+
#ifdef ISP_TARGET_MODE
if (isp_target_async(isp, chan, mbox)) {
acked = 1;
@@ -6033,9 +5985,7 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
}
ISP_SET_SENDMARKER(isp, chan, 1);
- fcp->isp_fwstate = FW_CONFIG_WAIT;
fcp->isp_loopstate = LOOP_NIL;
- ISP_MARK_PORTDB(isp, chan, 1);
isp_async(isp, ISPASYNC_LOOP_RESET, chan);
#ifdef ISP_TARGET_MODE
if (isp_target_async(isp, chan, mbox)) {
@@ -6067,9 +6017,8 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
if (fcp->role == ISP_ROLE_NONE) {
continue;
}
- ISP_SET_SENDMARKER(isp, chan, 1);
- fcp->isp_loopstate = LOOP_PDB_RCVD;
- ISP_MARK_PORTDB(isp, chan, 1);
+ if (fcp->isp_loopstate > LOOP_LTEST_DONE)
+ fcp->isp_loopstate = LOOP_LTEST_DONE;
isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_PDB, nphdl, nlstate, reason);
}
break;
@@ -6093,12 +6042,8 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
continue;
}
- if (fcp->isp_topo == TOPO_F_PORT) {
+ if (fcp->isp_loopstate > LOOP_LSCAN_DONE)
fcp->isp_loopstate = LOOP_LSCAN_DONE;
- } else {
- fcp->isp_loopstate = LOOP_PDB_RCVD;
- }
- ISP_MARK_PORTDB(isp, chan, 1);
isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_SNS);
}
break;
@@ -6114,7 +6059,6 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
}
chan = 0;
mbox = ISP_READ(isp, OUTMAILBOX1);
- ISP_MARK_PORTDB(isp, chan, 1);
switch (mbox) {
case ISP_CONN_LOOP:
isp_prt(isp, ISP_LOGINFO,
@@ -6143,10 +6087,9 @@ isp_parse_async_fc(ispsoftc_t *isp, uint16_t mbox)
"Unknown connection mode (0x%x)", mbox);
break;
}
+ ISP_SET_SENDMARKER(isp, chan, 1);
+ FCPARAM(isp, chan)->isp_loopstate = LOOP_NIL;
isp_async(isp, ISPASYNC_CHANGE_NOTIFY, chan, ISPASYNC_CHANGE_OTHER);
- FCPARAM(isp, chan)->sendmarker = 1;
- FCPARAM(isp, chan)->isp_fwstate = FW_CONFIG_WAIT;
- FCPARAM(isp, chan)->isp_loopstate = LOOP_LIP_RCVD;
break;
case ASYNC_RCV_ERR:
@@ -7557,19 +7500,19 @@ out:
}
}
-static void
+static int
isp_fw_state(ispsoftc_t *isp, int chan)
{
if (IS_FC(isp)) {
mbreg_t mbs;
- fcparam *fcp = FCPARAM(isp, chan);
MBSINIT(&mbs, MBOX_GET_FW_STATE, MBLOGALL, 0);
isp_mboxcmd(isp, &mbs);
if (mbs.param[0] == MBOX_COMMAND_COMPLETE) {
- fcp->isp_fwstate = mbs.param[1];
+ return (mbs.param[1]);
}
}
+ return (FW_ERROR);
}
static void
@@ -7939,7 +7882,7 @@ isp_reinit(ispsoftc_t *isp, int do_load_defaults)
isp_clear_commands(isp);
if (IS_FC(isp)) {
for (i = 0; i < isp->isp_nchan; i++)
- ISP_MARK_PORTDB(isp, i, -1);
+ isp_mark_portdb(isp, i, -1);
}
return (res);
}
diff --git a/sys/dev/isp/isp_library.c b/sys/dev/isp/isp_library.c
index f0a0322..73f50a7 100644
--- a/sys/dev/isp/isp_library.c
+++ b/sys/dev/isp/isp_library.c
@@ -400,31 +400,24 @@ isp_fc_runstate(ispsoftc_t *isp, int chan, int tval)
if (fcp->role == ISP_ROLE_NONE) {
return (0);
}
- if (fcp->isp_fwstate < FW_READY || fcp->isp_loopstate < LOOP_PDB_RCVD) {
- if (isp_control(isp, ISPCTL_FCLINK_TEST, chan, tval) != 0) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: linktest failed for channel %d", chan);
- return (-1);
- }
- if (fcp->isp_fwstate != FW_READY || fcp->isp_loopstate < LOOP_PDB_RCVD) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: f/w not ready for channel %d", chan);
- return (-1);
- }
+ if (isp_control(isp, ISPCTL_FCLINK_TEST, chan, tval) != 0) {
+ isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: linktest failed for channel %d", chan);
+ return (-1);
}
-
if (isp_control(isp, ISPCTL_SCAN_LOOP, chan) != 0) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: scan loop fails on channel %d", chan);
- return (LOOP_PDB_RCVD);
+ isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: scan loop failed on channel %d", chan);
+ return (LOOP_LTEST_DONE);
}
if (isp_control(isp, ISPCTL_SCAN_FABRIC, chan) != 0) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: scan fabric fails on channel %d", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: scan fabric failed on channel %d", chan);
return (LOOP_LSCAN_DONE);
}
if (isp_control(isp, ISPCTL_PDB_SYNC, chan) != 0) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: pdb_sync fails on channel %d", chan);
+ isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: pdb_sync failed on channel %d", chan);
return (LOOP_FSCAN_DONE);
}
- if (fcp->isp_fwstate != FW_READY || fcp->isp_loopstate != LOOP_READY) {
- isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: f/w not ready again on channel %d", chan);
+ if (fcp->isp_loopstate != LOOP_READY) {
+ isp_prt(isp, ISP_LOG_SANCFG, "isp_fc_runstate: not ready again on channel %d", chan);
return (-1);
}
return (0);
@@ -536,7 +529,7 @@ isp_fc_fw_statename(int state)
{
switch (state) {
case FW_CONFIG_WAIT: return "Config Wait";
- case FW_WAIT_AL_PA: return "Waiting for AL_PA";
+ case FW_WAIT_LINK: return "Wait Link";
case FW_WAIT_LOGIN: return "Wait Login";
case FW_READY: return "Ready";
case FW_LOSS_OF_SYNC: return "Loss Of Sync";
@@ -552,9 +545,9 @@ isp_fc_loop_statename(int state)
{
switch (state) {
case LOOP_NIL: return "NIL";
- case LOOP_LIP_RCVD: return "LIP Received";
- case LOOP_PDB_RCVD: return "PDB Received";
- case LOOP_SCANNING_LOOP: return "Scanning";
+ case LOOP_TESTING_LINK: return "Testing Link";
+ case LOOP_LTEST_DONE: return "Link Test Done";
+ case LOOP_SCANNING_LOOP: return "Scanning Loop";
case LOOP_LSCAN_DONE: return "Loop Scan Done";
case LOOP_SCANNING_FABRIC: return "Scanning Fabric";
case LOOP_FSCAN_DONE: return "Fabric Scan Done";
@@ -568,7 +561,7 @@ const char *
isp_fc_toponame(fcparam *fcp)
{
- if (fcp->isp_fwstate != FW_READY) {
+ if (fcp->isp_loopstate < LOOP_LTEST_DONE) {
return "Unavailable";
}
switch (fcp->isp_topo) {
@@ -2527,7 +2520,8 @@ isp_find_chan_by_did(ispsoftc_t *isp, uint32_t did, uint16_t *cp)
*cp = ISP_NOCHAN;
for (chan = 0; chan < isp->isp_nchan; chan++) {
fcparam *fcp = FCPARAM(isp, chan);
- if ((fcp->role & ISP_ROLE_TARGET) == 0 || fcp->isp_fwstate != FW_READY || fcp->isp_loopstate < LOOP_PDB_RCVD) {
+ if ((fcp->role & ISP_ROLE_TARGET) == 0 ||
+ fcp->isp_loopstate < LOOP_LTEST_DONE) {
continue;
}
if (fcp->isp_portid == did) {
diff --git a/sys/dev/isp/ispvar.h b/sys/dev/isp/ispvar.h
index 233c88c..0bf592f 100644
--- a/sys/dev/isp/ispvar.h
+++ b/sys/dev/isp/ispvar.h
@@ -482,7 +482,7 @@ typedef struct {
} fcparam;
#define FW_CONFIG_WAIT 0
-#define FW_WAIT_AL_PA 1
+#define FW_WAIT_LINK 1
#define FW_WAIT_LOGIN 2
#define FW_READY 3
#define FW_LOSS_OF_SYNC 4
@@ -491,8 +491,8 @@ typedef struct {
#define FW_NON_PART 7
#define LOOP_NIL 0
-#define LOOP_LIP_RCVD 1
-#define LOOP_PDB_RCVD 2
+#define LOOP_TESTING_LINK 1
+#define LOOP_LTEST_DONE 2
#define LOOP_SCANNING_LOOP 3
#define LOOP_LSCAN_DONE 4
#define LOOP_SCANNING_FABRIC 5
@@ -861,10 +861,10 @@ void isp_done(XS_T *);
* Update any operating parameters (speed, etc.)
* ... ISPCTL_FCLINK_TEST, int channel);
* Test FC link status on this channel
- * ... ISPCTL_SCAN_FABRIC, int channel);
- * Scan fabric on this channel
* ... ISPCTL_SCAN_LOOP, int channel);
* Scan local loop on this channel
+ * ... ISPCTL_SCAN_FABRIC, int channel);
+ * Scan fabric on this channel
* ... ISPCTL_PDB_SYNC, int channel);
* Synchronize port database on this channel
* ... ISPCTL_SEND_LIP, int channel);
@@ -881,12 +881,11 @@ void isp_done(XS_T *);
* Change role of specified channel
*
* ISPCTL_PDB_SYNC is somewhat misnamed. It actually is the final step, in
- * order, of ISPCTL_FCLINK_TEST, ISPCTL_SCAN_FABRIC, and ISPCTL_SCAN_LOOP.
+ * order, of ISPCTL_FCLINK_TEST, ISPCTL_SCAN_LOOP, and ISPCTL_SCAN_FABRIC.
* The main purpose of ISPCTL_PDB_SYNC is to complete management of logging
* and logging out of fabric devices (if one is on a fabric) and then marking
* the 'loop state' as being ready to now be used for sending commands to
- * devices. Originally fabric name server and local loop scanning were
- * part of this function. It's now been separated to allow for finer control.
+ * devices.
*/
typedef enum {
ISPCTL_RESET_BUS,
OpenPOWER on IntegriCloud