From 23dd98a6555897f65306c6937b428c8742fef610 Mon Sep 17 00:00:00 2001 From: Quinn Tran Date: Thu, 2 Aug 2018 13:16:45 -0700 Subject: scsi: qla2xxx: Fix login retry count Login retry count was not properly decrementing which lead to endless retry. Signed-off-by: Quinn Tran Signed-off-by: Himanshu Madhani Signed-off-by: Martin K. Petersen --- drivers/scsi/qla2xxx/qla_gs.c | 16 +++++++ drivers/scsi/qla2xxx/qla_init.c | 23 +++------- drivers/scsi/qla2xxx/qla_mbx.c | 1 + drivers/scsi/qla2xxx/qla_os.c | 90 ++++++++++++++++++++------------------- drivers/scsi/qla2xxx/qla_target.c | 3 +- 5 files changed, 70 insertions(+), 63 deletions(-) (limited to 'drivers') diff --git a/drivers/scsi/qla2xxx/qla_gs.c b/drivers/scsi/qla2xxx/qla_gs.c index 4bc2b66b299f..5139a3577bb3 100644 --- a/drivers/scsi/qla2xxx/qla_gs.c +++ b/drivers/scsi/qla2xxx/qla_gs.c @@ -3475,6 +3475,14 @@ void qla24xx_handle_gpnid_event(scsi_qla_host_t *vha, struct event_arg *ea) fcport->rscn_gen++; fcport->scan_state = QLA_FCPORT_FOUND; fcport->flags |= FCF_FABRIC_DEVICE; + if (fcport->login_retry == 0) { + fcport->login_retry = + vha->hw->login_retry_count; + ql_dbg(ql_dbg_disc, vha, 0xffff, + "Port login retry %8phN, lid 0x%04x cnt=%d.\n", + fcport->port_name, fcport->loop_id, + fcport->login_retry); + } switch (fcport->disc_state) { case DSC_LOGIN_COMPLETE: /* recheck session is still intact. */ @@ -3967,6 +3975,14 @@ void qla24xx_async_gnnft_done(scsi_qla_host_t *vha, srb_t *sp) } else { if (fcport->rscn_rcvd || fcport->disc_state != DSC_LOGIN_COMPLETE) { + if (fcport->login_retry == 0) { + fcport->login_retry = + vha->hw->login_retry_count; + ql_dbg(ql_dbg_disc, vha, 0x20a3, + "Port login retry %8phN, lid 0x%04x retry cnt=%d.\n", + fcport->port_name, fcport->loop_id, + fcport->login_retry); + } fcport->rscn_rcvd = 0; qla24xx_fcport_handle_login(vha, fcport); } diff --git a/drivers/scsi/qla2xxx/qla_init.c b/drivers/scsi/qla2xxx/qla_init.c index 52e163553e90..aea264100673 100644 --- a/drivers/scsi/qla2xxx/qla_init.c +++ b/drivers/scsi/qla2xxx/qla_init.c @@ -213,8 +213,6 @@ qla2x00_async_login(struct scsi_qla_host *vha, fc_port_t *fcport, if (fcport->fc4f_nvme) lio->u.logio.flags |= SRB_LOGIN_SKIP_PRLI; - if (data[1] & QLA_LOGIO_LOGIN_RETRIED) - lio->u.logio.flags |= SRB_LOGIN_RETRIED; } rval = qla2x00_start_sp(sp); @@ -485,7 +483,6 @@ static void qla24xx_handle_gnl_done_event(scsi_qla_host_t *vha, if (ea->rc) { /* rval */ if (fcport->login_retry == 0) { - fcport->login_retry = vha->hw->login_retry_count; ql_dbg(ql_dbg_disc, vha, 0x20de, "GNL failed Port login retry %8phN, retry cnt=%d.\n", fcport->port_name, fcport->login_retry); @@ -1256,11 +1253,10 @@ int qla24xx_fcport_handle_login(struct scsi_qla_host *vha, fc_port_t *fcport) return 0; } - if (fcport->login_retry > 0) - fcport->login_retry--; switch (fcport->disc_state) { case DSC_DELETED: + fcport->login_retry--; wwn = wwn_to_u64(fcport->node_name); if (wwn == 0) { ql_dbg(ql_dbg_disc, vha, 0xffff, @@ -1273,6 +1269,7 @@ int qla24xx_fcport_handle_login(struct scsi_qla_host *vha, fc_port_t *fcport) __func__, __LINE__, fcport->port_name); qla24xx_post_gnl_work(vha, fcport); } else { + fcport->login_retry--; qla_chk_n2n_b4_login(vha, fcport); } break; @@ -1289,6 +1286,7 @@ int qla24xx_fcport_handle_login(struct scsi_qla_host *vha, fc_port_t *fcport) break; case DSC_LOGIN_FAILED: + fcport->login_retry--; ql_dbg(ql_dbg_disc, vha, 0x20d0, "%s %d %8phC post gidpn\n", __func__, __LINE__, fcport->port_name); @@ -1303,6 +1301,7 @@ int qla24xx_fcport_handle_login(struct scsi_qla_host *vha, fc_port_t *fcport) ql_dbg(ql_dbg_disc, vha, 0x20d1, "%s %d %8phC post adisc\n", __func__, __LINE__, fcport->port_name); + fcport->login_retry--; data[0] = data[1] = 0; qla2x00_post_async_adisc_work(vha, fcport, data); break; @@ -1386,17 +1385,6 @@ void qla24xx_handle_relogin_event(scsi_qla_host_t *vha, } } - if (fcport->flags & FCF_ASYNC_SENT) { - fcport->login_retry++; - set_bit(RELOGIN_NEEDED, &vha->dpc_flags); - return; - } - - if (fcport->disc_state == DSC_DELETE_PEND) { - fcport->login_retry++; - return; - } - if (fcport->last_rscn_gen != fcport->rscn_gen) { ql_dbg(ql_dbg_disc, vha, 0x20e9, "%s %d %8phC post gidpn\n", __func__, __LINE__, fcport->port_name); @@ -1882,7 +1870,6 @@ void qla2x00_async_logout_done(struct scsi_qla_host *vha, fc_port_t *fcport, uint16_t *data) { - qla2x00_mark_device_lost(vha, fcport, 1, 0); qlt_logo_completion_handler(fcport, data[0]); fcport->login_gen++; fcport->flags &= ~FCF_ASYNC_ACTIVE; @@ -5076,11 +5063,11 @@ qla2x00_update_fcport(scsi_qla_host_t *vha, fc_port_t *fcport) if (IS_QLAFX00(vha->hw)) { qla2x00_set_fcport_state(fcport, FCS_ONLINE); } else { - fcport->login_retry = 0; fcport->flags &= ~(FCF_LOGIN_NEEDED | FCF_ASYNC_SENT); fcport->disc_state = DSC_LOGIN_COMPLETE; fcport->deleted = 0; fcport->logout_on_delete = 1; + fcport->login_retry = vha->hw->login_retry_count; qla2x00_set_fcport_state(fcport, FCS_ONLINE); } diff --git a/drivers/scsi/qla2xxx/qla_mbx.c b/drivers/scsi/qla2xxx/qla_mbx.c index 4e42ce057a37..17537f0b3b54 100644 --- a/drivers/scsi/qla2xxx/qla_mbx.c +++ b/drivers/scsi/qla2xxx/qla_mbx.c @@ -3912,6 +3912,7 @@ qla24xx_report_id_acquisition(scsi_qla_host_t *vha, rptid_entry->u.f2.port_name, 1); if (fcport) { + fcport->login_retry = vha->hw->login_retry_count; fcport->plogi_nack_done_deadline = jiffies + HZ; fcport->scan_state = QLA_FCPORT_FOUND; } diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c index eb804e2feedf..e218d68de532 100644 --- a/drivers/scsi/qla2xxx/qla_os.c +++ b/drivers/scsi/qla2xxx/qla_os.c @@ -3838,14 +3838,6 @@ void qla2x00_mark_device_lost(scsi_qla_host_t *vha, fc_port_t *fcport, return; set_bit(RELOGIN_NEEDED, &vha->dpc_flags); - - if (fcport->login_retry == 0) { - fcport->login_retry = vha->hw->login_retry_count; - - ql_dbg(ql_dbg_disc, vha, 0x20a3, - "Port login retry %8phN, lid 0x%04x retry cnt=%d.\n", - fcport->port_name, fcport->loop_id, fcport->login_retry); - } } /* @@ -5098,7 +5090,7 @@ int qla24xx_post_relogin_work(struct scsi_qla_host *vha) void qla2x00_relogin(struct scsi_qla_host *vha) { fc_port_t *fcport; - int status; + int status, relogin_needed = 0; struct event_arg ea; list_for_each_entry(fcport, &vha->vp_fcports, list) { @@ -5107,47 +5099,59 @@ void qla2x00_relogin(struct scsi_qla_host *vha) * to it if we haven't run out of retries. */ if (atomic_read(&fcport->state) != FCS_ONLINE && - fcport->login_retry && - !(fcport->flags & (FCF_ASYNC_SENT | FCF_ASYNC_ACTIVE))) { - if (vha->hw->current_topology != ISP_CFG_NL) { - ql_dbg(ql_dbg_disc, fcport->vha, 0x2108, - "%s %8phC DS %d LS %d\n", __func__, - fcport->port_name, fcport->disc_state, - fcport->fw_login_state); - memset(&ea, 0, sizeof(ea)); - ea.event = FCME_RELOGIN; - ea.fcport = fcport; - qla2x00_fcport_event_handler(vha, &ea); - } else if (vha->hw->current_topology == ISP_CFG_NL) { - fcport->login_retry--; - status = qla2x00_local_device_login(vha, - fcport); - if (status == QLA_SUCCESS) { - fcport->old_loop_id = fcport->loop_id; - ql_dbg(ql_dbg_disc, vha, 0x2003, - "Port login OK: logged in ID 0x%x.\n", - fcport->loop_id); - qla2x00_update_fcport(vha, fcport); - } else if (status == 1) { - set_bit(RELOGIN_NEEDED, &vha->dpc_flags); - /* retry the login again */ - ql_dbg(ql_dbg_disc, vha, 0x2007, - "Retrying %d login again loop_id 0x%x.\n", - fcport->login_retry, - fcport->loop_id); - } else { - fcport->login_retry = 0; - } + fcport->login_retry) { + if (fcport->scan_state != QLA_FCPORT_FOUND || + fcport->disc_state == DSC_LOGIN_COMPLETE) + continue; - if (fcport->login_retry == 0 && - status != QLA_SUCCESS) - qla2x00_clear_loop_id(fcport); + if (fcport->flags & (FCF_ASYNC_SENT|FCF_ASYNC_ACTIVE) || + fcport->disc_state == DSC_DELETE_PEND) { + relogin_needed = 1; + } else { + if (vha->hw->current_topology != ISP_CFG_NL) { + memset(&ea, 0, sizeof(ea)); + ea.event = FCME_RELOGIN; + ea.fcport = fcport; + qla2x00_fcport_event_handler(vha, &ea); + } else if (vha->hw->current_topology == + ISP_CFG_NL) { + fcport->login_retry--; + status = + qla2x00_local_device_login(vha, + fcport); + if (status == QLA_SUCCESS) { + fcport->old_loop_id = + fcport->loop_id; + ql_dbg(ql_dbg_disc, vha, 0x2003, + "Port login OK: logged in ID 0x%x.\n", + fcport->loop_id); + qla2x00_update_fcport + (vha, fcport); + } else if (status == 1) { + set_bit(RELOGIN_NEEDED, + &vha->dpc_flags); + /* retry the login again */ + ql_dbg(ql_dbg_disc, vha, 0x2007, + "Retrying %d login again loop_id 0x%x.\n", + fcport->login_retry, + fcport->loop_id); + } else { + fcport->login_retry = 0; + } + + if (fcport->login_retry == 0 && + status != QLA_SUCCESS) + qla2x00_clear_loop_id(fcport); + } } } if (test_bit(LOOP_RESYNC_NEEDED, &vha->dpc_flags)) break; } + if (relogin_needed) + set_bit(RELOGIN_NEEDED, &vha->dpc_flags); + ql_dbg(ql_dbg_disc, vha, 0x400e, "Relogin end.\n"); } diff --git a/drivers/scsi/qla2xxx/qla_target.c b/drivers/scsi/qla2xxx/qla_target.c index 9d10989ed027..4f9c315813df 100644 --- a/drivers/scsi/qla2xxx/qla_target.c +++ b/drivers/scsi/qla2xxx/qla_target.c @@ -1057,7 +1057,6 @@ void qlt_free_session_done(struct work_struct *work) sess->disc_state = DSC_DELETED; sess->fw_login_state = DSC_LS_PORT_UNAVAIL; sess->deleted = QLA_SESS_DELETED; - sess->login_retry = vha->hw->login_retry_count; if (sess->login_succ && !IS_SW_RESV_ADDR(sess->d_id)) { vha->fcport_count--; @@ -1161,7 +1160,7 @@ void qlt_unreg_sess(struct fc_port *sess) if (sess->se_sess) vha->hw->tgt.tgt_ops->clear_nacl_from_fcport_map(sess); - qla2x00_mark_device_lost(vha, sess, 1, 1); + qla2x00_mark_device_lost(vha, sess, 0, 0); sess->deleted = QLA_SESS_DELETION_IN_PROGRESS; sess->disc_state = DSC_DELETE_PEND; -- cgit v1.2.3