Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a4f92a32 authored by Andrew Vasquez's avatar Andrew Vasquez Committed by James Bottomley
Browse files

[SCSI] qla2xxx: Verify login-state has transitioned to PRLI-completed.



Before driver's own internal state is marked as PLOGI/PRLI
complete. This additional check closes a window seen with
dual-personality initiator/target devices where a driver's
PLOGI/PRLI request occurs within the window after the target's
PLOGI request has completed, but prior to the target's PRLI
arriving and processed by the firmware. Without this additional
check, the firmware will return port-information stating that the
port neither supports target nor initiator functions, causing the
driver to register the rport prematurely to the FC-transport
without the proper 'roles' being set.

Signed-off-by: default avatarAndrew Vasquez <andrew.vasquez@qlogic.com>
Signed-off-by: default avatarGiridhar Malavali <giridhar.malavali@qlogic.com>
Signed-off-by: default avatarMadhuranath Iyengar <Madhu.Iyengar@qlogic.com>
Signed-off-by: default avatarJames Bottomley <James.Bottomley@suse.de>
parent 92dbf273
Loading
Loading
Loading
Loading
+11 −0
Original line number Diff line number Diff line
@@ -383,6 +383,17 @@ qla2x00_async_login_done(struct scsi_qla_host *vha, fc_port_t *fcport,

	switch (data[0]) {
	case MBS_COMMAND_COMPLETE:
		/*
		 * Driver must validate login state - If PRLI not complete,
		 * force a relogin attempt via implicit LOGO, PLOGI, and PRLI
		 * requests.
		 */
		rval = qla2x00_get_port_database(vha, fcport, 0);
		if (rval != QLA_SUCCESS) {
			qla2x00_post_async_logout_work(vha, fcport, NULL);
			qla2x00_post_async_login_work(vha, fcport, NULL);
			break;
		}
		if (fcport->flags & FCF_FCP2_DEVICE) {
			qla2x00_post_async_adisc_work(vha, fcport, data);
			break;
+12 −5
Original line number Diff line number Diff line
@@ -1261,11 +1261,12 @@ qla2x00_get_port_database(scsi_qla_host_t *vha, fc_port_t *fcport, uint8_t opt)
		/* Check for logged in state. */
		if (pd24->current_login_state != PDS_PRLI_COMPLETE &&
		    pd24->last_login_state != PDS_PRLI_COMPLETE) {
			DEBUG2(printk("%s(%ld): Unable to verify "
			    "login-state (%x/%x) for loop_id %x\n",
			    __func__, vha->host_no,
			    pd24->current_login_state,
			    pd24->last_login_state, fcport->loop_id));
			DEBUG2(qla_printk(KERN_WARNING, ha,
			   "scsi(%ld): Unable to verify login-state (%x/%x) "
			   " - portid=%02x%02x%02x.\n", vha->host_no,
			   pd24->current_login_state, pd24->last_login_state,
			   fcport->d_id.b.domain, fcport->d_id.b.area,
			   fcport->d_id.b.al_pa));
			rval = QLA_FUNCTION_FAILED;
			goto gpd_error_out;
		}
@@ -1289,6 +1290,12 @@ qla2x00_get_port_database(scsi_qla_host_t *vha, fc_port_t *fcport, uint8_t opt)
		/* Check for logged in state. */
		if (pd->master_state != PD_STATE_PORT_LOGGED_IN &&
		    pd->slave_state != PD_STATE_PORT_LOGGED_IN) {
			DEBUG2(qla_printk(KERN_WARNING, ha,
			   "scsi(%ld): Unable to verify login-state (%x/%x) "
			   " - portid=%02x%02x%02x.\n", vha->host_no,
			   pd->master_state, pd->slave_state,
			   fcport->d_id.b.domain, fcport->d_id.b.area,
			   fcport->d_id.b.al_pa));
			rval = QLA_FUNCTION_FAILED;
			goto gpd_error_out;
		}