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

scsi: qla2xxx: Move resource to allow code reuse



dsd_list contains a list of dsd buffer resources allocated during traffic
time. It resides in the qla_hw_data location where some of the code is not
reusable.

Move this list to qpair to allow reuse by either single queue or multi
queue adapter / code.

Signed-off-by: default avatarQuinn Tran <qutran@marvell.com>
Signed-off-by: default avatarNilesh Javali <njavali@marvell.com>
Link: https://lore.kernel.org/r/20230817063132.21900-2-njavali@marvell.com


Reviewed-by: default avatarHimanshu Madhani <himanshu.madhani@oracle.com>
Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parent a31a596a
Loading
Loading
Loading
Loading
+6 −5
Original line number Diff line number Diff line
@@ -3787,6 +3787,12 @@ struct qla_qpair {

	uint16_t id;			/* qp number used with FW */
	uint16_t vp_idx;		/* vport ID */

	uint16_t dsd_inuse;
	uint16_t dsd_avail;
	struct list_head dsd_list;
#define NUM_DSD_CHAIN 4096

	mempool_t *srb_mempool;

	struct pci_dev  *pdev;
@@ -4715,11 +4721,6 @@ struct qla_hw_data {
	struct fw_blob	*hablob;
	struct qla82xx_legacy_intr_set nx_legacy_intr;

	uint16_t	gbl_dsd_inuse;
	uint16_t	gbl_dsd_avail;
	struct list_head gbl_dsd_list;
#define NUM_DSD_CHAIN 4096

	uint8_t fw_type;
	uint32_t file_prd_off;	/* File firmware product offset */

+14 −0
Original line number Diff line number Diff line
@@ -9643,6 +9643,7 @@ struct qla_qpair *qla2xxx_create_qpair(struct scsi_qla_host *vha, int qos,
		qpair->vp_idx = vp_idx;
		qpair->fw_started = ha->flags.fw_started;
		INIT_LIST_HEAD(&qpair->hints_list);
		INIT_LIST_HEAD(&qpair->dsd_list);
		qpair->chip_reset = ha->base_qpair->chip_reset;
		qpair->enable_class_2 = ha->base_qpair->enable_class_2;
		qpair->enable_explicit_conf =
@@ -9771,6 +9772,19 @@ int qla2xxx_delete_qpair(struct scsi_qla_host *vha, struct qla_qpair *qpair)
	if (ret != QLA_SUCCESS)
		goto fail;

	if (!list_empty(&qpair->dsd_list)) {
		struct dsd_dma *dsd_ptr, *tdsd_ptr;

		/* clean up allocated prev pool */
		list_for_each_entry_safe(dsd_ptr, tdsd_ptr,
					 &qpair->dsd_list, list) {
			dma_pool_free(ha->dl_dma_pool, dsd_ptr->dsd_addr,
				      dsd_ptr->dsd_list_dma);
			list_del(&dsd_ptr->list);
			kfree(dsd_ptr);
		}
	}

	mutex_lock(&ha->mq_lock);
	ha->queue_pair_map[qpair->id] = NULL;
	clear_bit(qpair->id, ha->qpair_qid_map);
+10 −10
Original line number Diff line number Diff line
@@ -636,14 +636,13 @@ qla24xx_build_scsi_type_6_iocbs(srb_t *sp, struct cmd_type_6 *cmd_pkt,
		tot_dsds -= avail_dsds;
		dsd_list_len = (avail_dsds + 1) * QLA_DSD_SIZE;

		dsd_ptr = list_first_entry(&ha->gbl_dsd_list,
		    struct dsd_dma, list);
		dsd_ptr = list_first_entry(&qpair->dsd_list, struct dsd_dma, list);
		next_dsd = dsd_ptr->dsd_addr;
		list_del(&dsd_ptr->list);
		ha->gbl_dsd_avail--;
		qpair->dsd_avail--;
		list_add_tail(&dsd_ptr->list, &ctx->dsd_list);
		ctx->dsd_use_cnt++;
		ha->gbl_dsd_inuse++;
		qpair->dsd_inuse++;

		if (first_iocb) {
			first_iocb = 0;
@@ -3367,6 +3366,7 @@ qla82xx_start_scsi(srb_t *sp)
	struct qla_hw_data *ha = vha->hw;
	struct req_que *req = NULL;
	struct rsp_que *rsp = NULL;
	struct qla_qpair *qpair = sp->qpair;

	/* Setup device pointers. */
	reg = &ha->iobase->isp82;
@@ -3415,18 +3415,18 @@ qla82xx_start_scsi(srb_t *sp)
		uint16_t i;

		more_dsd_lists = qla24xx_calc_dsd_lists(tot_dsds);
		if ((more_dsd_lists + ha->gbl_dsd_inuse) >= NUM_DSD_CHAIN) {
		if ((more_dsd_lists + qpair->dsd_inuse) >= NUM_DSD_CHAIN) {
			ql_dbg(ql_dbg_io, vha, 0x300d,
			    "Num of DSD list %d is than %d for cmd=%p.\n",
			    more_dsd_lists + ha->gbl_dsd_inuse, NUM_DSD_CHAIN,
			    more_dsd_lists + qpair->dsd_inuse, NUM_DSD_CHAIN,
			    cmd);
			goto queuing_error;
		}

		if (more_dsd_lists <= ha->gbl_dsd_avail)
		if (more_dsd_lists <= qpair->dsd_avail)
			goto sufficient_dsds;
		else
			more_dsd_lists -= ha->gbl_dsd_avail;
			more_dsd_lists -= qpair->dsd_avail;

		for (i = 0; i < more_dsd_lists; i++) {
			dsd_ptr = kzalloc(sizeof(struct dsd_dma), GFP_ATOMIC);
@@ -3446,8 +3446,8 @@ qla82xx_start_scsi(srb_t *sp)
				    "for cmd=%p.\n", cmd);
				goto queuing_error;
			}
			list_add_tail(&dsd_ptr->list, &ha->gbl_dsd_list);
			ha->gbl_dsd_avail++;
			list_add_tail(&dsd_ptr->list, &qpair->dsd_list);
			qpair->dsd_avail++;
		}

sufficient_dsds:
+17 −19
Original line number Diff line number Diff line
@@ -432,6 +432,7 @@ static void qla_init_base_qpair(struct scsi_qla_host *vha, struct req_que *req,
	ha->base_qpair->msix = &ha->msix_entries[QLA_MSIX_RSP_Q];
	ha->base_qpair->srb_mempool = ha->srb_mempool;
	INIT_LIST_HEAD(&ha->base_qpair->hints_list);
	INIT_LIST_HEAD(&ha->base_qpair->dsd_list);
	ha->base_qpair->enable_class_2 = ql2xenableclass2;
	/* init qpair to this cpu. Will adjust at run time. */
	qla_cpu_update(rsp->qpair, raw_smp_processor_id());
@@ -750,9 +751,9 @@ void qla2x00_sp_free_dma(srb_t *sp)

		dma_pool_free(ha->fcp_cmnd_dma_pool, ctx1->fcp_cmnd,
		    ctx1->fcp_cmnd_dma);
		list_splice(&ctx1->dsd_list, &ha->gbl_dsd_list);
		ha->gbl_dsd_inuse -= ctx1->dsd_use_cnt;
		ha->gbl_dsd_avail += ctx1->dsd_use_cnt;
		list_splice(&ctx1->dsd_list, &sp->qpair->dsd_list);
		sp->qpair->dsd_inuse -= ctx1->dsd_use_cnt;
		sp->qpair->dsd_avail += ctx1->dsd_use_cnt;
	}

	if (sp->flags & SRB_GOT_BUF)
@@ -836,9 +837,9 @@ void qla2xxx_qpair_sp_free_dma(srb_t *sp)

		dma_pool_free(ha->fcp_cmnd_dma_pool, ctx1->fcp_cmnd,
		    ctx1->fcp_cmnd_dma);
		list_splice(&ctx1->dsd_list, &ha->gbl_dsd_list);
		ha->gbl_dsd_inuse -= ctx1->dsd_use_cnt;
		ha->gbl_dsd_avail += ctx1->dsd_use_cnt;
		list_splice(&ctx1->dsd_list, &sp->qpair->dsd_list);
		sp->qpair->dsd_inuse -= ctx1->dsd_use_cnt;
		sp->qpair->dsd_avail += ctx1->dsd_use_cnt;
		sp->flags &= ~SRB_FCP_CMND_DMA_VALID;
	}

@@ -4402,7 +4403,6 @@ qla2x00_mem_alloc(struct qla_hw_data *ha, uint16_t req_len, uint16_t rsp_len,
			   "sf_init_cb=%p.\n", ha->sf_init_cb);
	}

	INIT_LIST_HEAD(&ha->gbl_dsd_list);

	/* Get consistent memory allocated for Async Port-Database. */
	if (!IS_FWI2_CAPABLE(ha)) {
@@ -4934,20 +4934,18 @@ qla2x00_mem_free(struct qla_hw_data *ha)
	ha->gid_list = NULL;
	ha->gid_list_dma = 0;

	if (IS_QLA82XX(ha)) {
		if (!list_empty(&ha->gbl_dsd_list)) {
	if (!list_empty(&ha->base_qpair->dsd_list)) {
		struct dsd_dma *dsd_ptr, *tdsd_ptr;

		/* clean up allocated prev pool */
			list_for_each_entry_safe(dsd_ptr,
				tdsd_ptr, &ha->gbl_dsd_list, list) {
				dma_pool_free(ha->dl_dma_pool,
				dsd_ptr->dsd_addr, dsd_ptr->dsd_list_dma);
		list_for_each_entry_safe(dsd_ptr, tdsd_ptr,
					 &ha->base_qpair->dsd_list, list) {
			dma_pool_free(ha->dl_dma_pool, dsd_ptr->dsd_addr,
				      dsd_ptr->dsd_list_dma);
			list_del(&dsd_ptr->list);
			kfree(dsd_ptr);
		}
	}
	}

	dma_pool_destroy(ha->dl_dma_pool);
	ha->dl_dma_pool = NULL;