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

Commit 45235022 authored by Quinn Tran's avatar Quinn Tran Committed by Martin K. Petersen
Browse files

scsi: qla2xxx: Fix driver unload by shutting down chip



Use chip shutdown at the start of unload to stop all DMA + traffic and
bring down the laser. This prevents any link activities from triggering the
driver to be re-engaged.

Fixes: 4b60c827 ("scsi: qla2xxx: Add fw_started flags to qpair")
Cc: <stable@vger.kernel.org> #4.16
Signed-off-by: default avatarQuinn Tran <quinn.tran@cavium.com>
Signed-off-by: default avatarHimanshu Madhani <himanshu.madhani@cavium.com>
Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parent efa93f48
Loading
Loading
Loading
Loading
+3 −0
Original line number Diff line number Diff line
@@ -631,6 +631,9 @@ qla2x00_async_event(scsi_qla_host_t *vha, struct rsp_que *rsp, uint16_t *mb)
	unsigned long	flags;
	fc_port_t	*fcport = NULL;

	if (!vha->hw->flags.fw_started)
		return;

	/* Setup to process RIO completion. */
	handle_cnt = 0;
	if (IS_CNA_CAPABLE(ha))
+6 −0
Original line number Diff line number Diff line
@@ -4220,6 +4220,9 @@ qla25xx_init_req_que(struct scsi_qla_host *vha, struct req_que *req)
	mbx_cmd_t *mcp = &mc;
	struct qla_hw_data *ha = vha->hw;

	if (!ha->flags.fw_started)
		return QLA_SUCCESS;

	ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d3,
	    "Entered %s.\n", __func__);

@@ -4289,6 +4292,9 @@ qla25xx_init_rsp_que(struct scsi_qla_host *vha, struct rsp_que *rsp)
	mbx_cmd_t *mcp = &mc;
	struct qla_hw_data *ha = vha->hw;

	if (!ha->flags.fw_started)
		return QLA_SUCCESS;

	ql_dbg(ql_dbg_mbx + ql_dbg_verbose, vha, 0x10d6,
	    "Entered %s.\n", __func__);

+4 −2
Original line number Diff line number Diff line
@@ -152,10 +152,12 @@ int
qla24xx_disable_vp(scsi_qla_host_t *vha)
{
	unsigned long flags;
	int ret;
	int ret = QLA_SUCCESS;
	fc_port_t *fcport;

	if (vha->hw->flags.fw_started)
		ret = qla24xx_control_vp(vha, VCE_COMMAND_DISABLE_VPS_LOGO_ALL);

	atomic_set(&vha->loop_state, LOOP_DOWN);
	atomic_set(&vha->loop_down_timer, LOOP_DOWN_TIME);
	list_for_each_entry(fcport, &vha->vp_fcports, list)
+18 −26
Original line number Diff line number Diff line
@@ -303,6 +303,7 @@ static void qla2x00_free_device(scsi_qla_host_t *);
static int qla2xxx_map_queues(struct Scsi_Host *shost);
static void qla2x00_destroy_deferred_work(struct qla_hw_data *);


struct scsi_host_template qla2xxx_driver_template = {
	.module			= THIS_MODULE,
	.name			= QLA2XXX_DRIVER_NAME,
@@ -3603,6 +3604,8 @@ qla2x00_remove_one(struct pci_dev *pdev)

	base_vha = pci_get_drvdata(pdev);
	ha = base_vha->hw;
	ql_log(ql_log_info, base_vha, 0xb079,
	    "Removing driver\n");

	/* Indicate device removal to prevent future board_disable and wait
	 * until any pending board_disable has completed. */
@@ -3625,6 +3628,21 @@ qla2x00_remove_one(struct pci_dev *pdev)
	}
	qla2x00_wait_for_hba_ready(base_vha);

	if (IS_QLA25XX(ha) || IS_QLA2031(ha) || IS_QLA27XX(ha)) {
		if (ha->flags.fw_started)
			qla2x00_abort_isp_cleanup(base_vha);
	} else if (!IS_QLAFX00(ha)) {
		if (IS_QLA8031(ha)) {
			ql_dbg(ql_dbg_p3p, base_vha, 0xb07e,
			    "Clearing fcoe driver presence.\n");
			if (qla83xx_clear_drv_presence(base_vha) != QLA_SUCCESS)
				ql_dbg(ql_dbg_p3p, base_vha, 0xb079,
				    "Error while clearing DRV-Presence.\n");
		}

		qla2x00_try_to_stop_firmware(base_vha);
	}

	qla2x00_wait_for_sess_deletion(base_vha);

	/*
@@ -3648,14 +3666,6 @@ qla2x00_remove_one(struct pci_dev *pdev)

	qla2x00_delete_all_vps(ha, base_vha);

	if (IS_QLA8031(ha)) {
		ql_dbg(ql_dbg_p3p, base_vha, 0xb07e,
		    "Clearing fcoe driver presence.\n");
		if (qla83xx_clear_drv_presence(base_vha) != QLA_SUCCESS)
			ql_dbg(ql_dbg_p3p, base_vha, 0xb079,
			    "Error while clearing DRV-Presence.\n");
	}

	qla2x00_abort_all_cmds(base_vha, DID_NO_CONNECT << 16);

	qla2x00_dfs_remove(base_vha);
@@ -3715,24 +3725,6 @@ qla2x00_free_device(scsi_qla_host_t *vha)
		qla2x00_stop_timer(vha);

	qla25xx_delete_queues(vha);

	if (ha->flags.fce_enabled)
		qla2x00_disable_fce_trace(vha, NULL, NULL);

	if (ha->eft)
		qla2x00_disable_eft_trace(vha);

	if (IS_QLA25XX(ha) ||  IS_QLA2031(ha) || IS_QLA27XX(ha)) {
		if (ha->flags.fw_started)
			qla2x00_abort_isp_cleanup(vha);
	} else {
		if (ha->flags.fw_started) {
			/* Stop currently executing firmware. */
			qla2x00_try_to_stop_firmware(vha);
			ha->flags.fw_started = 0;
		}
	}

	vha->flags.online = 0;

	/* turn-off interrupts on the card */
+3 −0
Original line number Diff line number Diff line
@@ -1880,6 +1880,9 @@ qla24xx_beacon_off(struct scsi_qla_host *vha)
	if (IS_P3P_TYPE(ha))
		return QLA_SUCCESS;

	if (!ha->flags.fw_started)
		return QLA_SUCCESS;

	ha->beacon_blink_led = 0;

	if (IS_QLA2031(ha) || IS_QLA27XX(ha))